Skip to content

Commit cf52adb

Browse files
committed
Handle missing database during startup and bump to 2.0.1b1
Wrap DB queries in register_typed_tabs() with try/except for OperationalError/ProgrammingError so Docker builds (collectstatic) don't crash when no database is available.
1 parent 7fc8a07 commit cf52adb

File tree

2 files changed

+35
-27
lines changed

2 files changed

+35
-27
lines changed

netbox_custom_objects_tab/views/typed.py

Lines changed: 34 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
from django.contrib.contenttypes.models import ContentType
44
from django.db.models import Q
5+
from django.db.utils import OperationalError, ProgrammingError
56
from django.shortcuts import get_object_or_404, render
67
from django.views.generic import View
78
from extras.choices import CustomFieldTypeChoices, CustomFieldUIVisibleChoices
@@ -247,32 +248,39 @@ def register_typed_tabs(model_classes, weight):
247248
Pre-fetches all relevant CustomObjectTypeFields and groups them.
248249
"""
249250

250-
# Collect all relevant fields
251-
all_fields = CustomObjectTypeField.objects.filter(
252-
type__in=[
253-
CustomFieldTypeChoices.TYPE_OBJECT,
254-
CustomFieldTypeChoices.TYPE_MULTIOBJECT,
255-
],
256-
).select_related("custom_object_type")
257-
258-
# Group by (content_type_id, custom_object_type_pk)
259-
# -> list of (field_name, field_type)
260-
from collections import defaultdict
261-
262-
ct_cot_fields = defaultdict(list)
263-
ct_cot_map = {} # (ct_id, cot_pk) -> CustomObjectType
264-
for field in all_fields:
265-
if field.related_object_type_id is None:
266-
continue
267-
key = (field.related_object_type_id, field.custom_object_type_id)
268-
ct_cot_fields[key].append((field.name, field.type))
269-
ct_cot_map[key] = field.custom_object_type
270-
271-
# Build a set of content_type_ids we care about
272-
model_ct_map = {} # content_type_id -> model_class
273-
for model_class in model_classes:
274-
ct = ContentType.objects.get_for_model(model_class)
275-
model_ct_map[ct.pk] = model_class
251+
try:
252+
# Collect all relevant fields
253+
all_fields = CustomObjectTypeField.objects.filter(
254+
type__in=[
255+
CustomFieldTypeChoices.TYPE_OBJECT,
256+
CustomFieldTypeChoices.TYPE_MULTIOBJECT,
257+
],
258+
).select_related("custom_object_type")
259+
260+
# Group by (content_type_id, custom_object_type_pk)
261+
# -> list of (field_name, field_type)
262+
from collections import defaultdict
263+
264+
ct_cot_fields = defaultdict(list)
265+
ct_cot_map = {} # (ct_id, cot_pk) -> CustomObjectType
266+
for field in all_fields:
267+
if field.related_object_type_id is None:
268+
continue
269+
key = (field.related_object_type_id, field.custom_object_type_id)
270+
ct_cot_fields[key].append((field.name, field.type))
271+
ct_cot_map[key] = field.custom_object_type
272+
273+
# Build a set of content_type_ids we care about
274+
model_ct_map = {} # content_type_id -> model_class
275+
for model_class in model_classes:
276+
ct = ContentType.objects.get_for_model(model_class)
277+
model_ct_map[ct.pk] = model_class
278+
except (OperationalError, ProgrammingError):
279+
logger.warning(
280+
"netbox_custom_objects_tab: database unavailable — typed tabs not registered. "
281+
"Restart NetBox once the database is ready."
282+
)
283+
return
276284

277285
for (ct_id, cot_pk), field_infos in ct_cot_fields.items():
278286
if ct_id not in model_ct_map:

pyproject.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
44

55
[project]
66
name = "netbox-custom-objects-tab"
7-
version = "2.0.0b1"
7+
version = "2.0.1b1"
88
description = "NetBox plugin that adds a Custom Objects tab to object detail pages"
99
readme = "README.md"
1010
requires-python = ">=3.12"

0 commit comments

Comments
 (0)