From 3597f792356e23fe32ec8682b1db1cf9a44c9a6e Mon Sep 17 00:00:00 2001 From: Jeremy Stretch Date: Fri, 4 Aug 2023 15:46:57 -0400 Subject: [PATCH 1/3] Introduce get_installed_plugins() utility --- netbox/extras/plugins/utils.py | 19 +++++++++++++++++++ netbox/netbox/api/views.py | 11 ++--------- 2 files changed, 21 insertions(+), 9 deletions(-) create mode 100644 netbox/extras/plugins/utils.py diff --git a/netbox/extras/plugins/utils.py b/netbox/extras/plugins/utils.py new file mode 100644 index 00000000000..8ec7ac67997 --- /dev/null +++ b/netbox/extras/plugins/utils.py @@ -0,0 +1,19 @@ +from django.apps import apps +from django.conf import settings + +__all__ = ( + 'get_installed_plugins', +) + + +def get_installed_plugins(): + """ + Return a dictionary mapping the names of installed plugins to their versions. + """ + plugins = {} + for plugin_name in settings.PLUGINS: + plugin_name = plugin_name.rsplit('.', 1)[-1] + plugin_config = apps.get_app_config(plugin_name) + plugins[plugin_name] = getattr(plugin_config, 'version', None) + + return dict(sorted(plugins.items())) diff --git a/netbox/netbox/api/views.py b/netbox/netbox/api/views.py index 5c55697ff6c..97f690762b7 100644 --- a/netbox/netbox/api/views.py +++ b/netbox/netbox/api/views.py @@ -11,6 +11,7 @@ from rest_framework.views import APIView from rq.worker import Worker +from extras.plugins.utils import get_installed_plugins from netbox.api.authentication import IsAuthenticatedOrLoginNotRequired @@ -61,19 +62,11 @@ def get(self, request): installed_apps[app_config.name] = version installed_apps = {k: v for k, v in sorted(installed_apps.items())} - # Gather installed plugins - plugins = {} - for plugin_name in settings.PLUGINS: - plugin_name = plugin_name.rsplit('.', 1)[-1] - plugin_config = apps.get_app_config(plugin_name) - plugins[plugin_name] = getattr(plugin_config, 'version', None) - plugins = {k: v for k, v in sorted(plugins.items())} - return Response({ 'django-version': DJANGO_VERSION, 'installed-apps': installed_apps, 'netbox-version': settings.VERSION, - 'plugins': plugins, + 'plugins': get_installed_plugins(), 'python-version': platform.python_version(), 'rq-workers-running': Worker.count(get_connection('default')), }) From 82180ecf42a917dfdb67fa9aea4ecb832c1eada8 Mon Sep 17 00:00:00 2001 From: Jeremy Stretch Date: Fri, 4 Aug 2023 15:55:51 -0400 Subject: [PATCH 2/3] Extend 500 error template to list installed plugins --- netbox/netbox/views/errors.py | 3 +++ netbox/templates/500.html | 5 ++++- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/netbox/netbox/views/errors.py b/netbox/netbox/views/errors.py index c74c67cef06..a81d45cb5cb 100644 --- a/netbox/netbox/views/errors.py +++ b/netbox/netbox/views/errors.py @@ -11,6 +11,8 @@ from django.views.generic import View from sentry_sdk import capture_message +from extras.plugins.utils import get_installed_plugins + __all__ = ( 'handler_404', 'handler_500', @@ -53,4 +55,5 @@ def handler_500(request, template_name=ERROR_500_TEMPLATE_NAME): 'exception': str(type_), 'netbox_version': settings.VERSION, 'python_version': platform.python_version(), + 'plugins': get_installed_plugins(), })) diff --git a/netbox/templates/500.html b/netbox/templates/500.html index 6cface941cd..0257e7c4370 100644 --- a/netbox/templates/500.html +++ b/netbox/templates/500.html @@ -30,7 +30,10 @@
{{ error }} Python version: {{ python_version }} -NetBox version: {{ netbox_version }} +NetBox version: {{ netbox_version }} +Plugins: {% for plugin, version in plugins.items %} + {{ plugin }}: {{ version }}{% empty %}None installed{% endfor %} +

If further assistance is required, please post to the NetBox discussion forum on GitHub.

From a6229ba56ea3f0736744a7e43969036335f324b8 Mon Sep 17 00:00:00 2001 From: Jeremy Stretch Date: Fri, 4 Aug 2023 15:58:31 -0400 Subject: [PATCH 3/3] Move get_plugin_config() to extras.plugins.utils --- netbox/extras/plugins/__init__.py | 21 --------------------- netbox/extras/plugins/utils.py | 18 ++++++++++++++++++ netbox/extras/tests/test_plugins.py | 3 ++- 3 files changed, 20 insertions(+), 22 deletions(-) diff --git a/netbox/extras/plugins/__init__.py b/netbox/extras/plugins/__init__.py index 83c7a7bb0e2..8736a319794 100644 --- a/netbox/extras/plugins/__init__.py +++ b/netbox/extras/plugins/__init__.py @@ -2,7 +2,6 @@ from importlib import import_module from django.apps import AppConfig -from django.conf import settings from django.core.exceptions import ImproperlyConfigured from django.utils.module_loading import import_string from packaging import version @@ -146,23 +145,3 @@ def validate(cls, user_config, netbox_version): for setting, value in cls.default_settings.items(): if setting not in user_config: user_config[setting] = value - - -# -# Utilities -# - -def get_plugin_config(plugin_name, parameter, default=None): - """ - Return the value of the specified plugin configuration parameter. - - Args: - plugin_name: The name of the plugin - parameter: The name of the configuration parameter - default: The value to return if the parameter is not defined (default: None) - """ - try: - plugin_config = settings.PLUGINS_CONFIG[plugin_name] - return plugin_config.get(parameter, default) - except KeyError: - raise ImproperlyConfigured(f"Plugin {plugin_name} is not registered.") diff --git a/netbox/extras/plugins/utils.py b/netbox/extras/plugins/utils.py index 8ec7ac67997..c260f156db6 100644 --- a/netbox/extras/plugins/utils.py +++ b/netbox/extras/plugins/utils.py @@ -1,8 +1,10 @@ from django.apps import apps from django.conf import settings +from django.core.exceptions import ImproperlyConfigured __all__ = ( 'get_installed_plugins', + 'get_plugin_config', ) @@ -17,3 +19,19 @@ def get_installed_plugins(): plugins[plugin_name] = getattr(plugin_config, 'version', None) return dict(sorted(plugins.items())) + + +def get_plugin_config(plugin_name, parameter, default=None): + """ + Return the value of the specified plugin configuration parameter. + + Args: + plugin_name: The name of the plugin + parameter: The name of the configuration parameter + default: The value to return if the parameter is not defined (default: None) + """ + try: + plugin_config = settings.PLUGINS_CONFIG[plugin_name] + return plugin_config.get(parameter, default) + except KeyError: + raise ImproperlyConfigured(f"Plugin {plugin_name} is not registered.") diff --git a/netbox/extras/tests/test_plugins.py b/netbox/extras/tests/test_plugins.py index cb7629ad24e..42dde43fdff 100644 --- a/netbox/extras/tests/test_plugins.py +++ b/netbox/extras/tests/test_plugins.py @@ -5,8 +5,9 @@ from django.test import Client, TestCase, override_settings from django.urls import reverse -from extras.plugins import PluginMenu, get_plugin_config +from extras.plugins import PluginMenu from extras.tests.dummy_plugin import config as dummy_config +from extras.plugins.utils import get_plugin_config from netbox.graphql.schema import Query from netbox.registry import registry