@injistack/react-inji-verify-sdk 0.19.0-beta.11 → 0.19.0-beta.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -1,7 +1,28 @@
1
1
  # INJI VERIFY SDK
2
2
 
3
+ **Repository:** [github.com/mosip/inji-verify](https://github.com/mosip/inji-verify)
4
+
3
5
  Inji Verify SDK provides ready-to-use **React components** to integrate [OpenID4VP](https://openid.net/specs/openid-4-verifiable-presentations-1_0.html)-based **Verifiable Credential (VC) and Verifiable Presentation (VP) verification** into any React TypeScript web application.
4
6
 
7
+ ## Index
8
+
9
+ 1. [Pre-requisites](#pre-requisites)
10
+ 2. [Usage Guide](#usage-guide)
11
+ - [Install](#step-1-install-the-package)
12
+ - [Choose Verification Method](#step-3-choose-verification-method)
13
+ - [Verification Response](#verification-response)
14
+ 3. [Detailed Component Guide](#detailed-component-guide)
15
+ - [Option A: QR Code Verification](#option-a-qr-code-verification-scan--upload)
16
+ - [Verification Response](#verification-response-1)
17
+ - [Option B: OpenID4VP Verification](#option-b-openid4vp-verification)
18
+ - [Verification Response](#verification-response-2)
19
+ - [DCQL Query](#dcql-query)
20
+ - [`require_cryptographic_holder_binding`](#require_cryptographic_holder_binding)
21
+ 4. [Component Options Reference](#️-component-options-reference)
22
+ 5. [Important Limitations](#️-important-limitations)
23
+
24
+ ---
25
+
5
26
  ## Pre-requisites
6
27
 
7
28
  ### What You Need:
@@ -15,7 +36,7 @@ Inji Verify SDK provides ready-to-use **React components** to integrate [OpenID4
15
36
  Your backend must support the OpenID4VP protocol. You can either:
16
37
 
17
38
  - Use the official `inji-verify-service`
18
- - Build your own following [this specification](https://openid.net/specs/openid-4-verifiable-presentations-1_0-ID3.html)
39
+ - Build your own following [this specification](https://openid.net/specs/openid-4-verifiable-presentations-1_0.html)
19
40
 
20
41
  **Important:** Your backend URL should look like:
21
42
 
@@ -78,13 +99,15 @@ function MyApp() {
78
99
  triggerElement={<button>Show QR for Wallet Scan</button>}
79
100
  verifyServiceUrl="https://your-backend.com/v1/verify"
80
101
  clientId="did:example:123456789" // DID example
81
- presentationDefinitionId="your-definition-id"
102
+ dcqlQuery={{
103
+ credentials: [{ id: "id_card", format: "ldp_vc", meta: {} }]
104
+ }}
82
105
  isSameDeviceFlowEnabled={false} // QR code flow
83
106
  onVPProcessed={(result) => {
84
107
  console.log("VP processed:", result);
85
108
  }}
86
109
  onQrCodeExpired={() => {
87
- console.log(" QR code expired - ask user to retry");
110
+ console.log("QR code expired - ask user to retry");
88
111
  }}
89
112
  onError={(error) => {
90
113
  console.error("Verification error:", error);
@@ -114,7 +137,7 @@ If `summariseResults = true`, the response will be:
114
137
  "vcResults": [
115
138
  {
116
139
  "vc": { /* Your verified credential data */ },
117
- "vcStatus": "SUCCESS" // or "INVALID", "EXPIRED"
140
+ "vcStatus": "SUCCESS" // or "INVALID", "EXPIRED", "REVOKED"
118
141
  }
119
142
  ],
120
143
  "vpResultStatus": "SUCCESS" // Overall verification status
@@ -265,7 +288,7 @@ If `summariseResults = false`, the response will be:
265
288
  "allChecksSuccessful": true,
266
289
  "schemaAndSignatureCheck": { "valid": true, "error": null },
267
290
  "expiryCheck": { "valid": true },
268
- "statusChecks": [
291
+ "statusCheck": [
269
292
  { "purpose": "revocation", "valid": true, "error": null }
270
293
  ],
271
294
  "claims": {...}
@@ -276,14 +299,18 @@ If `summariseResults = false`, the response will be:
276
299
 
277
300
  | Property | Type | Description |
278
301
  |---------------------------|---------|-----------------------------------------------------------|
279
- | `allChecksSuccessful` | boolean | Final aggregated validation flag |
280
- | `schemaAndSignatureCheck` | object | Validates schema and signature check |
281
- | `expiryCheck` | object | If false, the credential is EXPIRED |
282
- | `statusChecks` | array | Contains revocation and other status validations |
283
- | `statusChecks.error` | object | If present, throws an error instead of returning a status |
284
- | `statusChecks.purpose` | string | Identifies purpose (e.g., "revocation") |
285
- | `statusChecks.valid` | boolean | If false for revocation → credential is revoked |
286
- | `claims` | object | Includes all claims from credentialSubject |
302
+ | `vc` | object | The VC that has been verified |
303
+ | `allChecksSuccessful` | boolean | Final aggregated validation flag |
304
+ | `schemaAndSignatureCheck` | object | Schema and signature validation result |
305
+ | `schemaAndSignatureCheck.valid`| boolean | If false, credential signature or schema is invalid |
306
+ | `schemaAndSignatureCheck.error`| object | Non-null if the check could not be performed |
307
+ | `expiryCheck` | object | Expiry validation result |
308
+ | `expiryCheck.valid` | boolean | If false, the credential is EXPIRED |
309
+ | `statusCheck` | array | Contains revocation and other status validations |
310
+ | `statusCheck[].purpose` | string | Identifies purpose (e.g., "revocation") |
311
+ | `statusCheck[].valid` | boolean | If false for revocation and `error` is null → credential is revoked |
312
+ | `statusCheck[].error` | object | Non-null if the status check could not be performed (e.g. status list unreachable) |
313
+ | `claims` | object | Includes all claims from credentialSubject |
287
314
 
288
315
  ### Option B: OpenID4VP Verification
289
316
  OpenID4VPVerification Component verifies Verifiable Presentations securely using OpenID4VP standards for both cross-device and same-device flows.
@@ -307,42 +334,24 @@ export default function VerifyCrossDevice() {
307
334
  triggerElement={<button>Show QR for Wallet Scan</button>}
308
335
  verifyServiceUrl="https://your-backend.com/v1/verify"
309
336
  clientId="did:example:123456789" // DID example
310
- presentationDefinition={{
311
- id: "custom-verification",
312
- purpose: "We need to verify your identity",
313
- format: {
314
- ldp_vc: {
315
- proof_type: ["Ed25519Signature2020"],
316
- },
317
- },
318
- input_descriptors: [
319
- {
320
- id: "id-card-check",
321
- constraints: {
322
- fields: [
323
- {
324
- path: ["$.type"],
325
- filter: {
326
- type: "object",
327
- pattern: "DriverLicenseCredential",
328
- },
329
- },
330
- ],
331
- },
332
- },
333
- ],
337
+ dcqlQuery={{
338
+ credentials: [{
339
+ id: "id_card",
340
+ format: "ldp_vc",
341
+ meta: { type_values: [["DriverLicenseCredential"]] },
342
+ claims: [{ path: ["name"] }]
343
+ }]
334
344
  }}
335
345
  isSameDeviceFlowEnabled={false} // QR code flow
336
346
  onVPProcessed={(result) => {
337
347
  console.log("VP processed:", result);
338
348
  }}
339
349
  onQrCodeExpired={() => {
340
- console.log(" QR code expired - ask user to retry");
350
+ console.log("QR code expired - ask user to retry");
341
351
  }}
342
352
  onError={(error) => {
343
353
  console.error("Verification error:", error);
344
354
  }}
345
-
346
355
  />
347
356
  );
348
357
  }
@@ -354,28 +363,17 @@ sequenceDiagram
354
363
  participant VerifierBackend as Verifier Backend
355
364
  participant MobileWallet as Wallet (Mobile)
356
365
 
357
- UserBrowser->>VerifierBackend: Start verification(/vp-session-request,response_code_validation_required=false)
358
-
359
- VerifierBackend->>VerifierBackend: Generate transaction_id and request_id
360
- VerifierBackend-->>UserBrowser: Set HttpOnly Cookie (txn_id)
361
- VerifierBackend-->>UserBrowser: Return OpenID4VP request + QR code
362
-
366
+ UserBrowser->>VerifierBackend: POST /v2/vp-session-request
367
+ VerifierBackend-->>UserBrowser: Set HttpOnly Cookie (transaction_id) + authorization request
368
+ UserBrowser->>UserBrowser: SDK generates QR code from authorization request
363
369
  UserBrowser->>MobileWallet: User scans QR code
364
-
365
- MobileWallet->>VerifierBackend: Submit vp_token + presentation_submission
366
-
370
+ MobileWallet->>VerifierBackend: POST /v2/vp-submission/direct-post (vp_token)
367
371
  loop Long Polling
368
372
  UserBrowser->>VerifierBackend: GET /vp-request/{requestId}/status
369
- VerifierBackend-->>UserBrowser: Pending
373
+ VerifierBackend-->>UserBrowser: ACTIVE
370
374
  end
371
-
372
- VerifierBackend-->>UserBrowser: Completed
373
-
374
- UserBrowser->>VerifierBackend: GET /vp-session-results (Cookie txn_id automatically sent)
375
-
376
- VerifierBackend->>VerifierBackend: Resolve txn_id from cookie
377
- VerifierBackend->>VerifierBackend: Fetch transaction state
378
-
375
+ VerifierBackend-->>UserBrowser: VP_SUBMITTED
376
+ UserBrowser->>VerifierBackend: POST /vp-session-results (Cookie auto-sent)
379
377
  VerifierBackend-->>UserBrowser: Verification result
380
378
  ```
381
379
 
@@ -390,30 +388,12 @@ export default function VerifySameDevice() {
390
388
  triggerElement={<button>Verify with Wallet</button>}
391
389
  verifyServiceUrl="https://your-backend.com/v1/verify"
392
390
  clientId="client-12345" // non-DID example
393
- presentationDefinition={{
394
- id: "custom-verification",
395
- purpose: "We need to verify your identity",
396
- format: {
397
- ldp_vc: {
398
- proof_type: ["Ed25519Signature2020"],
399
- },
400
- },
401
- input_descriptors: [
402
- {
403
- id: "id-card-check",
404
- constraints: {
405
- fields: [
406
- {
407
- path: ["$.type"],
408
- filter: {
409
- type: "object",
410
- pattern: "DriverLicenseCredential",
411
- },
412
- },
413
- ],
414
- },
415
- },
416
- ],
391
+ dcqlQuery={{
392
+ credentials: [{
393
+ id: "id_card",
394
+ format: "ldp_vc",
395
+ meta: { type_values: [["DriverLicenseCredential"]] }
396
+ }]
417
397
  }}
418
398
  isSameDeviceFlowEnabled={true} //default value
419
399
  // No webWalletBaseUrl → triggers mobile wallet via deep link
@@ -431,36 +411,22 @@ export default function VerifySameDevice() {
431
411
  ```mermaid
432
412
  sequenceDiagram
433
413
  autonumber
434
- participant UserBrowser as User Browser (Verifier App)
414
+ participant UserBrowser as User Browser
435
415
  participant VerifierBackend as Verifier Backend
436
416
  participant MobileWallet as Mobile Wallet App
437
417
 
438
- UserBrowser->>VerifierBackend: Start verification(/vp-session-request,response_code_validation_required=false)
439
-
440
- VerifierBackend->>VerifierBackend: Generate transaction_id and request_id
441
- VerifierBackend-->>UserBrowser: Set HttpOnly Cookie (txn_id)
442
- VerifierBackend-->>UserBrowser: Return OpenID4VP authorization request
443
-
444
- UserBrowser->>MobileWallet: Open mobile wallet via deep link
445
-
446
- MobileWallet->>VerifierBackend: Submit vp_token + presentation_submission
447
-
448
- Note right of MobileWallet: User manually switches back to browser
449
-
418
+ UserBrowser->>VerifierBackend: POST /v2/vp-session-request
419
+ VerifierBackend-->>UserBrowser: Set HttpOnly Cookie (transaction_id) + authorization request
420
+ UserBrowser->>MobileWallet: Open via deep link
421
+ MobileWallet->>VerifierBackend: POST /v2/vp-submission/direct-post (vp_token)
422
+ Note right of MobileWallet: User switches back to browser
450
423
  loop Long Polling
451
424
  UserBrowser->>VerifierBackend: GET /vp-request/{requestId}/status
452
- VerifierBackend-->>UserBrowser: Pending
425
+ VerifierBackend-->>UserBrowser: ACTIVE
453
426
  end
454
-
455
- VerifierBackend-->>UserBrowser: Completed
456
-
457
- UserBrowser->>VerifierBackend: GET /vp-session-results (Cookie txn_id automatically sent)
458
-
459
- VerifierBackend->>VerifierBackend: Resolve txn_id from cookie
460
- VerifierBackend->>VerifierBackend: Fetch transaction state
461
-
427
+ VerifierBackend-->>UserBrowser: VP_SUBMITTED
428
+ UserBrowser->>VerifierBackend: POST /vp-session-results (Cookie auto-sent)
462
429
  VerifierBackend-->>UserBrowser: Verification result
463
- VerifierBackend-->>UserBrowser: Clear cookie (txn_id)
464
430
  ```
465
431
 
466
432
  #### 3. Same Device Flow with Web Wallet
@@ -474,30 +440,12 @@ export default function VerifySameDevice() {
474
440
  triggerElement={<button>Verify with Wallet</button>}
475
441
  verifyServiceUrl="https://your-backend.com/v1/verify"
476
442
  clientId="did:example:123456789" // DID example
477
- presentationDefinition={{
478
- id: "custom-verification",
479
- purpose: "We need to verify your identity",
480
- format: {
481
- ldp_vc: {
482
- proof_type: ["Ed25519Signature2020"],
483
- },
484
- },
485
- input_descriptors: [
486
- {
487
- id: "id-card-check",
488
- constraints: {
489
- fields: [
490
- {
491
- path: ["$.type"],
492
- filter: {
493
- type: "object",
494
- pattern: "DriverLicenseCredential",
495
- },
496
- },
497
- ],
498
- },
499
- },
500
- ],
443
+ dcqlQuery={{
444
+ credentials: [{
445
+ id: "id_card",
446
+ format: "ldp_vc",
447
+ meta: { type_values: [["DriverLicenseCredential"]] }
448
+ }]
501
449
  }}
502
450
  isSameDeviceFlowEnabled={true} //default value
503
451
  webWalletBaseUrl="https://wallet.example.com" // required to support web-wallets
@@ -519,28 +467,14 @@ sequenceDiagram
519
467
  participant VerifierBackend as Verifier Backend
520
468
  participant WebWallet as Web Wallet
521
469
 
522
- UserBrowser->>VerifierBackend: Start verification\n(/vp-session-request,\nresponse_code_validation_required=true)
523
-
524
- VerifierBackend->>VerifierBackend: Generate transaction_id\nand request_id
525
- VerifierBackend-->>UserBrowser: Set HttpOnly Cookie (txn_id)
526
- VerifierBackend-->>UserBrowser: Return OpenID4VP authorization request
527
-
470
+ UserBrowser->>VerifierBackend: POST /v2/vp-session-request (responseCodeValidationRequired=true)
471
+ VerifierBackend-->>UserBrowser: Set HttpOnly Cookie (transaction_id) + authorization request
528
472
  UserBrowser->>WebWallet: Open Web Wallet
529
-
530
- WebWallet->>VerifierBackend: Submit vp_token + presentation_submission
531
- VerifierBackend-->>WebWallet: Return response_code
532
-
533
- WebWallet-->>UserBrowser: Redirect to redirect_uri
534
-
535
- UserBrowser->>UserBrowser: Extract response_code
536
-
537
- UserBrowser->>VerifierBackend: GET /vp-session-results?response_code=xyz\n(Cookie txn_id automatically sent)
538
-
539
- VerifierBackend->>VerifierBackend: Validate response_code + txn_id
540
- VerifierBackend->>VerifierBackend: Fetch transaction state
541
-
473
+ WebWallet->>VerifierBackend: POST /v2/vp-submission/direct-post (vp_token)
474
+ VerifierBackend-->>WebWallet: response_code
475
+ WebWallet-->>UserBrowser: Redirect with response_code
476
+ UserBrowser->>VerifierBackend: POST /vp-session-results?response_code=... (Cookie auto-sent)
542
477
  VerifierBackend-->>UserBrowser: Verification result
543
- VerifierBackend-->>UserBrowser: Clear cookie (txn_id)
544
478
  ```
545
479
 
546
480
  > **NOTE**
@@ -559,31 +493,13 @@ export default function VerifyServerToServer() {
559
493
  triggerElement={<button>Start Verification</button>}
560
494
  verifyServiceUrl="https://your-backend.com/v1/verify"
561
495
  clientId="did:example:123456789" // DID example
562
- presentationDefinition={{
563
- id: "custom-verification",
564
- purpose: "We need to verify your identity",
565
- format: {
566
- ldp_vc: {
567
- proof_type: ["Ed25519Signature2020"],
568
- },
569
- },
570
- input_descriptors: [
571
- {
572
- id: "id-card-check",
573
- constraints: {
574
- fields: [
575
- {
576
- path: ["$.type"],
577
- filter: {
578
- type: "object",
579
- pattern: "DriverLicenseCredential",
580
- },
581
- },
582
- ],
583
- },
584
- },
585
- ],
586
- }}
496
+ dcqlQuery={{
497
+ credentials: [{
498
+ id: "id_card",
499
+ format: "ldp_vc",
500
+ meta: { type_values: [["DriverLicenseCredential"]] }
501
+ }]
502
+ }}
587
503
  isSameDeviceFlowEnabled={false}
588
504
  onVPReceived={(transactionId) => {
589
505
  //using the transactionId one can securely fetch the result from service
@@ -604,18 +520,31 @@ export default function VerifyServerToServer() {
604
520
 
605
521
  Once VP Verification is complete, the response depends on the `summariseResults` attribute (default = true)
606
522
 
607
- If `summariseResults = true`, the response will be:
523
+ If `summariseResults = true`, the response will be an array with one element per credential. Each element's `verificationResponse` contains the full `vcResults` list and the overall `vpResultStatus`:
608
524
 
609
525
  ```javascript
610
- {
611
- "vcResults": [
612
- {
613
- "vc": { /* verified credential data */ },
614
- "vcStatus": "SUCCESS" // or "INVALID", "EXPIRED","REVOKED"
615
- }
616
- ],
617
- "vpResultStatus": "SUCCESS" // or "INVALID" Overall verification status
526
+ [
527
+ {
528
+ "vc": { /* credential-1 data */ },
529
+ "verificationResponse": {
530
+ "vcResults": [
531
+ { "vc": { /* credential-1 data */ }, "vcStatus": "SUCCESS" }, // or "INVALID", "EXPIRED", "REVOKED"
532
+ { "vc": { /* credential-2 data */ }, "vcStatus": "SUCCESS" }
533
+ ],
534
+ "vpResultStatus": "SUCCESS" // or "INVALID" — overall verification status
535
+ }
536
+ },
537
+ {
538
+ "vc": { /* credential-2 data */ },
539
+ "verificationResponse": {
540
+ "vcResults": [
541
+ { "vc": { /* credential-1 data */ }, "vcStatus": "SUCCESS" },
542
+ { "vc": { /* credential-2 data */ }, "vcStatus": "SUCCESS" }
543
+ ],
544
+ "vpResultStatus": "SUCCESS"
618
545
  }
546
+ }
547
+ ]
619
548
  ```
620
549
 
621
550
  If `summariseResults = false`, the response will be:
@@ -623,83 +552,114 @@ If `summariseResults = false`, the response will be:
623
552
  ```javascript
624
553
  {
625
554
  "transactionId": "txn_11",
626
- "allChecksSuccessful": true,
627
- "credentialResults": [
555
+ "allChecksSuccessful": true,
556
+ "credentialResults": [
628
557
  {
629
558
  "verifiableCredential": "{...}",
630
559
  "allChecksSuccessful": true,
631
560
  "holderProofCheck": { "valid": true, "error": null },
632
561
  "schemaAndSignatureCheck": { "valid": true, "error": null },
633
562
  "expiryCheck": { "valid": true },
634
- "statusChecks": [
563
+ "statusCheck": [
635
564
  { "purpose": "revocation", "valid": true, "error": null }
636
565
  ],
637
- "claims": {..}
566
+ "claims": {...}
638
567
  }
639
568
  ]
640
- }
569
+ }
641
570
  ```
642
571
 
643
572
  #### Response Fields Summary
644
573
 
645
574
  | Property | Type | Description |
646
575
  |---------------------------|---------|-----------------------------------------------------------|
647
- | `allChecksSuccessful` | boolean | Final aggregated validation flag |
648
- | `verifiableCredential` | string | The VC which needs to be verified |
649
- | `holderProofCheck` | object | Validates if presenter owns the credential |
650
- | `schemaAndSignatureCheck` | object | Validates schema and signature check |
651
- | `expiryCheck` | object | If false, the credential is EXPIRED |
652
- | `statusChecks` | array | Contains revocation and other status validations |
653
- | `statusChecks.error` | object | If present, throws an error instead of returning a status |
654
- | `statusChecks.purpose` | string | Identifies purpose (e.g., "revocation") |
655
- | `statusChecks.valid` | boolean | If false for revocation → credential is revoked |
656
- | `claims` | object | Includes all claims from credentialSubject |
657
-
658
- ### Presentation Definition:
576
+ | `allChecksSuccessful` | boolean | Final aggregated validation flag |
577
+ | `verifiableCredential` | string | The VC that has been verified |
578
+ | `holderProofCheck` | object | Holder binding result. `null` when `require_cryptographic_holder_binding=false` |
579
+ | `holderProofCheck.valid` | boolean | If false, presenter does not own the credential |
580
+ | `holderProofCheck.error` | object | Non-null if the check could not be performed |
581
+ | `schemaAndSignatureCheck` | object | Schema and signature validation result |
582
+ | `schemaAndSignatureCheck.valid`| boolean | If false, credential signature or schema is invalid |
583
+ | `schemaAndSignatureCheck.error`| object | Non-null if the check could not be performed |
584
+ | `expiryCheck` | object | Expiry validation result |
585
+ | `expiryCheck.valid` | boolean | If false, the credential is EXPIRED |
586
+ | `statusCheck` | array | Contains revocation and other status validations |
587
+ | `statusCheck[].purpose` | string | Identifies purpose (e.g., "revocation") |
588
+ | `statusCheck[].valid` | boolean | If false for revocation and `error` is null → credential is revoked |
589
+ | `statusCheck[].error` | object | Non-null if the status check could not be performed (e.g. status list unreachable) |
590
+ | `claims` | object | Includes all claims from credentialSubject |
591
+
592
+ ### DCQL Query:
593
+
594
+ The `dcqlQuery` prop describes which credentials to request from the wallet, following the [DCQL (Digital Credentials Query Language)](https://openid.net/specs/openid-4-verifiable-presentations-1_0.html) format.
595
+
596
+ > **Unsupported:** `trusted_authorities` is not currently supported. DCQL queries containing `trusted_authorities` will be rejected with `UNKNOWN_FIELD`.
597
+
598
+ **Minimal example — request a single ldp_vc:**
659
599
 
660
- #### Define What to Verify:
600
+ ```javascript
601
+ dcqlQuery={{
602
+ credentials: [{
603
+ id: "id_card",
604
+ format: "ldp_vc",
605
+ meta: { type_values: [["DriverLicenseCredential"]] }
606
+ }]
607
+ }}
608
+ ```
661
609
 
662
- **Option 1: Use a predefined template ID**
610
+ **Request specific claims:**
663
611
 
664
612
  ```javascript
665
- presentationDefinitionId = "drivers-license-check";
613
+ dcqlQuery={{
614
+ credentials: [{
615
+ id: "id_card",
616
+ format: "dc+sd-jwt",
617
+ meta: { vct_values: ["DriverLicenseCredential"] },
618
+ claims: [
619
+ { path: ["given_name"] },
620
+ { path: ["birth_date"] }
621
+ ]
622
+ }]
623
+ }}
666
624
  ```
667
625
 
668
- **Option 2: Define Presentation Definition**
626
+ **Request multiple credential types (OR logic via credential_sets):**
669
627
 
670
628
  ```javascript
671
- presentationDefinition={{
672
- id: "custom-verification",
673
- purpose: "We need to verify your identity",
674
- format: {
675
- ldp_vc: {
676
- proof_type: ["Ed25519Signature2020"],
677
- },
678
- },
679
- input_descriptors: [
680
- {
681
- id: "id-card-check",
682
- constraints: {
683
- fields: [
684
- {
685
- path: ["$.type"],
686
- filter: {
687
- type: "object",
688
- pattern: "DriverLicenseCredential",
689
- },
690
- },
691
- ],
692
- },
693
- },
629
+ dcqlQuery={{
630
+ credentials: [
631
+ { id: "mdl", format: "dc+sd-jwt", meta: { vct_values: ["DriverLicense"] } },
632
+ { id: "pid", format: "ldp_vc", meta: { type_values: [["PersonalID"]] } }
694
633
  ],
634
+ credential_sets: [
635
+ { options: [["mdl"], ["pid"]] } // wallet can satisfy with either
636
+ ]
637
+ }}
638
+ ```
639
+
640
+ **`require_cryptographic_holder_binding` — holder binding control:**
641
+
642
+ Each credential entry in `dcqlQuery` supports a `require_cryptographic_holder_binding` flag (default `true`) that controls whether the wallet must prove it cryptographically owns the credential:
643
+
644
+ | Value | Behavior | `holderProofCheck` in result |
645
+ |---|---|---|
646
+ | `true` (default) | Wallet must wrap the VC in a signed VP. The verifier checks that the presenter owns the credential. | Populated — `valid: true` if holder proof passes |
647
+ | `false` | Wallet may submit the VC without a VP wrapper (bare VC). No holder binding check is performed. | `null` |
648
+
649
+ Format-specific behavior:
650
+ - **`ldp_vc`**: when `true`, wallet submits a JSON-LD VP with a `proof` field; when `false`, bare VC is accepted.
651
+ - **`dc+sd-jwt` / `vc+sd-jwt`**: when `true`, a KB-JWT (Key Binding JWT) is required, containing `aud`, `nonce`, `iat`, and `sd_hash`; when `false`, KB-JWT is skipped.
652
+
653
+ ```javascript
654
+ dcqlQuery={{
655
+ credentials: [{
656
+ id: "id_card",
657
+ format: "ldp_vc",
658
+ meta: { type_values: [["DriverLicenseCredential"]] },
659
+ require_cryptographic_holder_binding: false // accept bare VC, skip holder check
660
+ }]
695
661
  }}
696
662
  ```
697
- > **NOTE**
698
- >
699
- > Only one of presentationDefinitionId or presentationDefinition should be provided at a time.
700
- > It is recommended to use:
701
- >- presentationDefinitionId when leveraging predefined templates.
702
- >- presentationDefinition when custom verification requirements are needed.
703
663
 
704
664
  ## 🎛️ Component Options Reference
705
665
 
@@ -712,7 +672,6 @@ presentationDefinition={{
712
672
  | `triggerElement` | React element | ❌ | Custom button/element to start verification |
713
673
  | `transactionId` | string | ❌ | Optional client-side tracking ID |
714
674
  | `clientId` | string | ✅ | Client identifier (DID or Non-DID) |
715
- | `acceptVPWithoutHolderProof` | boolean | ❌ | Allow unsigned Verifiable Presentations |
716
675
  | `summariseResults` | boolean | ❌ | Decides format of SDK Response |
717
676
 
718
677
  ### QRCodeVerification Specific
@@ -730,17 +689,16 @@ presentationDefinition={{
730
689
 
731
690
  ### OpenID4VPVerification Specific
732
691
 
733
- | Property | Type | Default | Description |
734
- |--------------------------| -------- |----------------|-------------------------------------------|
735
- | `protocol` | string | "openid4vp://" | Protocol for QR codes (optional) |
736
- | `presentationDefinitionId` | string | - | Predefined verification template |
737
- | `presentationDefinition` | object | - | Custom verification rules |
738
- | `onVPProcessed` | function | - | Get full results immediately |
739
- | `onVPReceived` | function | - | Get transaction ID only |
740
- | `onQrCodeExpired` | function | - | Handle QR code expiration |
692
+ | Property | Type | Default | Description |
693
+ |---------------------------| -------- |----------------|-------------------------------------------|
694
+ | `dcqlQuery` | object | - | DCQL query describing requested credentials (required) |
695
+ | `protocol` | string | "openid4vp://" | Protocol for QR codes (optional) |
696
+ | `onVPProcessed` | function | - | Get full results immediately |
697
+ | `onVPReceived` | function | - | Get transaction ID only |
698
+ | `onQrCodeExpired` | function | - | Handle QR code expiration |
741
699
  | `isSameDeviceFlowEnabled` | boolean | true | Enable same-device flow (optional) |
742
- | `qrCodeStyles` | object | - | Customize QR code appearance |
743
- | `vpVerificationRequest` | object | - | contains request body for VP Verification |
700
+ | `qrCodeStyles` | object | - | Customize QR code appearance |
701
+ | `vpVerificationRequest` | object | - | contains request body for VP Verification |
744
702
 
745
703
  ## ⚠️ Important Limitations
746
704
 
@@ -228,7 +228,7 @@ export interface CredentialResult {
228
228
  expiryCheck?: {
229
229
  valid: boolean;
230
230
  };
231
- statusChecks?: {
231
+ statusCheck?: {
232
232
  purpose: string;
233
233
  valid: boolean;
234
234
  error: any;
@@ -146,7 +146,7 @@ export interface CredentialResult {
146
146
  expiryCheck?: {
147
147
  valid: boolean;
148
148
  };
149
- statusChecks?: {
149
+ statusCheck?: {
150
150
  purpose: string;
151
151
  valid: boolean;
152
152
  error: any;