Jeder EU-Mitgliedstaat muss bis zum 24. Dezember 2026 eine EU Digital Identity (EUDI) Wallet anbieten, und regulierte Unternehmen müssen sie bis zum 24. Dezember 2027 akzeptieren. Didit unterstützt heute fünf nationale elektronische IDs (eIDs), und die Akzeptanz der EUDI-Wallet kommt bald in denselben Workflow.
Eine Wallet pro Person. Nur die Daten, die du anfragst.
Die EUDI-Wallet ist eine kostenlose App für die europäische digitale Identität, die jeder EU-Mitgliedstaat gemäß der Verordnung (EU) 2024/1183, bekannt als eIDAS 2, anbieten muss. Sie enthält Personenidentifizierungsdaten (PID), also Name, Geburtsdatum und -ort sowie Staatsangehörigkeit, dazu elektronische Attributsbescheinigungen wie einen Führerschein oder ein Diplom. Die Nutzung ist freiwillig.
Wenn ein Unternehmen Daten anfordert, sieht die Person, wer anfragt, und teilt nur die angeforderten Attribute. Dies wird als selektive Offenlegung bezeichnet: Eine Website kann erfahren, dass jemand über 18 ist, ohne das Geburtsdatum zu sehen. Die Wallet arbeitet mit dem Sicherheitsniveau „hoch“, dem stärksten der drei eIDAS-Niveaus, und das Unternehmen prüft die Ausstellerunterschrift, bevor es sich auf die Daten verlässt.
Zuletzt geprüft: 5. Oktober 2026. Keine Rechtsberatung.
Wichtige Termine
Wallets bis Ende 2026. Akzeptanz bis 24. Dezember 2027.
Dies sind die Termine in der Verordnung (EU) 2024/1183 und ihren Durchführungsrechtsakten, die ein Unternehmen berücksichtigen sollte.
30. April 2024
eIDAS 2 veröffentlicht
Die Verordnung (EU) 2024/1183 zur Änderung der eIDAS-Verordnung (EU) Nr. 910/2014 erscheint im Amtsblatt der EU. Sie tritt am zwanzigsten Tag nach ihrer Veröffentlichung in Kraft.
24. Dezember 2024
Erste Wallet-Regeln in Kraft
Die ersten fünf Durchführungsverordnungen für die Wallet treten in Kraft: personenbezogene Identifikationsdaten, Kernfunktionen, Benachrichtigungen, Zertifizierung sowie Protokolle und Schnittstellen. Sie starten die unten genannten 24- und 36-Monatsfristen.
15. Juli 2026
Wallet-Regeln aktualisiert
Die Kommission erlässt die Durchführungsverordnung (EU) 2026/1731. Sie legt die beiden Credential-Formate, SD-JWT VC und ISO/IEC mdoc, fest und plant das obligatorische Porträt für 2028 ein.
23. Juli 2026
ARF v3.0.0
Das Architecture and Reference Framework (ARF), der technische Bauplan, auf dem Wallets und vertrauende Parteien aufbauen, erreicht Version 3.0.0.
24. Dezember 2026
Wallets in jedem Mitgliedstaat
Jeder Mitgliedstaat muss mindestens eine EUDI-Wallet bereitstellen. Die Regeln für die Registrierung vertrauender Parteien, Durchführungsverordnung (EU) 2025/848, gelten ab demselben Tag.
24. Dezember 2027
Private Unternehmen müssen sie akzeptieren
Private Unternehmen, die gesetzlich oder vertraglich eine starke Nutzerauthentifizierung verwenden müssen, mit Ausnahme von Kleinst- und Kleinunternehmen, müssen die Wallet akzeptieren, wenn ein Nutzer sie verwenden möchte (Artikel 5f Absatz 2). Diese Frist endet 36 Monate nach Inkrafttreten der ersten Durchführungsrechtsakte am 24. Dezember 2024, also am 24. Dezember 2027.
11. August 2028
Porträt- und Registrierungsprüfungen
Das Porträt wird Teil der obligatorischen personenbezogenen Identifikationsdaten, und Wallets müssen das Registrierungszertifikat jeder vertrauenden Partei authentifizieren und validieren.
Wer sie akzeptieren muss
Wer die Wallet wann akzeptieren muss.
Artikel 5f der eIDAS-Verordnung, geändert durch die Verordnung (EU) 2024/1183, legt die Akzeptanzpflichten fest. In jedem Fall wählt der Nutzer die Verwendung der Wallet, und du behältst deine anderen Möglichkeiten zur Identifizierung von Personen bei.
Wer
Was das im Klartext bedeutet
Artikel · Datum
Wer
Öffentliche Stellen
Was das im Klartext bedeutet
Wenn ein Mitgliedstaat eine elektronische Identifizierung für den Zugang zu einem öffentlichen Online-Dienst verlangt, muss dieser Dienst auch die EUDI-Wallet akzeptieren.
Artikel · Datum
Art. 5f(1)
Wer
Private Dienste, die eine starke Nutzerauthentifizierung erfordern
Was das im Klartext bedeutet
Wenn ein Gesetz oder Vertrag von dir eine starke Nutzerauthentifizierung für die Online-Identifizierung verlangt, musst du auch die EUDI-Wallet akzeptieren. Auslöser ist diese Anforderung, nicht dein Sektor.
Artikel · Datum
Art. 5f(2) · 24. Dez. 2027
Wer
Genannte Bereiche im Artikel
Was das im Klartext bedeutet
Transport, Energie, Banken, Finanzdienstleistungen, soziale Sicherheit, Gesundheit, Trinkwasser, Postdienste, digitale Infrastruktur, Bildung und Telekommunikation. Der Artikel sagt „einschließlich“, die Liste ist also beispielhaft und nicht abschließend.
Artikel · Datum
Art. 5f(2)
Wer
Kleinst- und Kleinunternehmen
Was das im Klartext bedeutet
Von der Pflicht für den Privatsektor ausgenommen, wie in der Empfehlung 2003/361/EG der Kommission definiert. Sie können die Wallet dennoch akzeptieren, wenn sie dies wünschen.
Artikel · Datum
Art. 5f(2)
Wer
Nur auf Anfrage des Nutzers
Was das im Klartext bedeutet
Die Akzeptanz ist fällig, wenn der Nutzer die Wallet verwenden möchte. Die Nutzung ist für Personen freiwillig, und Dienste müssen offen für andere Identifizierungs- und Authentifizierungsmittel bleiben.
Artikel · Datum
Art. 5f(2), 5a(15)
Wer
Sehr große Online-Plattformen
Was das im Klartext bedeutet
Plattformen, die unter dem Gesetz über digitale Dienste benannt sind und eine Nutzerauthentifizierung erfordern, müssen die Wallet auf Anfrage des Nutzers für die minimalen Daten akzeptieren, die der Dienst benötigt. Der Text legt kein separates Datum für diese Pflicht fest.
Artikel · Datum
Art. 5f(3)
Relying Parties müssen sich auch in dem Mitgliedstaat registrieren, in dem sie niedergelassen sind, und dürfen nur die Daten anfordern, die sie registriert haben (Artikel 5b). Letzte Überprüfung: 5. Oktober 2026. Keine Rechtsberatung.
So akzeptiert ein Unternehmen die Wallet
So akzeptiert eine Relying Party die EUDI-Wallet, in fünf Schritten.
Schritt 01 / 05
01
Als Relying Party registrieren
Registriere dich in dem Mitgliedstaat, in dem du niedergelassen bist, mit deinen Daten und den Daten, die du anfordern möchtest. Du erhältst ein Zugangszertifikat, das dich gegenüber der Wallet authentifiziert, und, falls dein Mitgliedstaat eines ausstellt, ein Registrierungszertifikat, das die von dir registrierten Attribute auflistet.
Nur anfordern, was du brauchst
Fordere spezifische Attribute an, zum Beispiel Alter über 18, mit OpenID for Verifiable Presentations (OpenID4VP) und einer Digital Credentials Query Language (DCQL) Abfrage oder mit ISO/IEC 18013-7. Du darfst keine Daten anfordern, die über deine Registrierung hinausgehen.
Der Nutzer stimmt in der Wallet zu
Auf demselben Telefon übergibt der Browser an die Wallet-App. Auf einem Computer scannt der Nutzer einen QR-Code. Die Wallet zeigt an, wer anfragt, prüft, ob du nicht mehr anforderst, als du registriert hast, und der Nutzer genehmigt oder lehnt ab.
Die Präsentation verifizieren
Überprüfe die Aussteller-Signatur anhand der vertrauenswürdigen Listen, prüfe, ob das Credential nicht widerrufen wurde, und überprüfe die Gerätebindung, die zeigt, dass das Credential nicht kopiert oder wiederverwendet wurde.
Attribute erhalten und entscheiden
Du erhältst nur die Attribute, die der Nutzer geteilt hat, signiert vom Aussteller. Die Onboarding- oder Zugangsentscheidung und die Aufzeichnung, die du führst, bleiben bei dir.
Didit wird diese Schritte für dich ausführen, sobald die Akzeptanz der EUDI-Wallet startet (bald verfügbar).
Was du erhältst vs. was KYC noch braucht
Die Wallet beweist, wer jemand ist. Sorgfaltspflichten brauchen mehr.
Gemäß der Geldwäscheverordnung (AMLR), Verordnung (EU) 2024/1624, ist die elektronische Identifizierung mit einem Sicherheitsniveau von „erheblich“ oder „hoch“ eine von zwei Möglichkeiten zur Identitätsprüfung (Artikel 22(6)). Sie deckt nicht alles ab, was Know Your Customer (KYC)-Prüfungen erfordern. Hier ist, was die Personenidentifizierungsdaten (PID) enthält und wie Didit jeden Punkt heute abdeckt.
Due Diligence braucht
In der EUDI-Wallet PID
Wie Didit es heute abdeckt
Due Diligence braucht
Alle Vor- und Nachnamen
AMLR Art. 22(1)(a)
In der EUDI-Wallet PID
Familienname und Vorname, beides obligatorisch.
Wie Didit es heute abdeckt
Nationale eIDs liefern den vollständigen Namen. Der Dokumenten-Workflow liest ihn aus über 14.000 Dokumententypen aus.
Due Diligence braucht
Ort und vollständiges Geburtsdatum
AMLR Art. 22(1)(a)
In der EUDI-Wallet PID
Geburtsdatum und Geburtsort, beides obligatorisch.
Wie Didit es heute abdeckt
Nationale eIDs liefern das Geburtsdatum. Der Dokumenten-Workflow liest den Geburtsort aus, sofern er auf dem Dokument vermerkt ist.
Due Diligence braucht
Nationalitäten
AMLR Art. 22(1)(a)
In der EUDI-Wallet PID
Nationalität, obligatorisch, ein oder mehrere Länder.
Wie Didit es heute abdeckt
Der Dokumenten-Workflow liest die Nationalität aus dem Ausweisdokument oder dessen Chip aus.
Due Diligence braucht
Nationale Identifikationsnummer, falls zutreffend
AMLR Art. 22(1)(a)
In der EUDI-Wallet PID
Persönliche Verwaltungsnummer, optional. Jeder Mitgliedstaat entscheidet, ob er diese ausstellt.
Wie Didit es heute abdeckt
Nationale eIDs liefern eine Kennung des jeweiligen Systems: die schwedische Personennummer, den finnischen Personenkenncode oder den baltischen Personencode. MitID liefert eine pseudonymisierte Kennung, nicht die CPR-Nummer.
Due Diligence braucht
Gewöhnlicher Wohnsitz
AMLR Art. 22(1)(a)
In der EUDI-Wallet PID
Adressfelder sind optional und oft nicht vorhanden. Die endgültigen Entwurfsstandards der AMLA besagen, dass fehlende Attribute auf andere Weise beschafft werden müssen.
Wie Didit es heute abdeckt
Keine nationale eID liefert eine Adresse. Der Adressnachweis prüft eine Stromrechnung, einen Kontoauszug oder ein behördliches Schreiben.
Due Diligence braucht
Steueridentifikationsnummer, falls vorhanden
AMLR Art. 22(1)(a)
In der EUDI-Wallet PID
Nicht Teil der PID.
Wie Didit es heute abdeckt
Erfasse sie mit einem Fragebogenschritt im selben Workflow.
Due Diligence braucht
Die Person stimmt mit der Identität überein
ARF · Nutzerbindung
In der EUDI-Wallet PID
Das Porträt bleibt optional, bis es am 11. August 2028 obligatorisch wird.
Wie Didit es heute abdeckt
Passive Liveness und ein 1:1-Gesichtsabgleich mit dem Dokumentenfoto oder dem Chip-Porträt, im Rahmen der vollständigen KYC-Prüfung für $0.33.
Due Diligence braucht
Wirtschaftlich Berechtigte eines Unternehmens
AMLR Art. 20(1)(b)
In der EUDI-Wallet PID
Nicht in der PID enthalten. Eine Wallet identifiziert eine Person, nicht den Eigentümer eines Unternehmens.
Wie Didit es heute abdeckt
Die Unternehmensverifizierung ruft Registerdaten und Eigentümer ab, sofern diese im Register hinterlegt sind, mit einer Identitätsprüfung für jeden Eigentümer.
Due Diligence braucht
Sanktionen und politisch exponierte Personen (PEPs)
AMLR Art. 20(1)(d), (g)
In der EUDI-Wallet PID
Nicht in der PID enthalten.
Wie Didit es heute abdeckt
AML-Screening gegen über 1.300 Sanktions-, PEP- und Beobachtungslisten, für $0.20 pro Prüfung.
Due Diligence braucht
Zweck der Geschäftsbeziehung und laufende Überwachung
AMLR Art. 25, 26
In der EUDI-Wallet PID
Nicht in der PID enthalten.
Wie Didit es heute abdeckt
Fragebögen erfassen den Zweck der Geschäftsbeziehung. Die laufende Überwachung überprüft Kunden täglich erneut für $0.07 pro Person und Jahr.
Die Sorgfaltspflichten für Kunden bleiben deine Aufgabe. Didit liefert Prüfungen und Nachweise, macht dich aber nicht gesetzeskonform. Die AMLR gilt ab dem 10. Juli 2027, und die technischen Standards der AMLA sind ein endgültiger Entwurf vom 30. September 2026, noch kein Gesetz.
Bereitschaft nach Ländern
Der Stand der nationalen Wallets, datiert und belegt.
Das haben die einzelnen Länder veröffentlicht oder eine genannte Quelle berichtet, inklusive Datum und Link für jede Zeile.
Stand vom 5. Oktober 2026
Land
Wallet oder App
Status
Datum
Was bekannt ist
Land
Italien
Wallet oder App
IT-Wallet (app IO)
Status
Live-App
Datum
17. Februar 2026
Was bekannt ist
Live in der IO App, mit 10,1 Millionen Aktivierungen und 17,3 Millionen geladenen Dokumenten bis zum 17. Februar 2026. Kostenlos und optional für Erwachsene, die sich mit CIE oder SPID anmelden.
AltID ist mit digitalem Ausweis und Altersnachweis verfügbar, und bis zum 4. August 2026 hatten 281.390 Personen eine AltID erstellt. Die Agentur für digitale Verwaltung implementiert die Wallet schrittweise.
Öffentliche Sandbox seit Dezember 2025. Die App soll Anfang 2027 erscheinen, beginnend mit der ID-Funktion. Das Umsetzungsgesetz hatte seine erste Lesung im Bundestag am 23. September 2026.
Nicht aufgeführt: Österreich, Belgien, Estland, Ungarn, Lettland, Litauen, Luxemburg, Malta, Portugal, Slowenien. Für diese Länder haben wir an diesem Datum keinen öffentlichen Status gefunden. Wir aktualisieren diese Tabelle, sobald nationale Apps starten.
So bringt dich Didit ans Ziel · Fünf Zeilen
Akzeptiere jetzt nationale eIDs. Füge als Nächstes die EUDI-Wallet hinzu.
Die EUDI-Wallet ergänzt deine Optionen, ersetzt aber keine bestehenden. Baue deinen Workflow einmal auf: nationale eIDs und Dokumente heute, und EUDI-Wallet Akzeptanz im selben ID-Verifizierungsschritt, sobald sie verfügbar ist.
Akzeptiere die nationalen eIDs, die deine Kunden bereits nutzen.
Fünf nationale eIDs sind über Didit in sieben Ländern live: MitID, BankID Sweden, Finnish Trust Network, Smart-ID und Mobile-ID. Der Nutzer meldet sich mit seiner eID an, und die Session erhält signierte Attribute: vollständiger Name, Geburtsdatum, eine Kennung des jeweiligen Systems (zum Beispiel die schwedische Personennummer; MitID liefert eine pseudonymisierte Kennung) und das vom Schema bestätigte Sicherheitsniveau. Nur abgeschlossene Anmeldungen werden abgerechnet.
Niveaus, wie Didit sie kennzeichnet. Es werden keine Adresse und kein Porträt zurückgegeben.
02 · EUDI-Wallet, demnächst
EUDI-Wallet Akzeptanz, im selben Workflow.
Die Akzeptanz der EUDI Wallet kommt bald. Unser Wallet-Katalog listet sie für 30 EWR-Länder im selben Schritt der ID-Verifizierung wie die nationalen eIDs. Ein Datum oder Preis steht noch nicht fest.
Noch kein Datum oder Preis für die EUDI-Wallet-Akzeptanz.
03 · Dokumenten-Route
Eine Dokumenten-Route für alle ohne Wallet.
Nicht jeder wird eine Wallet haben oder nutzen, und das Gesetz lässt andere Mittel offen. Die Dokumenten-Route liest den Chip in Pässen und Ausweisen per NFC ($0.15), führt eine passive Lebenderkennung durch und gleicht das Gesicht mit dem Dokumentenfoto ab, über 14.000+ Dokumententypen in 220+ Ländern und Gebieten.
Die EUDI-Wallet kann nachweisen, dass jemand über 18 ist, ohne ein Geburtsdatum preiszugeben. Bis Wallets verbreitet sind, kostet die Altersschätzung per Selfie $0.10 pro Prüfung und leitet Grenzfälle an einen ID-Verifizierungs-Fallback weiter. Eine Live-eID-Anmeldung liefert auch ein signiertes Geburtsdatum ohne Dokumentenfoto.
Screening, Monitoring und Unternehmen, alles an einem Ort.
Identität ist ein Teil der Customer Due Diligence. Im selben Workflow kannst du Personen gegen 1.300+ Sanktions-, PEP- und Beobachtungslisten screenen ($0.20 pro Prüfung), sie täglich mit fortlaufendem Monitoring erneut screenen ($0.07 pro Person pro Jahr) und Unternehmen sowie deren Eigentümer verifizieren.
Eine geräteübergreifende Darstellung, wie sie die ARF beschreibt: Die Person beginnt am Computer und beendet den Vorgang auf dem Telefon, das die Wallet enthält.
01Scannen zum Fortfahren
QR-Code scannen
Der Dienst zeigt einen QR-Code an, den die Person mit der Wallet-App scannt.
02Online-Shop fragt nach: Alter über 18
Anfrage prüfen
Die Wallet zeigt an, wer anfragt und welche Attribute benötigt werden.
031 Attribut teilen
Teilen
Die Person stimmt zu, und nur die angefragten Attribute verlassen das Telefon.
04Verifiziert
Verifiziert
Der Dienst prüft die Aussteller-Signatur und fährt fort. Nichts anderes wurde geteilt.
Eine Illustration des Standardablaufs. Didits EUDI-Wallet Akzeptanz kommt bald.
Jetzt integrieren
Jetzt integrieren und behalten, wenn die Wallet kommt.
Es gibt noch keine EUDI-spezifische Didit API. Erstelle eine Session für einen Workflow, der die nationalen eIDs und Dokumente akzeptiert, und lies dann das Ergebnis aus. Die Akzeptanz der EUDI-Wallet ist für denselben ID-Verifizierungsschritt geplant.
Bereite dich mit einem Prompt auf die EUDI-Wallet vor.
Kopiere diesen Prompt in deinen Coding Agent. Er erstellt den Workflow, den du heute schon nutzen kannst: Live nationale eIDs mit Dokument-Fallback, plus den Session-Call und den signierten Webhook. Er erfindet keinen EUDI-Endpunkt, da noch keiner existiert.
didit-integration-prompt.md
# Didit: get ready for the EUDI Wallet with the ID Verification step you run today
You are adding electronic identification to my_stack so the product is ready
for the EU Digital Identity (EUDI) Wallet. Every URL, header and enum value
below is canonical. Do not paraphrase or "improve" them.
## 0. What exists today, and what does not
- EUDI Wallet acceptance on Didit is coming soon. There is NO EUDI-specific
endpoint, wallet id, field or flag to integrate yet. Do not invent one, do
not send any EUDI identifier in a workflow, and do not build an OpenID4VP
verifier yourself as part of this task.
- What is live: national digital ID wallets inside the ID Verification step,
with document capture (chip reading, liveness, face match) as the fallback.
EUDI Wallet acceptance is planned for the same ID Verification step, so the
workflow, session call and webhook you build now are the ones you keep.
- The live wallets, as listed by the methods catalog:
- MitID: wallet id mitid, country keys DNK (Denmark)
- BankID: wallet id bankid_se, country keys SWE (Sweden)
- Finnish Trust Network: wallet id ftn, country keys FIN (Finland)
- Smart-ID: wallet id smart_id, country keys EST (Estonia), LVA (Latvia), LTU (Lithuania), BEL (Belgium)
- Mobile-ID: wallet id mobile_id, country keys EST (Estonia), LTU (Lithuania)
Check the catalog for your environment before you go live. Never
hard-code dates.
## 1. Provision an account
- Sign up: https://business.didit.me (no credit card required).
- Copy the API key of your application from the console.
## 2. Read the methods catalog
Availability is server-driven per country. Only wallets marked available can
be enabled on a live application.
- Business Console: your application -> Workflows -> the ID Verification
step -> Countries -> "Wallets accepted". Coming-soon wallets are listed
but cannot be switched on. https://docs.didit.me/console/id-verification-methods
- Didit MCP server (https://mcp.didit.me/mcp), tool
didit_workflow_get_id_verification_methods_catalog; pass country as ISO
3166-1 alpha-3 to narrow it. The MCP server signs in with "Log in with
Didit" (OAuth). It does not accept the x-api-key.
https://docs.didit.me/integration/mcp/tools
- Public coverage table (no sign-in, read-only):
https://docs.didit.me/core-technology/id-verification/digital-id-wallets#supported-wallets
If your code holds only an API key, it cannot read the catalog itself: use the
wallet ids listed in this prompt, and treat the answer of the workflow save as
the check. A live application answers 400 for a wallet that is not available
in that country ("<wallet> is not offered in <ISO3>", "unknown wallet").
## 3. Create the workflow (ID Verification = feature OCR)
POST https://verification.didit.me/v3/workflows/
-H "x-api-key: <your-api-key>"
-H "Content-Type: application/json"
{
"workflow_label": "eID onboarding",
"features": [
{
"feature": "OCR",
"config": {
"methods": {
"DNK": {
"document": { "enabled": true },
"wallet": {
"enabled": true,
"providers": ["mitid"],
"on_failure": "fallback_to_document"
}
},
"EST": {
"document": { "enabled": true },
"wallet": {
"enabled": true,
"providers": ["smart_id", "mobile_id"],
"on_failure": "fallback_to_document"
}
}
}
}
}
]
}
Response: 201. The workflow id is uuid (workflow_id carries the same value);
the workflow is published straight away. Create it once and keep the id:
every call to this endpoint makes a new workflow.
is_desktop_allowed defaults to false: on a desktop browser the hosted flow
then shows a QR code to continue on a phone. Add "is_desktop_allowed": true
next to workflow_label to let people finish on desktop.
Rules the API enforces:
- OCR is UPPERCASE; ID_VERIFICATION is rejected in this body (the decision
later lists the step as ID_VERIFICATION in its features)
- country keys are ISO 3166-1 alpha-3; method keys are document, id_lookup, wallet
- providers is an accept-list, not a ranking; the end user picks
- on_failure is fallback_to_document or decline
- a wallet the catalog does not mark available rejects the whole save (400)
- every other country keeps document capture, so people without an eID
can still verify
- this body runs document capture only. Chip reading, liveness and face
match are their own features: add { "feature": "NFC" },
{ "feature": "LIVENESS" } and { "feature": "FACE_MATCH" } to features
when your policy needs them
## 4. Create a session
POST https://verification.didit.me/v3/session/
-H "x-api-key: <your-api-key>"
-H "Content-Type: application/json"
-d '{ "workflow_id": "<id from step 3>", "vendor_data": "<your user id>" }'
Response: 201 with session_id, session_token, url and status "Not Started".
Redirect the user to url (hosted flow) or open it in the Web, iOS, Android,
React Native or Flutter SDK. The field is named url on this response.
One unfinished session exists per workflow_id and vendor_data pair: calling
create again with the same pair answers 201 again with that same session.
## 5. Webhook
Register a destination in the console (API & Webhooks), or over the API:
POST https://verification.didit.me/v3/webhook/destinations/
-H "x-api-key: <your-api-key>"
-H "Content-Type: application/json"
-d '{
"label": "Verification webhooks",
"url": "https://<your-public-host>/webhooks/didit",
"webhook_version": "v3",
"subscribed_events": ["status.updated", "data.updated"]
}'
label, url and subscribed_events are required. url must be a public HTTPS
address: Didit does not deliver to localhost or private addresses. Response:
201 with uuid and secret_shared_key. Store secret_shared_key as the webhook
secret (DIDIT_WEBHOOK_SECRET); it is unique to this destination. Remove a
destination with DELETE /v3/webhook/destinations/{uuid}/ (204).
What arrives:
- webhook_type is "status.updated" (the session changed status) or
"data.updated" (verification data was corrected after the fact)
- a destination receives the events of every session of the application,
so filter on workflow_id or vendor_data when several flows share it
- creating a session already sends status.updated with status
"Not Started". The decision key is present only when status is Approved,
Declined, In Review or Abandoned.
Verify every delivery:
Header: X-Signature-V2 (not X-Signature, not X-Signature-Simple)
Algorithm: HMAC-SHA256, hex digest, over the canonical JSON of the payload
(Python json.dumps(sort_keys=True, separators=(",", ":"),
ensure_ascii=False) after whole-valued floats become ints).
Never hash the raw request bytes under this header.
Freshness: the signed body field timestamp is the dispatch time (Unix
seconds). Reject when abs(now - timestamp) > 300 seconds, and
reject when the X-Timestamp header does not equal it.
Idempotency: event_id is the same on every retry of one event, so store it
and skip a delivery you already processed. One session can
still send the same status under two event ids, and the
console's Try Webhook test deliveries carry no event_id, so
also make the handler safe to run twice for one
(session_id, status, webhook_type).
Compare: constant-time (crypto.timingSafeEqual)
Reference handler (Express). Keep the verification lines as written.
The handler is a fragment. Put this above it and app.listen(process.env.PORT)
below it. It needs Express and Node 21 or newer (an older Node rejects
every delivery). It expects a JSON body: answer 400 yourself if you accept
anything else on this route, and refuse to start without the secret.
const express = require("express");
const app = express();
const SECRET = process.env.DIDIT_WEBHOOK_SECRET; // secret_shared_key of the destination
// Your endpoint receives a signed payload
const crypto = require("node:crypto"); // ESM: import crypto from "node:crypto"
// X-Signature-V2 = HMAC over the canonical JSON, never the raw bytes. Match the sender byte for
// byte: keys sorted by code point, integers digit for digit, floats in Python's repr.
class Num { constructor(src) { this.src = src; } } // a number as written on the wire, not a double
const num = (s) => { if (/^-?\d+$/.test(s)) return BigInt(s).toString(); const n = +s; // ints stay exact
if (Number.isInteger(n)) return BigInt(n).toString(); const [m, e] = n.toExponential().split("e"); // 27.0 -> 27
return +e >= -4 ? String(n) : `${m}e-${String(-e).padStart(2, "0")}`; }; // 1e-05, not 0.00001
const byCodePoint = (a, b) => Buffer.compare(Buffer.from(a), Buffer.from(b)); // UTF-8 order = Python's
const canon = (v) => Array.isArray(v) ? `[${v.map(canon)}]` : v instanceof Num ? num(v.src)
: v && typeof v === "object" ? `{${Object.keys(v).sort(byCodePoint).map((k) => `${JSON.stringify(k)}:${canon(v[k])}`)}}`
: JSON.stringify(v);
// Read the body as text: express.json() would round 1000000000000000129 to a double first.
// Register this route ABOVE any global app.use(express.json()): the first parser to run
// consumes the stream, and a body it already parsed has lost the digits the signature covers.
app.post("/webhooks/didit", express.text({ type: "application/json" }), (req, res) => {
const exact = JSON.parse(req.body, (k, v, c) => typeof v === "number" ? new Num(c.source) : v); // Node 21+
const body = JSON.parse(req.body);
const mac = crypto.createHmac("sha256", SECRET).update(canon(exact), "utf8").digest("hex");
const sig = Buffer.from(String(req.headers["x-signature-v2"] ?? ""));
// Freshness comes from the signed body timestamp; the header alone is unsigned and replayable.
const ts = body.timestamp, fresh = String(ts) === req.headers["x-timestamp"]
&& Math.abs(Date.now() / 1000 - ts) <= 300;
if (!fresh || sig.length !== mac.length
|| !crypto.timingSafeEqual(sig, Buffer.from(mac))) return res.sendStatus(401);
const { status, decision } = body;
// One entry per ID Verification node; pick yours by node_id when you run several.
const [idv] = decision?.id_verifications ?? [];
// idv.verification_method: "document" | "id_lookup" | "wallet"
res.sendStatus(200);
});
Status values (exact strings): Not Started, In Progress, Approved, Declined,
In Review, Resubmitted, Expired, Abandoned, Kyc Expired. Awaiting User only
appears on business verification sessions.
## 6. Read the result
The same V3 decision reaches you two ways:
- webhook body: body.decision.id_verifications[]
- GET https://verification.didit.me/v3/session/{session_id}/decision/
-H "x-api-key: <your-api-key>"
This response IS the decision object. Read id_verifications at the top
level: there is no decision wrapper here.
Until the user finishes the ID step, status is "Not Started" or "In Progress"
and id_verifications is null, not an empty array. Guard for it.
id_verifications[] has one entry per ID Verification node; with a single step
take index 0. A wallet sign-in sets:
verification_method "wallet"
assurance "cryptographic"
wallet_provider the catalog wallet id the user picked
wallet_verification provider, provider_name, issuing_authority,
issuing_country, credential_type, level_of_assurance,
verified_at, signature_valid, attributes, portrait
(null for the live wallets), face_match_score
fallback_from { method, reason, action } when the wallet sign-in failed
and on_failure declined the session; otherwise
null. After a document fallback that succeeds the
entry reads verification_method "document" with
fallback_from null
full_name, the normalised identity fields, on the entry itself
date_of_birth
On a live application, check wallet_verification.signature_valid before you
trust attributes. The
live wallets return name, date of birth and a scheme identifier (for example
the Swedish personnummer; MitID returns a pseudonymised identifier), never an
address or a portrait: collect those through other steps if your policy
needs them.
Reference: https://docs.didit.me/core-technology/id-verification/digital-id-wallets
## 7. Billing
Only completed wallet sign-ins are billed; cancelled, timed-out and failed
ones are free. Prices per wallet: https://didit.me/pricing
## 8. Verify your integration
Sandbox (an application in sandbox mode: nothing is billed and no real eID is
called). https://docs.didit.me/integration/sandbox-testing
- a sandbox application can enable every wallet in the catalog, the
coming-soon ones included. A workflow that saves in sandbox can still be
refused on a live application, so only use wallets marked available.
- open the session url, pick the wallet and confirm: the default approve
scenario simulates the sign-in. The entry then has verification_method
"wallet", assurance "cryptographic" and wallet_provider set, and the
normalised full_name and date_of_birth are filled. But
wallet_verification.signature_valid and level_of_assurance are null and
attributes is { "sandbox": true }: no real credential was checked.
Assert signature_valid === true and the level of assurance only against
a live application.
- to exercise on_failure, create the session with
"sandbox_scenario": "wallet_cancelled" (also wallet_timeout and
wallet_provider_error). The wallet sign-in then fails and the flow moves
to document capture or declines, as on_failure says. A fallback that
ends in an approved document reads verification_method "document".
- POST /v3/session/{session_id}/simulate/ forces a final status but writes
no id_verifications entry, so it cannot stand in for a sign-in.
Checks:
- create the workflow, create a session, and read its decision: expect 201,
201 with url, and 200 with status "Not Started"
- run one sandbox session per accepted wallet through the hosted flow and
assert verification_method is "wallet" and wallet_provider is the wallet
you picked
- run one session with sandbox_scenario "wallet_cancelled" and assert the
flow offers document capture
- assert the webhook accepts a correctly signed payload and rejects a wrong
X-Signature-V2, a changed body, and a payload whose signed timestamp is
older than 300 seconds, even when X-Timestamp is refreshed
- on a live application, assert wallet_verification.signature_valid is true
Docs: https://docs.didit.me/core-technology/id-verification/digital-id-wallets
Compliant by Design
Ein neues Land mit einem Klick erschließen. Wir machen die Arbeit.
Wir gründen lokale Tochtergesellschaften, sichern Lizenzen, führen Penetrationstests durch, erhalten Zertifizierungen und passen uns jeder neuen Regulierung an. Um Verifizierungen in einem neuen Land zu starten, legst du einfach einen Schalter um. Über 220 Länder live, vierteljährlich auditiert und Pen-getestet, der einzige Identitätsanbieter, den eine EU-Mitgliedsregierung offiziell als sicherer als die persönliche Verifizierung eingestuft hat.
Kostenlos starten. Nach Verbrauch zahlen. Bis zum Enterprise-Level skalieren.
500 kostenlose Verifizierungen jeden Monat, für immer. Danach zahlst du nur, wenn ein Modul läuft. Individuelle Verträge, Datenresidenz und Service Level Agreements (SLAs) für Enterprise-Kunden.
Kostenlos
$0/ Monat · keine Kreditkarte nötig
Zum Entwickeln, Testen und für deine ersten Nutzer.
Alles, was du für den Start brauchst:
500 vollständige KYC-Verifizierungen pro Monat
ID, Liveness, Face Match, Gerät & IP
Über 200 Betrugssignale, Blocklist, Duplikate
Wiederverwendbares KYC im Didit-Netzwerk
Workflow Builder, Case Management, SDKs
KI-SupportKI-Agent in der Konsole, Docs und Community.