mirror of
https://github.com/inventree/InvenTree.git
synced 2025-07-01 19:20:55 +00:00
Plugin url fix (#9833)
* Handle error when loading plugin URLs - Error separation between plugins - Format plugin URLs outside the plugin code - Add "catch-all" URL * Attempt to resolve URL * Accept 404 error * Cleanup * Tweak unit tests
This commit is contained in:
@ -1,7 +1,6 @@
|
|||||||
"""Plugin mixin class for UrlsMixin."""
|
"""Plugin mixin class for UrlsMixin."""
|
||||||
|
|
||||||
from django.conf import settings
|
from django.conf import settings
|
||||||
from django.urls import include, re_path
|
|
||||||
|
|
||||||
import structlog
|
import structlog
|
||||||
|
|
||||||
@ -72,12 +71,8 @@ class UrlsMixin:
|
|||||||
|
|
||||||
@property
|
@property
|
||||||
def urlpatterns(self):
|
def urlpatterns(self):
|
||||||
"""Urlpatterns for this plugin."""
|
"""URL patterns for this plugin."""
|
||||||
if self.has_urls:
|
return self.urls or None
|
||||||
return re_path(
|
|
||||||
f'^{self.slug}/', include((self.urls, self.slug)), name=self.slug
|
|
||||||
)
|
|
||||||
return None
|
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def has_urls(self):
|
def has_urls(self):
|
||||||
|
@ -113,13 +113,10 @@ class UrlsMixinTest(BaseMixinDefinition, TestCase):
|
|||||||
target_pattern = re_path(
|
target_pattern = re_path(
|
||||||
f'^{plg_name}/', include((self.mixin.urls, plg_name)), name=plg_name
|
f'^{plg_name}/', include((self.mixin.urls, plg_name)), name=plg_name
|
||||||
)
|
)
|
||||||
self.assertEqual(
|
|
||||||
self.mixin.urlpatterns.reverse_dict, target_pattern.reverse_dict
|
|
||||||
)
|
|
||||||
|
|
||||||
# resolve the view
|
# resolve the view
|
||||||
self.assertEqual(self.mixin.urlpatterns.resolve('/testpath').func(), 'ccc')
|
self.assertEqual(target_pattern.resolve('/testpath').func(), 'ccc')
|
||||||
self.assertEqual(self.mixin.urlpatterns.reverse('test'), 'testpath')
|
self.assertEqual(target_pattern.reverse('test'), 'testpath')
|
||||||
|
|
||||||
# no url
|
# no url
|
||||||
self.assertIsNone(self.mixin_nothing.urls)
|
self.assertIsNone(self.mixin_nothing.urls)
|
||||||
|
@ -2,8 +2,11 @@
|
|||||||
|
|
||||||
from django.conf import settings
|
from django.conf import settings
|
||||||
from django.urls import include, re_path
|
from django.urls import include, re_path
|
||||||
|
from django.urls.exceptions import Resolver404
|
||||||
|
from django.views.generic.base import RedirectView
|
||||||
|
|
||||||
from common.validators import get_global_setting
|
from common.validators import get_global_setting
|
||||||
|
from InvenTree.exceptions import log_error
|
||||||
from plugin import PluginMixinEnum
|
from plugin import PluginMixinEnum
|
||||||
|
|
||||||
PLUGIN_BASE = 'plugin' # Constant for links
|
PLUGIN_BASE = 'plugin' # Constant for links
|
||||||
@ -16,8 +19,35 @@ def get_plugin_urls():
|
|||||||
urls = []
|
urls = []
|
||||||
|
|
||||||
if get_global_setting('ENABLE_PLUGINS_URL', False) or settings.PLUGIN_TESTING_SETUP:
|
if get_global_setting('ENABLE_PLUGINS_URL', False) or settings.PLUGIN_TESTING_SETUP:
|
||||||
for plugin in registry.plugins.values():
|
for plugin in registry.with_mixin(PluginMixinEnum.URLS):
|
||||||
if plugin.mixin_enabled(PluginMixinEnum.URLS):
|
try:
|
||||||
urls.append(plugin.urlpatterns)
|
if plugin_urls := plugin.urlpatterns:
|
||||||
|
# Check if the plugin has a custom URL pattern
|
||||||
|
for url in plugin_urls:
|
||||||
|
# Attempt to resolve against the URL pattern as a validation check
|
||||||
|
try:
|
||||||
|
url.resolve('')
|
||||||
|
except Resolver404:
|
||||||
|
pass
|
||||||
|
|
||||||
|
urls.append(
|
||||||
|
re_path(
|
||||||
|
f'^{plugin.slug}/',
|
||||||
|
include((plugin_urls, plugin.slug)),
|
||||||
|
name=plugin.slug,
|
||||||
|
)
|
||||||
|
)
|
||||||
|
except Exception:
|
||||||
|
log_error('get_plugin_urls', plugin=plugin.slug)
|
||||||
|
continue
|
||||||
|
|
||||||
|
# Redirect anything else to the root index
|
||||||
|
urls.append(
|
||||||
|
re_path(
|
||||||
|
r'^.*$',
|
||||||
|
RedirectView.as_view(url=f'/{settings.FRONTEND_URL_BASE}', permanent=False),
|
||||||
|
name='index',
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
return re_path(f'^{PLUGIN_BASE}/', include((urls, 'plugin')))
|
return re_path(f'^{PLUGIN_BASE}/', include((urls, 'plugin')))
|
||||||
|
Reference in New Issue
Block a user