fix: show rack elevation errors in the exported document

Rack SVG failures were only logged, leaving racks silently without an
image. The error is now written into the document next to the rack so
the cause (e.g. missing rack_elevation.css in STATIC_ROOT) is visible.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
2026-09-23 13:07:45 +02:00
co-authored by Claude Opus 5.5
parent 0719f42cb3
commit 1b9970b5dd
2 changed files with 11 additions and 7 deletions
+4 -4
View File
@@ -8,7 +8,7 @@ logger = logging.getLogger("netbox_customer_export")
def render_rack_svg(rack, face, user):
"""Gibt das SVG als String zurück oder None bei Fehlern.
"""Gibt (svg, fehler) zurück – genau einer der beiden Werte ist None.
Ist ``rack_svg_renderer`` gesetzt (z.B. der Offline-Renderer aus Netbox-Utilities, der mehrere
Geräte pro HE korrekt darstellt), wird dieser aufgerufen: ``fn(rack=..., face=..., user=...)``.
@@ -22,7 +22,7 @@ def render_rack_svg(rack, face, user):
from dcim.svg import RackElevationSVG
svg = RackElevationSVG(rack, user=user, include_images=False, base_url="").render(face)
return svg.tostring() if hasattr(svg, "tostring") else str(svg)
except Exception: # noqa: BLE001 – ein defektes Rack soll nicht den ganzen Export abbrechen
return (svg.tostring() if hasattr(svg, "tostring") else str(svg)), None
except Exception as e: # noqa: BLE001 – ein defektes Rack soll nicht den ganzen Export abbrechen
logger.exception("Rack-SVG für %s (%s) fehlgeschlagen", rack, face)
return None
return None, f"{type(e).__name__}: {e}"
+7 -3
View File
@@ -172,13 +172,17 @@ def racks(scope, opts):
)
)
if opts.get("rack_svg"):
images = []
images, errors = [], []
for face in opts.get("rack_faces") or ["front"]:
svg = render_rack_svg(rack, face, scope.user)
caption = "Vorderseite" if face == "front" else "Rückseite"
svg, error = render_rack_svg(rack, face, scope.user)
if svg:
images.append((svg, "Vorderseite" if face == "front" else "Rückseite"))
images.append((svg, caption))
else:
errors.append(f"Rack-Ansicht ({caption}) konnte nicht erzeugt werden: {error}")
if images:
blocks.append(IMAGES(images))
blocks += [P(e) for e in errors]
if opts.get("rack_devices"):
devs = scope.restrict(rack.devices.all()).select_related("device_type__manufacturer").order_by("-position", "name")
if devs.exists():