Polycrate API 0.15.2¶
Release-Datum: 19. April 2026
Typ: Fix
Highlights¶
- Stabilerer Icon-Resolver –
GET /api/v1/backups/backup-schedules/<id>/und andere ManagedObject-Retrieves fallen nicht mehr mit HTTP 500 aus, wenn für eine Klasse kein Icon-SVG hinterlegt ist. Der Resolver fällt auf ein Default-Icon zurück und loggt die Lücke. - Saubere 409-Semantik auf Create – Unique-Constraint-Verstöße (
K8sClusterund andereManagedObject-Endpoints) liefern HTTP 409 Conflict mit strukturiertem Error-Body statt HTTP 500. Voraussetzung für robustes Re-Adoption im Operator. - Loopback-Integration sichtbar und debugbar – Organization-Detail zeigt eine read-only Card mit
loopback_org_id,loopback_project_idund Match-Status (auto-resolved/manually set/unresolved). Auto-Match-Fehler propagieren alsConditionam SystemOwner. - Humanized Bandwidth-Werte –
LoadbalancerInstanceBandwidth-Tab und Organization LB-Bandwidth-Chart rendern Werte mitB/s,KB/s,MB/s,GB/sin Tooltips und Achsen-Ticks. Der Org-Chart hatte zusätzlich eine falsche Unit (bytesstattbytes/s), das ist korrigiert. - CatalogueApp Admin/Form entrümpelt – Das Legacy-Feld
template_blockist aus Form und Admin raus,registry_urlist das einzige User-sichtbare Quellfeld.
Artefakte¶
Docker Image¶
Block¶
Hintergrund¶
Nach dem 0.15.0-Release (Bundled Feature Release mit User/Contact-Migration, Keycloak-Integration, Artifacts→Blocks, externe DNS via Lexicon, RBAC und Managed Object Dashboard) sind während des Operator-Rollouts auf 0.15.1 mehrere eng umrissene Regressionen und UX-Schwachstellen sichtbar geworden. 0.15.2 sammelt die Fixes in einem Hotfix-Release ohne Breaking-Changes und ohne Schema-Migration.
Fixes¶
Fix 1: Icon-Resolver robust machen¶
Problem: GET /api/v1/backups/backup-schedules/<id>/ schlug mit HTTP 500 fehl, weil kein backupschedule.svg unter polycrate_api/img/object_icons/ existierte und der Resolver die ValueError aus static() nicht abfing.
Lösung:
- Neues Icon
src/static/polycrate_api/img/object_icons/backupschedule.svghinzugefügt. resolve_managed_object_icon_urlinsrc/polycrate_api/serializers/common.pyfängt jetzt fehlende Assets ab (staticfiles_storage.exists/ValueError) und fällt auf ein Default-Icon zurück. Die fehlende Datei wird geloggt, damit Lücken in der Icon-Abdeckung erkennbar bleiben.- Audit aller
ManagedObject-Subklassen auf verfügbare Icons; vorhandene Lücken in der selben Änderung geschlossen.
Fix 2: 409 Conflict bei Unique-Constraint statt 500¶
Problem: POST /api/v1/kubernetes/clusters/ (und analog andere ManagedObject-Create-Endpoints) lieferte bei Unique-Constraint-Verstößen HTTP 500, weil IntegrityError ungefangen bis zum DRF-Handler durchschlug. Für den Operator-Reconciler sah jeder "existiert bereits"-Fall damit aus wie ein echter Server-Fehler und wurde mit exponentiellem Backoff reprobiert statt per Lookup adoptiert.
Lösung:
ManagedObjectBaseViewset.create()fängtIntegrityErrorund mappt Unique-Constraint-Verstöße auf HTTP 409 mit strukturiertem Body:
- Gilt automatisch für alle ManagedObject-Subklassen, nicht nur
K8sCluster. Kein Per-Viewset-Patch nötig. - Der operator-seitige Lookup-Retry über alle Reconciler hinweg ist in
polycrate-cliSpec 154 beschrieben und folgt in einem separaten CLI-Release. Er ist für den Rollout von 0.15.2 nicht blockierend — das API-Verhalten ist für sich genommen korrekt und rückwärtskompatibel.
Fix 3: CatalogueAppForm/Admin von template_block bereinigen¶
Problem: Nach der Migration von template_block zu registry_url (0.15.0 Artifacts→Blocks Refactoring) referenzierten CatalogueAppForm.Meta.fields und CatalogueAppAdmin noch das alte Feld. Das führte zu Django-SystemCheck-Warnings (fields.E*) und in bestimmten Admin-Pfaden zu Rendering-Fehlern.
Lösung:
template_blockentfernt aussrc/artifacts/forms.py::CatalogueAppForm.Meta.fieldsund aussrc/artifacts/admin.py::CatalogueAppAdmin(list_display,list_filter,search_fields,raw_id_fields,fieldsets,readonly_fields).registry_urlin Form und Admin sichtbar gemacht (list_display,search_fields).- Repo-weiter Audit via
rg -n "template_block" src/— verbleibende Treffer nur noch in historischen Migrations (0047_catalogueapp_registry_url,0048_*). - Client-Artefakte (
schemas.gen.js,services.gen.js) viapolycrate run openapi generateneu gebaut.
Fix 4: Loopback-Integration — Sichtbarkeit und Condition-Pfad¶
Problem: Die Loopback-Auto-Resolve-Logik aus 0.15.0 lief zwar produktiv, war aber in der UI unsichtbar und bei Auto-Match-Failure schwer zu debuggen. Docstring und Release-Doku beschrieben zusätzlich ein veraltetes Matching-Verhalten ("match by slug ayedo"), was nicht mehr dem Code entsprach.
Lösung (Default bleibt Auto-Resolve, keine manuelle Pflege nötig):
- Dashboard-Card auf Organization-Detail (nur wenn
LOOPBACK_INTEGRATION_ENABLED=true): - Zeigt
loopback_org_id(auf dem SystemOwner relevant) undloopback_project_idread-only mit Copy-Button. - Match-Status-Badge:
auto-resolved,manually set,unresolved (auto-match failed),not set. - Keine Write-Komponente in der UI — Editieren nur über Django-Admin.
- Condition-Propagation in
Organization._reconcile_loopback_clusters: - Fehlender Org-Match auf SystemOwner →
Conditionmittype=LoopbackOrgResolved,status=False,reason=NoNameMatch, Message inkl. erwartetemlegal_name. - Fehlender Project-Match nur dann als Condition, wenn für die Org ein Match erwartet wird. Orgs ohne Loopback-Präsenz erzeugen kein Dauer-Warning.
- Bei erfolgreichem Resolve:
Condition.status=Truebzw. Condition wird entfernt. - Client-Robustheit:
LoopbackClientklassifiziert 401/403 als eigene Exception mit Hinweis aufLOOPBACK_API_KEY, damit Condition-Messages aussagekräftig bleiben. - Docstring/Doku aktualisiert: Matching-Regeln explizit (
Loopback.org.name == SystemOwner.legal_name,Loopback.project.name == Polycrate.org.slug). Der zugehörige Abschnitt in den 0.15.0-Release-Notes wurde ergänzt.
Fix 5: LoadbalancerInstance-Bandwidth humanizen¶
Problem: Der Bandwidth-Tab auf LoadbalancerInstance zeigte rohe Bytes-pro-Sekunde-Werte in Tooltips und Ticks (1180000 statt 1.18 MB/s).
Lösung: Frontend-Only-Fix in src/static/polycrate_api/js/metric-chart.js. Ein neuer formatBytesPerSecond-Helper skaliert pro Wert automatisch auf B/s, KB/s, MB/s oder GB/s. Negative Werte bekommen ein --Präfix, 0 bleibt 0 B/s. Keine Änderung an Prometheus-Queries oder Metric-Semantik.
Fix 6: Organization LB Bandwidth Chart — Unit korrigieren¶
Problem: Das lb_bandwidth-Chart auf der Organization-Detail-Seite deklarierte im API-Response "unit": "bytes" statt "bytes/s". Die gelieferten Werte waren korrekt (polycrate_io_api_loadbalancer_traffic_bytes_per_second), aber das Frontend formatierte sie als kumulativen Byte-Wert ohne /s-Suffix.
Lösung: Backend-Only-Fix in src/organizations/models.py: chart_spec.unit für lb_bandwidth auf bytes/s korrigiert. Damit rendert der Org-Chart konsistent mit dem Instance-Chart (Fix 5). Keine Änderung an _metric_lb_bandwidth oder an der Prometheus-Query.
Kompatibilität¶
- Kein Breaking-Change, keine Schema-Migration.
- 409-Semantik auf Create-Endpoints ist eine Korrektur des dokumentierten Verhaltens; Clients, die bisher 500 als Duplikat-Signal interpretiert haben, müssen nachziehen (der Operator-Fix dafür ist in
polycrate-cliSpec 154 getrackt und nicht blockierend für diesen Release). - Alle Icon-/Chart-/Loopback-Änderungen sind additiv und rückwärtskompatibel.
Nach dem Deployment¶
- Optional:
Condition-Liste auf der SystemOwner-Organization prüfen. Steht dortLoopbackOrgResolved=Falsemitreason=NoNameMatch, stimmt entwederlegal_namenicht mit der Loopback-Org überein, oderLOOPBACK_INTEGRATION_ENABLEDist fälschlich aktiv. Fix via Django-Admin (loopback_org_idsetzen) oder via Env-Var. - Prüfen, dass der Bandwidth-Tab der Organization-Detail-Seite Werte jetzt mit
/s-Suffix rendert und dassLoadbalancerInstance-Bandwidth-Tooltips humanisiert sind.