From 1cf8a1f222868e946573114b7f42ed5c6b6b9700 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Norman=20J=C3=A4ckel?= Date: Fri, 10 Jul 2015 15:07:11 +0200 Subject: [PATCH] Updated plugin utils. Enabled plugins to override urlpatterns. --- CHANGELOG | 1 + openslides/urls.py | 8 +++++-- openslides/utils/plugins.py | 45 +++++++++++++++++++++++++++---------- 3 files changed, 40 insertions(+), 14 deletions(-) diff --git a/CHANGELOG b/CHANGELOG index 9cb47a72a..b17f7fc19 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -44,6 +44,7 @@ Other: now. - Updated to Bootstrap 3. - Used SockJS for automatic update of AngularJS driven single page frontend. +- Refactored plugin API. - Refactored start script and management commands. - Refactored tests. - Used Bower and gulp to manage third party JavaScript and Cascading Style diff --git a/openslides/urls.py b/openslides/urls.py index cd83c4801..2f7f24404 100644 --- a/openslides/urls.py +++ b/openslides/urls.py @@ -1,9 +1,12 @@ from django.conf.urls import include, patterns, url from django.views.generic import RedirectView +from openslides.utils.plugins import get_all_plugin_urlpatterns from openslides.utils.rest_api import router -urlpatterns = patterns( +urlpatterns = get_all_plugin_urlpatterns() + +urlpatterns += patterns( '', url(r'^(?P.*[^/])$', RedirectView.as_view(url='/%(url)s/', permanent=True)), url(r'^rest/', include(router.urls)), @@ -12,6 +15,7 @@ urlpatterns = patterns( url(r'^motions/', include('openslides.motions.urls')), url(r'^users/', include('openslides.users.urls')), - # The urls.py for the core app has to be the last entry in the urls.py + # The urls.py of the core app has to be the last entry. It contains the + # main entry points for OpenSlides' browser clients. url(r'^', include('openslides.core.urls')), ) diff --git a/openslides/utils/plugins.py b/openslides/utils/plugins.py index c532b1b66..2d1ae47fe 100644 --- a/openslides/utils/plugins.py +++ b/openslides/utils/plugins.py @@ -2,6 +2,7 @@ import os import pkgutil import sys +from django.conf import settings from django.utils.importlib import import_module from pkg_resources import iter_entry_points @@ -14,7 +15,9 @@ from openslides.utils.main import ( plugins = {} -def get_plugins_from_entry_points(): +# Methods to collect plugins. + +def collect_plugins_from_entry_points(): """ Collects all entry points in the group openslides_plugins from all distributions in the default working set and returns their module names as @@ -23,10 +26,10 @@ def get_plugins_from_entry_points(): return tuple(entry_point.module_name for entry_point in iter_entry_points('openslides_plugins')) -def get_plugins_from_path(path): +def collect_plugins_from_path(path): """ - Collects all modules/packages in the given `path` - and returns a tuple of their names + Collects all modules/packages in the given `path` and returns a tuple + of their names. """ return tuple(x[1] for x in pkgutil.iter_modules([path])) @@ -35,16 +38,21 @@ def collect_plugins(): """ Collect all plugins that can be automatically discovered. """ - plugins = get_plugins_from_entry_points() - # add all modules in plugins/ dir of portable automatically + # Collect plugins from entry points. + collected_plugins = collect_plugins_from_entry_points() + + # Collect plugins in plugins/ directory of portable. if detect_openslides_type() == WINDOWS_PORTABLE_VERSION: plugins_path = os.path.join( - get_win32_portable_user_data_path(), "plugins") + get_win32_portable_user_data_path(), 'plugins') if plugins_path not in sys.path: sys.path.append(plugins_path) - plugins += get_plugins_from_path(plugins_path) - return plugins + collected_plugins += collect_plugins_from_path(plugins_path) + return collected_plugins + + +# Methods to retrieve plugins and their metadata. def get_plugin(plugin): """ @@ -93,7 +101,7 @@ def get_plugin_description(plugin): def get_plugin_version(plugin): """ - Returns the version string of a plugin. The plugin argument must be a# + Returns the version string of a plugin. The plugin argument must be a python dotted module path. """ plugin = get_plugin(plugin) @@ -107,17 +115,30 @@ def get_plugin_version(plugin): return version -def get_urlpatterns(plugin): +def get_plugin_urlpatterns(plugin): """ Returns the urlpatterns object for a plugin. The plugin argument must be a python dotted module path. """ plugin = get_plugin(plugin) try: - urlpatterns = plugin.urlpatterns + urlpatterns = plugin.get_urlpatterns() except AttributeError: try: urlpatterns = plugin.urls.urlpatterns except AttributeError: urlpatterns = None return urlpatterns + + +def get_all_plugin_urlpatterns(): + """ + Helper function to return all urlpatterns of all plugins listed in + settings.INSTALLED_PLUGINS. + """ + urlpatterns = [] + for plugin in settings.INSTALLED_PLUGINS: + plugin_urlpatterns = get_plugin_urlpatterns(plugin) + if plugin_urlpatterns: + urlpatterns += plugin_urlpatterns + return urlpatterns