mirror of
https://github.com/netbox-community/netbox.git
synced 2025-08-08 08:38:16 -06:00
14731 review changes
This commit is contained in:
parent
dd90cca89f
commit
83a0a553c4
@ -5,44 +5,11 @@ from django.utils.translation import gettext_lazy as _
|
|||||||
from netbox.tables import BaseTable
|
from netbox.tables import BaseTable
|
||||||
|
|
||||||
__all__ = (
|
__all__ = (
|
||||||
'CertifiedPluginTable',
|
'CatalogPluginTable',
|
||||||
'InstalledPluginTable',
|
|
||||||
'PluginVersionTable',
|
'PluginVersionTable',
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
class InstalledPluginTable(BaseTable):
|
|
||||||
name = tables.Column(
|
|
||||||
accessor=tables.A('verbose_name'),
|
|
||||||
verbose_name=_('Name')
|
|
||||||
)
|
|
||||||
version = tables.Column(
|
|
||||||
verbose_name=_('Version')
|
|
||||||
)
|
|
||||||
package = tables.Column(
|
|
||||||
accessor=tables.A('name'),
|
|
||||||
verbose_name=_('Package')
|
|
||||||
)
|
|
||||||
author = tables.Column(
|
|
||||||
verbose_name=_('Author')
|
|
||||||
)
|
|
||||||
author_email = tables.Column(
|
|
||||||
verbose_name=_('Author Email')
|
|
||||||
)
|
|
||||||
description = tables.Column(
|
|
||||||
verbose_name=_('Description')
|
|
||||||
)
|
|
||||||
|
|
||||||
class Meta(BaseTable.Meta):
|
|
||||||
empty_text = _('No plugins found')
|
|
||||||
fields = (
|
|
||||||
'name', 'version', 'package', 'author', 'author_email', 'description',
|
|
||||||
)
|
|
||||||
default_columns = (
|
|
||||||
'name', 'version', 'package', 'description',
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
class PluginVersionTable(BaseTable):
|
class PluginVersionTable(BaseTable):
|
||||||
version = tables.Column(
|
version = tables.Column(
|
||||||
verbose_name=_('Version')
|
verbose_name=_('Version')
|
||||||
@ -71,10 +38,10 @@ class PluginVersionTable(BaseTable):
|
|||||||
orderable = False
|
orderable = False
|
||||||
|
|
||||||
def render_last_updated(self, value, record):
|
def render_last_updated(self, value, record):
|
||||||
return naturalday(datetime.fromisoformat(value))
|
return naturalday(value)
|
||||||
|
|
||||||
|
|
||||||
class CertifiedPluginTable(BaseTable):
|
class CatalogPluginTable(BaseTable):
|
||||||
name = tables.Column(
|
name = tables.Column(
|
||||||
linkify=('core:plugin', [tables.A('slug')]),
|
linkify=('core:plugin', [tables.A('slug')]),
|
||||||
verbose_name=_('Name')
|
verbose_name=_('Name')
|
||||||
|
@ -1,9 +1,11 @@
|
|||||||
|
import datetime
|
||||||
import importlib
|
import importlib
|
||||||
import importlib.util
|
import importlib.util
|
||||||
import json
|
import json
|
||||||
import platform
|
import platform
|
||||||
import requests
|
import requests
|
||||||
|
|
||||||
|
from dataclasses import dataclass, field
|
||||||
from django import __version__ as DJANGO_VERSION
|
from django import __version__ as DJANGO_VERSION
|
||||||
from django.apps import apps
|
from django.apps import apps
|
||||||
from django.conf import settings
|
from django.conf import settings
|
||||||
@ -41,7 +43,7 @@ from utilities.query import count_related
|
|||||||
from utilities.views import ContentTypePermissionRequiredMixin, GetRelatedModelsMixin, register_model_view
|
from utilities.views import ContentTypePermissionRequiredMixin, GetRelatedModelsMixin, register_model_view
|
||||||
from . import filtersets, forms, tables
|
from . import filtersets, forms, tables
|
||||||
from .models import *
|
from .models import *
|
||||||
from .tables import CertifiedPluginTable, PluginVersionTable
|
from .tables import CatalogPluginTable, PluginVersionTable
|
||||||
|
|
||||||
|
|
||||||
#
|
#
|
||||||
@ -648,12 +650,8 @@ class SystemView(UserPassesTestMixin, View):
|
|||||||
response['Content-Disposition'] = 'attachment; filename="netbox.json"'
|
response['Content-Disposition'] = 'attachment; filename="netbox.json"'
|
||||||
return response
|
return response
|
||||||
|
|
||||||
plugins_table = tables.InstalledPluginTable(plugins, orderable=False)
|
|
||||||
plugins_table.configure(request)
|
|
||||||
|
|
||||||
return render(request, 'core/system.html', {
|
return render(request, 'core/system.html', {
|
||||||
'stats': stats,
|
'stats': stats,
|
||||||
'plugins_table': plugins_table,
|
|
||||||
'config': config,
|
'config': config,
|
||||||
})
|
})
|
||||||
|
|
||||||
@ -662,6 +660,36 @@ class SystemView(UserPassesTestMixin, View):
|
|||||||
# Plugins
|
# Plugins
|
||||||
#
|
#
|
||||||
|
|
||||||
|
@dataclass
|
||||||
|
class PluginVersion:
|
||||||
|
date: datetime.datetime = None
|
||||||
|
version: str = ''
|
||||||
|
netbox_min_version: str = ''
|
||||||
|
netbox_max_version: str = ''
|
||||||
|
has_model: bool = False
|
||||||
|
is_certified: bool = False
|
||||||
|
is_feature: bool = False
|
||||||
|
is_integration: bool = False
|
||||||
|
is_netboxlabs_supported: bool = False
|
||||||
|
|
||||||
|
|
||||||
|
@dataclass
|
||||||
|
class Plugin:
|
||||||
|
slug: str = ''
|
||||||
|
config_name: str = ''
|
||||||
|
name: str = ''
|
||||||
|
tag_line: str = ''
|
||||||
|
description_short: str = ''
|
||||||
|
author: str = ''
|
||||||
|
created: datetime.datetime = None
|
||||||
|
updated: datetime.datetime = None
|
||||||
|
is_local: bool = False
|
||||||
|
is_installed: bool = False
|
||||||
|
is_certified: bool = False
|
||||||
|
is_community: bool = False
|
||||||
|
versions: list[PluginVersion] = field(default_factory=list)
|
||||||
|
|
||||||
|
|
||||||
def get_local_plugins(plugins):
|
def get_local_plugins(plugins):
|
||||||
for plugin_name in settings.PLUGINS:
|
for plugin_name in settings.PLUGINS:
|
||||||
plugin = importlib.import_module(plugin_name)
|
plugin = importlib.import_module(plugin_name)
|
||||||
@ -692,7 +720,8 @@ def get_catalog_plugins(plugins):
|
|||||||
session = requests.Session()
|
session = requests.Session()
|
||||||
|
|
||||||
def get_pages():
|
def get_pages():
|
||||||
payload = {'page': '1', 'per_page': '25'}
|
# TODO: pagintation is curently broken in API
|
||||||
|
payload = {'page': '1', 'per_page': '50'}
|
||||||
first_page = session.get(url, params=payload).json()
|
first_page = session.get(url, params=payload).json()
|
||||||
yield first_page
|
yield first_page
|
||||||
num_pages = first_page['metadata']['pagination']['last_page']
|
num_pages = first_page['metadata']['pagination']['last_page']
|
||||||
@ -706,7 +735,6 @@ def get_catalog_plugins(plugins):
|
|||||||
for data in page['data']:
|
for data in page['data']:
|
||||||
|
|
||||||
versions = []
|
versions = []
|
||||||
versions.append(data['release_latest'])
|
|
||||||
versions.extend(data['release_recent_history'])
|
versions.extend(data['release_recent_history'])
|
||||||
if data['slug'] in plugins:
|
if data['slug'] in plugins:
|
||||||
plugins[data['slug']]['is_local'] = False
|
plugins[data['slug']]['is_local'] = False
|
||||||
@ -748,7 +776,7 @@ def get_plugins():
|
|||||||
class PluginListView(UserPassesTestMixin, View):
|
class PluginListView(UserPassesTestMixin, View):
|
||||||
|
|
||||||
def test_func(self):
|
def test_func(self):
|
||||||
return self.request.user.is_staff
|
return self.request.user.is_superuser
|
||||||
|
|
||||||
def get(self, request):
|
def get(self, request):
|
||||||
q = request.GET.get('q', None)
|
q = request.GET.get('q', None)
|
||||||
@ -757,9 +785,9 @@ class PluginListView(UserPassesTestMixin, View):
|
|||||||
if q:
|
if q:
|
||||||
plugins = [v for k, v in plugins.items() if q.casefold() in v['name'].casefold()]
|
plugins = [v for k, v in plugins.items() if q.casefold() in v['name'].casefold()]
|
||||||
else:
|
else:
|
||||||
plugins = [v for k, v in plugins.items()]
|
plugins = plugins.values()
|
||||||
|
|
||||||
table = CertifiedPluginTable(plugins, user=request.user)
|
table = CatalogPluginTable(plugins, user=request.user)
|
||||||
table.configure(request)
|
table.configure(request)
|
||||||
|
|
||||||
# If this is an HTMX request, return only the rendered table HTML
|
# If this is an HTMX request, return only the rendered table HTML
|
||||||
|
@ -431,13 +431,13 @@ ADMIN_MENU = Menu(
|
|||||||
label=_('System'),
|
label=_('System'),
|
||||||
items=(
|
items=(
|
||||||
MenuItem(
|
MenuItem(
|
||||||
link='core:plugin_list',
|
link='core:system',
|
||||||
link_text=_('Plugins'),
|
link_text=_('System'),
|
||||||
auth_required=True
|
auth_required=True
|
||||||
),
|
),
|
||||||
MenuItem(
|
MenuItem(
|
||||||
link='core:system',
|
link='core:plugin_list',
|
||||||
link_text=_('System'),
|
link_text=_('Plugins'),
|
||||||
auth_required=True
|
auth_required=True
|
||||||
),
|
),
|
||||||
MenuItem(
|
MenuItem(
|
||||||
|
@ -50,7 +50,6 @@ From
|
|||||||
|
|
||||||
{% block content %}
|
{% block content %}
|
||||||
|
|
||||||
{# Component creation form #}
|
|
||||||
<div class="tab-pane show active" id="overview" role="tabpanel" aria-labelledby="overview-tab">
|
<div class="tab-pane show active" id="overview" role="tabpanel" aria-labelledby="overview-tab">
|
||||||
{{ plugin.description_short }}
|
{{ plugin.description_short }}
|
||||||
</div>
|
</div>
|
||||||
|
@ -78,16 +78,6 @@
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{# Plugins #}
|
|
||||||
<div class="row mb-3">
|
|
||||||
<div class="col col-md-12">
|
|
||||||
<div class="card">
|
|
||||||
<h5 class="card-header">{% trans "Plugins" %}</h5>
|
|
||||||
{% render_table plugins_table %}
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
{# Configuration #}
|
{# Configuration #}
|
||||||
<div class="row mb-3">
|
<div class="row mb-3">
|
||||||
<div class="col col-md-12">
|
<div class="col col-md-12">
|
||||||
|
Loading…
Reference in New Issue
Block a user