Worum es geht
Ein endgültiges Dokument liegt bei CRMS. Deine Anwendung kann es jederzeit wieder lesen, die Fassungen einer Kette auflisten und prüfen lassen, ob Kette und Bytes noch stimmen. Dafür gibt es eine kleine Gruppe von Endpunkten unter /crms/documents.
Die Endpunkte
| Aufruf | Rolle (Standard) | Antwort |
|---|---|---|
GET /crms/documents?template=…&scope=…&reference=… | crms-document-reader | alle Revisionen der Kette, älteste zuerst |
GET /crms/documents/{revision} | crms-document-reader | die Bytes, die Beschreibung in Headern |
POST /crms/documents/{revision}/verify | crms-document-reader | { "ok": …, "problem": … } |
POST /crms/documents/{revision}/legal-hold | crms-document-custodian | 204, siehe Aufbewahrung |
POST /crms/documents/{revision}/legal-hold/release | crms-document-custodian | 204 |
POST /crms/documents/{revision}/erase | crms-document-eraser | 204 |
{revision}ist eine UUID in kanonischer Form. Eine andere Schreibweise ist ein Verstoß am Feldrevision.- Die Rollen stellst du mit
CODAMAI_CRMS_REST_DOCUMENT_ROLES_READ,_HOLDund_ERASEein, jeweils als kommagetrennte Liste. Eine Rolle der Liste genügt, eine leere Liste lässt niemanden zu. - Die Rolle wird geprüft, bevor CRMS das Dokument sucht. Fehlt sie: 403
document-access-denied. - Du siehst nur Dokumente deines eigenen Mandanten. Eine Revision eines anderen Mandanten gibt es für dich nicht: 404
document-not-found.
Läuft CRMS als eigener Dienst, bietet crms-client dieselben Aufrufe über dieselbe Schnittstelle an und reicht das Token des Benutzers weiter. Siehe Der CRMS-Client.
Ein Dokument lesen
GET /crms/documents/7c1e…200 OK
Content-Type: application/pdf
Content-Disposition: inline; filename="audit-report.pdf"
X-Content-Type-Options: nosniff
Crms-Document-Revision: 7c1e…
Crms-Document-Number: 2
Crms-Document-Format: PDF
Crms-Document-Stored-At: 2026-10-17T09:12:44.123456Z
Crms-Document-Retain-Until: 2036-10-17T09:12:44.123456Z
Crms-Document-Legal-Hold: false
Crms-Document-Content-Hash: sha-256:3b1d…
Crms-Template-Key: audit-report
Crms-Template-Scope: TENANT
Crms-Template-Variant: de
Crms-Template-Revision: a2f0…
Crms-Template-Revision-Hash: sha-256:9f86…
(die Bytes)Beim Lesen entschlüsselt CRMS die Bytes und vergleicht sie mit dem Inhalts-Hash der Revision. Stimmen sie nicht, gibt es kein Dokument, sondern 500 document-integrity-failed. Ein HTML-Dokument bekommt zusätzlich Content-Security-Policy: sandbox, damit ein Skript darin nicht im Namen deiner Anwendung läuft.
| Fall | Antwort |
|---|---|
| Revision gibt es nicht (für diesen Mandanten) | 404 document-not-found |
| Revision ist gelöscht | 410 document-erased |
| Bytes passen nicht zum Hash | 500 document-integrity-failed |
| Objekt fehlt im Speicher | 500 document-object-missing |
Lesen protokollieren
Mit CODAMAI_CRMS_AUDIT_READS=true schreibt CRMS jedes Lesen eines endgültigen Dokuments als document-read mit dem Leser ins Journal. Standard ist false. Die Prüfung über verify zählt nicht als Lesen.
Ein Dokument prüfen
-
CRMSKetteErgibt jeder Eintrag der ganzen Dokumentkette seinen gespeicherten Hash?↳ nein
ok: false,document-chain-broken -
CRMSGelöscht?Hat die Revision noch Bytes?↳ nein
ok: true– ein Grabstein ist intakt, wenn die Kette es ist -
CRMSEntschlüsselnLassen sich die Bytes mit ihrem Schlüssel entschlüsseln?↳ nein
ok: false,document-decryption-failed -
CRMSInhaltPassen die Bytes zum Inhalts-Hash?↳ nein
ok: false,document-integrity-failed ok: true
POST /crms/documents/7c1e…/verify{ "ok": false, "problem": "document-chain-broken" }Ist alles in Ordnung, fehlt problem: { "ok": true }. Ein Befund ist eine normale Antwort mit 200, kein Fehler. Die Schlüssel stehen unter Fehler.
Fehlt das Objekt im Speicher, meldet die Prüfung document-object-missing.
Vorlagen prüfen
Auch die Kette einer Vorlagenvariante lässt sich prüfen: POST /crms/variants/{variant}/verify. Die Antwort ist { "intact": true } oder { "intact": false, "brokenAt": 4 } mit der ersten Stelle, die nicht stimmt. Mehr unter Lebenszyklus einer Vorlage.
Was die Kette nicht beweist
| Frage | Belegt der Nachweis das? |
|---|---|
| Sind die Bytes seit dem Speichern unverändert? | ja, über Inhalts-Hash und Kette |
| Mit welcher freigegebenen Vorlagen-Revision wurde gerendert? | ja, über den Revisions-Hash der Vorlage |
| Mit welchen Daten wurde gerendert? | ja, wer die Daten hat, vergleicht sie mit dem Payload-Hash |
| Wer hat wann gespeichert, festgehalten, gelöscht? | ja, über Benutzer und Zeit in Kette und Journal |
| Wurde die Geschichte nachträglich stimmig neu berechnet? | ja, das deckt der Anker auf |
| Waren die Daten richtig? | nein, das verantwortet die Anwendung, die sie geschickt hat |