Skip to content

harden: Öffentliche Endpoints — Delta-Cache-Schlüssel normalisieren, Turtle cachen (v2.34.2) - #85

Merged
daimpad merged 1 commit into
mainfrom
claude/fix-data-prep-errors-kJYpl
Jul 31, 2026
Merged

harden: Öffentliche Endpoints — Delta-Cache-Schlüssel normalisieren, Turtle cachen (v2.34.2)#85
daimpad merged 1 commit into
mainfrom
claude/fix-data-prep-errors-kJYpl

Conversation

@daimpad

@daimpad daimpad commented Jul 31, 2026

Copy link
Copy Markdown
Owner

Schließt die beiden nachrangigen „Residuals" aus dem Sicherheits-Review zu v2.33.1.

Einordnung — kein Notfall: Das Review (6 Prüfdimensionen, jeder Befund adversarial verifiziert) fand keine ausnutzbare Lücke. Die folgenden Punkte waren dort ausdrücklich als low severity / hardening eingestuft. Für bestehende Installationen besteht kein Handlungsdruck.

1 · /delta-Cache-Schlüssel normalisiert

Der Schlüssel entstand aus der rohen since-Eingabe, obwohl der geparste, kanonische Wert direkt darüber bereits vorlag. Dadurch legte jede Schreibweise desselben Zeitpunkts einen eigenen Transient an:

2024-01-01            ┐
2024-01-01T00:00:00Z  ├─ derselbe Zeitpunkt, bisher 4 Cache-Einträge
2024-01-01T00:00:00+00:00 │
2024-01-01T02:00:00+02:00 ┘

Da der Endpoint unauthentifiziert ist, ließ sich der Schlüsselraum so unnötig aufblähen. Jetzt bildet der kanonische UTC-Zeitstempel den Schlüssel — der Raum ist auf tatsächlich verschiedene Zeitpunkte begrenzt.

2 · Turtle-Serialisierung wird gecacht

Der Katalog-Transient sparte bislang nur die Datenbankarbeit. Die Serialisierung des gesamten Katalogs nach Turtle lief dagegen bei jedem Aufruf neu — auch bei Cache-Treffer. Auf einem unauthentifizierten Endpoint ist das unnötige CPU-Last pro Anfrage.

Das serialisierte Dokument liegt jetzt in einem eigenen Transient mit _ttl-Suffix. Weil der Schlüssel weiterhin mit odw_catalog_ beginnt, wird er von der bestehenden Cache-Invalidierung (delete_catalog_transients, Muster odw_catalog_%) automatisch miterfasst — es gibt also keinen zweiten Invalidierungspfad, der veralten könnte.

Bewusst nicht umgesetzt

Rate-Limiting — das gehört auf Host-/WAF-Ebene, nicht in ein WordPress-Plugin. (Die dritte Residual-Idee aus dem Review.)

Tests / Qualität

  • Zwei Regressionstests, beide gegengeprüft — ohne die jeweilige Härtung schlagen sie fehl:
    • fünf Schreibweisen eines Zeitpunkts ergeben genau einen Cache-Schlüssel
    • das gecachte Turtle-Dokument wird tatsächlich verwendet statt neu serialisiert
  • WP_REST_Response-Stub um get_data(), get_headers() und get_status() ergänzt, damit Tests dieselben Zugriffsmethoden nutzen wie der Produktivcode (serve_raw_rdf()).
  • 190 Tests grün, PHPCS 0, PHPStan Level 6 clean.
  • Turtle-Ausgabe byte-identisch zur Vorversion und weiterhin GovData DCAT-AP.de Conforms: True — die Härtung ändert nichts am ausgelieferten Dokument.

🤖 Generated with Claude Code

https://claude.ai/code/session_01JB1xUQM892bVZ4Yv3MZjvq


Generated by Claude Code

Schließt die beiden nachrangigen 'Residuals' aus dem Sicherheits-Review zu
v2.33.1. Das Review fand KEINE ausnutzbare Lücke — dies ist Defense-in-Depth.

- /delta-Cache-Schlüssel aus dem kanonischen UTC-Zeitstempel statt aus der
  rohen Eingabe. Bisher erzeugte jede Schreibweise desselben Zeitpunkts einen
  eigenen Transient; der Endpoint ist unauthentifiziert.
- Turtle-Antworten werden gecacht. Der Katalog-Transient sparte nur die
  DB-Arbeit, die Serialisierung des gesamten Katalogs lief bei jedem Aufruf
  neu. Eigener Transient mit '_ttl'-Suffix, den die bestehende Invalidierung
  (delete_catalog_transients, Muster odw_catalog_%) miterfasst.

Rate-Limiting bewusst nicht umgesetzt (Host-/WAF-Ebene).

Tests: 2 Regressionstests, beide gegengeprüft (ohne Härtung rot).
WP_REST_Response-Stub um get_data/get_headers/get_status ergänzt, damit Tests
dieselben Accessoren nutzen wie serve_raw_rdf(). 190 grün, PHPCS 0,
PHPStan clean. Turtle-Ausgabe byte-identisch und weiterhin DCAT-AP.de-konform.

https://claude.ai/code/session_01JB1xUQM892bVZ4Yv3MZjvq

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01JB1xUQM892bVZ4Yv3MZjvq
@daimpad
daimpad merged commit d52e199 into main Jul 31, 2026
8 of 10 checks passed
@daimpad
daimpad deleted the claude/fix-data-prep-errors-kJYpl branch July 31, 2026 14:52
daimpad added a commit that referenced this pull request Jul 31, 2026
PR #85 wurde gemergt, während ich diese beiden Lint-Verstöße noch behoben
habe — dadurch ist WPCS auf main rot. Rein redaktionell, keine
Verhaltensänderung; das veröffentlichte v2.34.2-ZIP ist funktional korrekt.

- class-rest-api.php: Ausrichtung eines Zuweisungsoperators (phpcbf).
- test-rest-delta.php: serialize() im neuen Test annotiert. Die Ausnahme in
  config/phpcs.xml gilt nur für includes/class-rest-api.php; der Test spiegelt
  die Schlüsselbildung bewusst nach, daher ein lokaler phpcs:ignore.

Ursache der wiederholten Fehlschläge: Mein lokales vendor/ lag noch auf
WPCS 3.3.0. Da vendor/ seit v2.34.0 gitignoriert ist, konnte ich es jetzt
folgenlos auf den Lock-Stand (3.4.1) heben — ab sofort prüfe ich lokal mit
derselben Version wie die CI. Damit lokal verifiziert: PHPCS 0.

190 Tests grün, PHPStan clean.

https://claude.ai/code/session_01JB1xUQM892bVZ4Yv3MZjvq


Claude-Session: https://claude.ai/code/session_01JB1xUQM892bVZ4Yv3MZjvq

Co-authored-by: Claude <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants