#19973: Improve & extend nbhshell banner text

This commit is contained in:
Jeremy Stretch 2025-07-31 17:09:18 -04:00
parent 9a2fab1d48
commit 19f89acc3a
3 changed files with 49 additions and 21 deletions

View File

@ -1,3 +1,7 @@
# Shell text coloring
# https://github.com/tartley/colorama/blob/master/CHANGELOG.rst
colorama
# The Python web framework on which NetBox is built # The Python web framework on which NetBox is built
# https://docs.djangoproject.com/en/stable/releases/ # https://docs.djangoproject.com/en/stable/releases/
Django==5.2.* Django==5.2.*

View File

@ -2,28 +2,24 @@ import code
import platform import platform
import sys import sys
from colorama import Fore, Style
from django import get_version from django import get_version
from django.apps import apps from django.apps import apps
from django.conf import settings from django.conf import settings
from django.core.management.base import BaseCommand from django.core.management.base import BaseCommand
from core.models import ObjectType from netbox.constants import CORE_APPS
from users.models import User from netbox.plugins.utils import get_installed_plugins
APPS = ('circuits', 'core', 'dcim', 'extras', 'ipam', 'tenancy', 'users', 'virtualization', 'vpn', 'wireless') EXCLUDE_MODELS = ()
EXCLUDE_MODELS = (
'extras.branch',
'extras.stagedchange',
)
BANNER_TEXT = """### NetBox interactive shell ({node})
### Python {python} | Django {django} | NetBox {netbox} def color(color: str, text: str):
### lsmodels() will show available models. Use help(<model>) for more info.""".format( return getattr(Fore, color.upper()) + text + Style.RESET_ALL
node=platform.node(),
python=platform.python_version(),
django=get_version(), def bright(text: str):
netbox=settings.RELEASE.name return Style.BRIGHT + text + Style.RESET_ALL
)
class Command(BaseCommand): class Command(BaseCommand):
@ -47,7 +43,7 @@ class Command(BaseCommand):
namespace = {} namespace = {}
# Gather Django models and constants from each app # Gather Django models and constants from each app
for app in APPS: for app in CORE_APPS:
models = [] models = []
# Load models from each app # Load models from each app
@ -67,10 +63,6 @@ class Command(BaseCommand):
except KeyError: except KeyError:
pass pass
# Additional objects to include
namespace['ObjectType'] = ObjectType
namespace['User'] = User
# Load convenience commands # Load convenience commands
namespace.update({ namespace.update({
'lsmodels': self._lsmodels, 'lsmodels': self._lsmodels,
@ -78,6 +70,37 @@ class Command(BaseCommand):
return namespace return namespace
def get_banner_text(self):
lines = [
'{title} ({hostname})'.format(
title=bright('NetBox interactive shell'),
hostname=platform.node(),
),
'{python} | {django} | {netbox}'.format(
python=color('green', f'Python v{platform.python_version()}'),
django=color('green', f'Django v{get_version()}'),
netbox=color('green', settings.RELEASE.name),
),
]
if installed_plugins := get_installed_plugins():
plugin_list = ', '.join([
color('cyan', f'{name} v{version}') for name, version in installed_plugins.items()
])
lines.append(
'Plugins: {plugin_list}'.format(
plugin_list=plugin_list
)
)
lines.append(
'lsmodels() will show available models. Use help(<model>) for more info.'
)
return '\n'.join([
f'### {line}' for line in lines
])
def handle(self, **options): def handle(self, **options):
namespace = self.get_namespace() namespace = self.get_namespace()
@ -97,5 +120,5 @@ class Command(BaseCommand):
readline.parse_and_bind('tab: complete') readline.parse_and_bind('tab: complete')
# Run interactive shell # Run interactive shell
shell = code.interact(banner=BANNER_TEXT, local=namespace) shell = code.interact(banner=self.get_banner_text(), local=namespace)
return shell return shell

View File

@ -1,3 +1,4 @@
colorama==0.4.6
Django==5.2.4 Django==5.2.4
django-cors-headers==4.7.0 django-cors-headers==4.7.0
django-debug-toolbar==5.2.0 django-debug-toolbar==5.2.0