@pagopa/io-react-native-wallet 1.4.0 → 1.6.0
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/lib/commonjs/credential/issuance/06-obtain-credential.js +1 -5
- package/lib/commonjs/credential/issuance/06-obtain-credential.js.map +1 -1
- package/lib/commonjs/credential/issuance/07-verify-and-parse-credential.js +33 -21
- package/lib/commonjs/credential/issuance/07-verify-and-parse-credential.js.map +1 -1
- package/lib/commonjs/credential/presentation/07-evaluate-input-descriptor.js +318 -24
- package/lib/commonjs/credential/presentation/07-evaluate-input-descriptor.js.map +1 -1
- package/lib/commonjs/credential/presentation/08-send-authorization-response.js +47 -83
- package/lib/commonjs/credential/presentation/08-send-authorization-response.js.map +1 -1
- package/lib/commonjs/credential/presentation/errors.js +18 -1
- package/lib/commonjs/credential/presentation/errors.js.map +1 -1
- package/lib/commonjs/credential/presentation/index.js +8 -2
- package/lib/commonjs/credential/presentation/index.js.map +1 -1
- package/lib/commonjs/credential/presentation/types.js +6 -2
- package/lib/commonjs/credential/presentation/types.js.map +1 -1
- package/lib/commonjs/entity/trust/chain.js.map +1 -1
- package/lib/commonjs/mdoc/index.js +45 -13
- package/lib/commonjs/mdoc/index.js.map +1 -1
- package/lib/commonjs/sd-jwt/index.js +41 -1
- package/lib/commonjs/sd-jwt/index.js.map +1 -1
- package/lib/commonjs/utils/crypto.js +70 -4
- package/lib/commonjs/utils/crypto.js.map +1 -1
- package/lib/commonjs/utils/string.js +6 -7
- package/lib/commonjs/utils/string.js.map +1 -1
- package/lib/module/credential/issuance/06-obtain-credential.js +1 -5
- package/lib/module/credential/issuance/06-obtain-credential.js.map +1 -1
- package/lib/module/credential/issuance/07-verify-and-parse-credential.js +33 -21
- package/lib/module/credential/issuance/07-verify-and-parse-credential.js.map +1 -1
- package/lib/module/credential/presentation/07-evaluate-input-descriptor.js +311 -23
- package/lib/module/credential/presentation/07-evaluate-input-descriptor.js.map +1 -1
- package/lib/module/credential/presentation/08-send-authorization-response.js +46 -81
- package/lib/module/credential/presentation/08-send-authorization-response.js.map +1 -1
- package/lib/module/credential/presentation/errors.js +16 -0
- package/lib/module/credential/presentation/errors.js.map +1 -1
- package/lib/module/credential/presentation/index.js +2 -2
- package/lib/module/credential/presentation/index.js.map +1 -1
- package/lib/module/credential/presentation/types.js +6 -2
- package/lib/module/credential/presentation/types.js.map +1 -1
- package/lib/module/entity/trust/chain.js.map +1 -1
- package/lib/module/mdoc/index.js +43 -12
- package/lib/module/mdoc/index.js.map +1 -1
- package/lib/module/sd-jwt/index.js +40 -1
- package/lib/module/sd-jwt/index.js.map +1 -1
- package/lib/module/utils/crypto.js +67 -2
- package/lib/module/utils/crypto.js.map +1 -1
- package/lib/module/utils/string.js +4 -6
- package/lib/module/utils/string.js.map +1 -1
- package/lib/typescript/credential/issuance/06-obtain-credential.d.ts.map +1 -1
- package/lib/typescript/credential/issuance/07-verify-and-parse-credential.d.ts +1 -1
- package/lib/typescript/credential/issuance/07-verify-and-parse-credential.d.ts.map +1 -1
- package/lib/typescript/credential/presentation/07-evaluate-input-descriptor.d.ts +106 -9
- package/lib/typescript/credential/presentation/07-evaluate-input-descriptor.d.ts.map +1 -1
- package/lib/typescript/credential/presentation/08-send-authorization-response.d.ts +4 -33
- package/lib/typescript/credential/presentation/08-send-authorization-response.d.ts.map +1 -1
- package/lib/typescript/credential/presentation/errors.d.ts +11 -0
- package/lib/typescript/credential/presentation/errors.d.ts.map +1 -1
- package/lib/typescript/credential/presentation/index.d.ts +3 -3
- package/lib/typescript/credential/presentation/index.d.ts.map +1 -1
- package/lib/typescript/credential/presentation/types.d.ts +18 -6
- package/lib/typescript/credential/presentation/types.d.ts.map +1 -1
- package/lib/typescript/entity/trust/chain.d.ts.map +1 -1
- package/lib/typescript/mdoc/index.d.ts +6 -2
- package/lib/typescript/mdoc/index.d.ts.map +1 -1
- package/lib/typescript/sd-jwt/index.d.ts +19 -0
- package/lib/typescript/sd-jwt/index.d.ts.map +1 -1
- package/lib/typescript/utils/crypto.d.ts +8 -0
- package/lib/typescript/utils/crypto.d.ts.map +1 -1
- package/lib/typescript/utils/errors.d.ts.map +1 -1
- package/lib/typescript/utils/misc.d.ts.map +1 -1
- package/lib/typescript/utils/string.d.ts +3 -3
- package/lib/typescript/utils/string.d.ts.map +1 -1
- package/package.json +16 -14
- package/src/credential/issuance/06-obtain-credential.ts +1 -7
- package/src/credential/issuance/07-verify-and-parse-credential.ts +37 -16
- package/src/credential/presentation/07-evaluate-input-descriptor.ts +459 -49
- package/src/credential/presentation/08-send-authorization-response.ts +57 -101
- package/src/credential/presentation/errors.ts +16 -0
- package/src/credential/presentation/index.ts +8 -4
- package/src/credential/presentation/types.ts +16 -3
- package/src/entity/trust/chain.ts +14 -10
- package/src/mdoc/index.ts +72 -15
- package/src/sd-jwt/index.ts +49 -1
- package/src/utils/crypto.ts +61 -2
- package/src/utils/errors.ts +2 -2
- package/src/utils/misc.ts +2 -2
- package/src/utils/string.ts +4 -6
@@ -1,10 +1,21 @@
|
|
1
|
+
import { decode, prepareVpToken } from "../../sd-jwt";
|
2
|
+
import { createCryptoContextFor } from "../../utils/crypto";
|
1
3
|
import { JSONPath } from "jsonpath-plus";
|
2
|
-
import { MissingDataError } from "./errors";
|
4
|
+
import { MissingDataError, CredentialNotFoundError } from "./errors";
|
3
5
|
import Ajv from "ajv";
|
6
|
+
import { CBOR } from "@pagopa/io-react-native-cbor";
|
7
|
+
import { prepareVpTokenMdoc } from "../../mdoc";
|
8
|
+
import { generateRandomAlphaNumericString } from "../../utils/misc";
|
4
9
|
const ajv = new Ajv({
|
5
10
|
allErrors: true
|
6
11
|
});
|
7
|
-
const
|
12
|
+
export const disclosureWithEncodedToEvaluatedDisclosure = disclosure => {
|
13
|
+
const [, claimName, claimValue] = disclosure.decoded;
|
14
|
+
return {
|
15
|
+
name: claimName,
|
16
|
+
value: claimValue
|
17
|
+
};
|
18
|
+
};
|
8
19
|
/**
|
9
20
|
* Transforms an array of DisclosureWithEncoded objects into a key-value map.
|
10
21
|
* @param disclosures - An array of DisclosureWithEncoded, each containing a decoded property with [?, claimName, claimValue].
|
@@ -21,6 +32,22 @@ const mapDisclosuresToObject = disclosures => {
|
|
21
32
|
}, {});
|
22
33
|
};
|
23
34
|
|
35
|
+
/**
|
36
|
+
* Transforms the issuer's namespaces from a CBOR structure into a plain JavaScript object.
|
37
|
+
*
|
38
|
+
* @param namespaces - The CBOR-based namespaces object where each key corresponds to a namespace,
|
39
|
+
* and each value is an array of elements containing identifiers and values.
|
40
|
+
* @returns A record (plain object) where each key is a namespace, and its value is another object
|
41
|
+
* mapping element identifiers to their corresponding element values.
|
42
|
+
*/
|
43
|
+
const mapNamespacesToObject = namespaces => {
|
44
|
+
return Object.entries(namespaces).reduce((obj, _ref2) => {
|
45
|
+
let [namespace, elements] = _ref2;
|
46
|
+
obj[namespace] = Object.fromEntries(elements.map(element => [element.elementIdentifier, element.elementValue]));
|
47
|
+
return obj;
|
48
|
+
}, {});
|
49
|
+
};
|
50
|
+
|
24
51
|
/**
|
25
52
|
* Finds a claim within the payload based on provided JSONPath expressions.
|
26
53
|
* @param paths - An array of JSONPath expressions to search for in the payload.
|
@@ -68,10 +95,91 @@ const extractClaimName = path => {
|
|
68
95
|
// match[2] corresponds to the second capture group (\w+) inside [""] or ['']
|
69
96
|
return match[1] || match[2];
|
70
97
|
}
|
98
|
+
throw new Error(`Invalid input format: "${path}". Expected formats are "$.propertyName", "$['propertyName']", or '$["propertyName"]'.`);
|
99
|
+
};
|
71
100
|
|
72
|
-
|
101
|
+
/**
|
102
|
+
* Extracts the namespace and claim name from a path in the following format:
|
103
|
+
* $['nameSpace']['propertyName']
|
104
|
+
*
|
105
|
+
* @param path - The path string containing the claim reference.
|
106
|
+
* @returns An object with the extracted namespace and claim name.
|
107
|
+
* @throws An error if the input format is invalid.
|
108
|
+
*/
|
109
|
+
const extractNamespaceAndClaimName = path => {
|
110
|
+
const regex = /^\$\[(?:'|")([^'"\]]+)(?:'|")\]\[(?:'|")([^'"\]]+)(?:'|")\]$/;
|
111
|
+
const match = path.match(regex);
|
112
|
+
if (match) {
|
113
|
+
return {
|
114
|
+
nameSpace: match[1],
|
115
|
+
propertyName: match[2]
|
116
|
+
};
|
117
|
+
}
|
118
|
+
throw new Error(`Invalid input format: "${path}". Expected format is "$['nameSpace']['propertyName']".`);
|
119
|
+
};
|
120
|
+
/**
|
121
|
+
* Evaluates the input descriptor for an mDoc by verifying that the issuerSigned claims meet
|
122
|
+
* the constraints defined in the input descriptor. It categorizes disclosures as either required
|
123
|
+
* or optional based on the field definitions.
|
124
|
+
*
|
125
|
+
* @param inputDescriptor - Contains constraints and field definitions specifying required/optional claims.
|
126
|
+
* @param issuerSigned - Contains the issuerSigned with namespaces and their associated claims.
|
127
|
+
* @returns An object with two arrays: one for required disclosures and one for optional disclosures.
|
128
|
+
* @throws MissingDataError - If a required field is missing or if a claim fails JSON Schema validation.
|
129
|
+
*/
|
130
|
+
export const evaluateInputDescriptorForMdoc = (inputDescriptor, issuerSigned) => {
|
131
|
+
var _inputDescriptor$cons;
|
132
|
+
if (!(inputDescriptor !== null && inputDescriptor !== void 0 && (_inputDescriptor$cons = inputDescriptor.constraints) !== null && _inputDescriptor$cons !== void 0 && _inputDescriptor$cons.fields)) {
|
133
|
+
// No validation, no field are required
|
134
|
+
return {
|
135
|
+
requiredDisclosures: [],
|
136
|
+
optionalDisclosures: []
|
137
|
+
};
|
138
|
+
}
|
139
|
+
const requiredDisclosures = [];
|
140
|
+
const optionalDisclosures = [];
|
73
141
|
|
74
|
-
|
142
|
+
// Convert issuer's namespaces into an object for easier lookup of claim values.
|
143
|
+
const namespacesAsPayload = mapNamespacesToObject(issuerSigned.nameSpaces);
|
144
|
+
const allFieldsValid = inputDescriptor.constraints.fields.every(field => {
|
145
|
+
const [matchedPath, matchedValue] = findMatchedClaim(field.path, namespacesAsPayload);
|
146
|
+
|
147
|
+
// If no matching claim is found, the field is valid only if it's marked as optional.
|
148
|
+
if (matchedValue === undefined || !matchedPath) {
|
149
|
+
return field === null || field === void 0 ? void 0 : field.optional;
|
150
|
+
} else {
|
151
|
+
// Extract the namespace and property name from the matched path.
|
152
|
+
const {
|
153
|
+
nameSpace,
|
154
|
+
propertyName
|
155
|
+
} = extractNamespaceAndClaimName(matchedPath);
|
156
|
+
if (nameSpace && propertyName) {
|
157
|
+
(field !== null && field !== void 0 && field.optional ? optionalDisclosures : requiredDisclosures).push({
|
158
|
+
namespace: nameSpace,
|
159
|
+
name: propertyName,
|
160
|
+
value: matchedValue
|
161
|
+
});
|
162
|
+
}
|
163
|
+
}
|
164
|
+
if (field.filter) {
|
165
|
+
try {
|
166
|
+
const validateSchema = ajv.compile(field.filter);
|
167
|
+
if (!validateSchema(matchedValue)) {
|
168
|
+
throw new MissingDataError(`Claim value "${matchedValue}" for path "${matchedPath}" does not match the provided JSON Schema.`);
|
169
|
+
}
|
170
|
+
} catch (error) {
|
171
|
+
return false;
|
172
|
+
}
|
173
|
+
}
|
174
|
+
return true;
|
175
|
+
});
|
176
|
+
if (!allFieldsValid) {
|
177
|
+
throw new MissingDataError("Credential validation failed: Required fields are missing or do not match the input descriptor.");
|
178
|
+
}
|
179
|
+
return {
|
180
|
+
requiredDisclosures,
|
181
|
+
optionalDisclosures
|
182
|
+
};
|
75
183
|
};
|
76
184
|
|
77
185
|
/**
|
@@ -82,30 +190,27 @@ const extractClaimName = path => {
|
|
82
190
|
* - Validates whether required fields are present (unless marked optional)
|
83
191
|
* and match any specified JSONPath.
|
84
192
|
* - If a field includes a JSON Schema filter, validates the claim value against that schema.
|
85
|
-
* - Enforces `limit_disclosure` rules by returning only disclosures, required and optional, matching the specified fields
|
86
|
-
* if set to "required". Otherwise also return the array unrequestedDisclosures with disclosures which can be passed for a particular use case.
|
87
193
|
* - Throws an error if a required field is invalid or missing.
|
88
194
|
*
|
89
195
|
* @param inputDescriptor - Describes constraints (fields, filters, etc.) that must be satisfied.
|
90
196
|
* @param payloadCredential - The credential payload to check against.
|
91
197
|
* @param disclosures - An array of DisclosureWithEncoded objects representing selective disclosures.
|
92
|
-
* @returns
|
198
|
+
* @returns An object with two arrays: one for required disclosures and one for optional disclosures.
|
93
199
|
* @throws Will throw an error if any required constraint fails or if JSONPath lookups are invalid.
|
94
200
|
*/
|
95
201
|
export const evaluateInputDescriptorForSdJwt4VC = (inputDescriptor, payloadCredential, disclosures) => {
|
96
|
-
var _inputDescriptor$
|
97
|
-
if (!(inputDescriptor !== null && inputDescriptor !== void 0 && (_inputDescriptor$
|
202
|
+
var _inputDescriptor$cons2;
|
203
|
+
if (!(inputDescriptor !== null && inputDescriptor !== void 0 && (_inputDescriptor$cons2 = inputDescriptor.constraints) !== null && _inputDescriptor$cons2 !== void 0 && _inputDescriptor$cons2.fields)) {
|
98
204
|
// No validation, all field are optional
|
99
205
|
return {
|
100
206
|
requiredDisclosures: [],
|
101
|
-
optionalDisclosures: []
|
102
|
-
unrequestedDisclosures: disclosures
|
207
|
+
optionalDisclosures: []
|
103
208
|
};
|
104
209
|
}
|
105
|
-
const
|
106
|
-
const
|
210
|
+
const requiredDisclosures = [];
|
211
|
+
const optionalDisclosures = [];
|
107
212
|
|
108
|
-
// Transform disclosures
|
213
|
+
// Transform disclosures into an object for easier lookup of claim values.
|
109
214
|
const disclosuresAsPayload = mapDisclosuresToObject(disclosures);
|
110
215
|
|
111
216
|
// For each field, we need at least one matching path
|
@@ -125,7 +230,10 @@ export const evaluateInputDescriptorForSdJwt4VC = (inputDescriptor, payloadCrede
|
|
125
230
|
// if match a disclouse we save which is required or optional
|
126
231
|
const claimName = extractClaimName(matchedPath);
|
127
232
|
if (claimName) {
|
128
|
-
(field !== null && field !== void 0 && field.optional ?
|
233
|
+
(field !== null && field !== void 0 && field.optional ? optionalDisclosures : requiredDisclosures).push({
|
234
|
+
value: matchedValue,
|
235
|
+
name: claimName
|
236
|
+
});
|
129
237
|
}
|
130
238
|
}
|
131
239
|
|
@@ -149,17 +257,197 @@ export const evaluateInputDescriptorForSdJwt4VC = (inputDescriptor, payloadCrede
|
|
149
257
|
if (!allFieldsValid) {
|
150
258
|
throw new MissingDataError("Credential validation failed: Required fields are missing or do not match the input descriptor.");
|
151
259
|
}
|
260
|
+
return {
|
261
|
+
requiredDisclosures,
|
262
|
+
optionalDisclosures
|
263
|
+
};
|
264
|
+
};
|
265
|
+
|
266
|
+
/**
|
267
|
+
* Finds the first credential that satisfies the input descriptor constraints.
|
268
|
+
* @param inputDescriptor The input descriptor to evaluate.
|
269
|
+
* @param decodedSdJwtCredentials An array of decoded SD-JWT credentials.
|
270
|
+
* @returns An object containing the matched evaluation, keyTag, and credential.
|
271
|
+
*/
|
272
|
+
export const findCredentialSdJwt = (inputDescriptor, decodedSdJwtCredentials) => {
|
273
|
+
for (const {
|
274
|
+
keyTag,
|
275
|
+
credential,
|
276
|
+
sdJwt,
|
277
|
+
disclosures
|
278
|
+
} of decodedSdJwtCredentials) {
|
279
|
+
try {
|
280
|
+
const evaluatedDisclosure = evaluateInputDescriptorForSdJwt4VC(inputDescriptor, sdJwt.payload, disclosures);
|
281
|
+
return {
|
282
|
+
matchedEvaluation: evaluatedDisclosure,
|
283
|
+
matchedKeyTag: keyTag,
|
284
|
+
matchedCredential: credential
|
285
|
+
};
|
286
|
+
} catch {
|
287
|
+
// skip to next credential
|
288
|
+
continue;
|
289
|
+
}
|
290
|
+
}
|
291
|
+
throw new CredentialNotFoundError("None of the vc+sd-jwt credentials satisfy the requirements.");
|
292
|
+
};
|
293
|
+
|
294
|
+
/**
|
295
|
+
* Finds the first credential that satisfies the input descriptor constraints.
|
296
|
+
* @param inputDescriptor The input descriptor to evaluate.
|
297
|
+
* @param decodedMdocCredentials An array of decoded MDOC credentials.
|
298
|
+
* @returns An object containing the matched evaluation, keyTag, and credential.
|
299
|
+
*/
|
300
|
+
export const findCredentialMDoc = (inputDescriptor, decodedMDocCredentials) => {
|
301
|
+
for (const {
|
302
|
+
keyTag,
|
303
|
+
credential,
|
304
|
+
issuerSigned
|
305
|
+
} of decodedMDocCredentials) {
|
306
|
+
try {
|
307
|
+
const evaluatedDisclosure = evaluateInputDescriptorForMdoc(inputDescriptor, issuerSigned);
|
308
|
+
return {
|
309
|
+
matchedEvaluation: evaluatedDisclosure,
|
310
|
+
matchedKeyTag: keyTag,
|
311
|
+
matchedCredential: credential
|
312
|
+
};
|
313
|
+
} catch {
|
314
|
+
// skip to next credential
|
315
|
+
continue;
|
316
|
+
}
|
317
|
+
}
|
318
|
+
throw new CredentialNotFoundError("None of the mso_mdoc credentials satisfy the requirements.");
|
319
|
+
};
|
320
|
+
|
321
|
+
/**
|
322
|
+
* Evaluates multiple input descriptors against provided SD-JWT and MDOC credentials.
|
323
|
+
*
|
324
|
+
* For each input descriptor, this function:
|
325
|
+
* - Checks the credential format.
|
326
|
+
* - Decodes the credential.
|
327
|
+
* - Evaluates the descriptor using the associated disclosures.
|
328
|
+
*
|
329
|
+
* @param inputDescriptors - An array of input descriptors.
|
330
|
+
* @param credentialsSdJwt - An array of tuples containing keyTag and SD-JWT credential.
|
331
|
+
* @param credentialsMdoc - An array of tuples containing keyTag and MDOC credential.
|
332
|
+
* @returns An array of objects, each containing the evaluated disclosures,
|
333
|
+
* the input descriptor, the credential, and the keyTag.
|
334
|
+
* @throws {CredentialNotFoundError} When the credential format is unsupported.
|
335
|
+
*/
|
336
|
+
export const evaluateInputDescriptors = async (inputDescriptors, credentialsSdJwt, credentialsMdoc) => {
|
337
|
+
// We need decode SD-JWT credentials for evaluation
|
338
|
+
const decodedSdJwtCredentials = (credentialsSdJwt === null || credentialsSdJwt === void 0 ? void 0 : credentialsSdJwt.map(_ref3 => {
|
339
|
+
let [keyTag, credential] = _ref3;
|
340
|
+
const {
|
341
|
+
sdJwt,
|
342
|
+
disclosures
|
343
|
+
} = decode(credential);
|
344
|
+
return {
|
345
|
+
keyTag,
|
346
|
+
credential,
|
347
|
+
sdJwt,
|
348
|
+
disclosures
|
349
|
+
};
|
350
|
+
})) || [];
|
152
351
|
|
153
|
-
//
|
352
|
+
// We need decode Mdoc credentials for evaluation
|
353
|
+
const decodedMdocCredentials = (await Promise.all(credentialsMdoc === null || credentialsMdoc === void 0 ? void 0 : credentialsMdoc.map(async _ref4 => {
|
354
|
+
let [keyTag, credential] = _ref4;
|
355
|
+
const issuerSigned = await CBOR.decodeIssuerSigned(credential);
|
356
|
+
if (!issuerSigned) {
|
357
|
+
throw new CredentialNotFoundError("mso_mdoc credential is not present.");
|
358
|
+
}
|
359
|
+
return {
|
360
|
+
keyTag,
|
361
|
+
credential,
|
362
|
+
issuerSigned
|
363
|
+
};
|
364
|
+
}))) || [];
|
365
|
+
const results = Promise.all(inputDescriptors.map(async descriptor => {
|
366
|
+
var _descriptor$format, _descriptor$format2;
|
367
|
+
if ((_descriptor$format = descriptor.format) !== null && _descriptor$format !== void 0 && _descriptor$format.mso_mdoc) {
|
368
|
+
if (!credentialsMdoc.length) {
|
369
|
+
throw new CredentialNotFoundError("mso_mdoc credential is not supported.");
|
370
|
+
}
|
371
|
+
const {
|
372
|
+
matchedEvaluation,
|
373
|
+
matchedKeyTag,
|
374
|
+
matchedCredential
|
375
|
+
} = findCredentialMDoc(descriptor, decodedMdocCredentials);
|
376
|
+
return {
|
377
|
+
evaluatedDisclosure: matchedEvaluation,
|
378
|
+
inputDescriptor: descriptor,
|
379
|
+
credential: matchedCredential,
|
380
|
+
keyTag: matchedKeyTag
|
381
|
+
};
|
382
|
+
}
|
383
|
+
if ((_descriptor$format2 = descriptor.format) !== null && _descriptor$format2 !== void 0 && _descriptor$format2["vc+sd-jwt"]) {
|
384
|
+
if (!decodedSdJwtCredentials.length) {
|
385
|
+
throw new CredentialNotFoundError("vc+sd-jwt credential is not supported.");
|
386
|
+
}
|
387
|
+
const {
|
388
|
+
matchedEvaluation,
|
389
|
+
matchedKeyTag,
|
390
|
+
matchedCredential
|
391
|
+
} = findCredentialSdJwt(descriptor, decodedSdJwtCredentials);
|
392
|
+
return {
|
393
|
+
evaluatedDisclosure: matchedEvaluation,
|
394
|
+
inputDescriptor: descriptor,
|
395
|
+
credential: matchedCredential,
|
396
|
+
keyTag: matchedKeyTag
|
397
|
+
};
|
398
|
+
}
|
399
|
+
throw new CredentialNotFoundError(`${descriptor.format} format is not supported.`);
|
400
|
+
}));
|
401
|
+
return results;
|
402
|
+
};
|
154
403
|
|
155
|
-
|
156
|
-
|
157
|
-
|
158
|
-
|
404
|
+
/**
|
405
|
+
* Prepares remote presentations for a set of credentials based on input descriptors.
|
406
|
+
*
|
407
|
+
* For each credential and its corresponding input descriptor, this function:
|
408
|
+
* - Validates the credential format.
|
409
|
+
* - Generates a verifiable presentation token (vpToken) using the provided nonce and client identifier.
|
410
|
+
*
|
411
|
+
* @param credentialAndDescriptors - An array containing objects with requested claims,
|
412
|
+
* input descriptor, credential, and keyTag.
|
413
|
+
* @param nonce - A unique nonce for the verifiable presentation token.
|
414
|
+
* @param client_id - The client identifier.
|
415
|
+
* @returns A promise that resolves to an array of RemotePresentation objects.
|
416
|
+
* @throws {CredentialNotFoundError} When the credential format is unsupported.
|
417
|
+
*/
|
418
|
+
export const prepareRemotePresentations = async (credentialAndDescriptors, authRequestObject) => {
|
419
|
+
/* In case of ISO 18013-7 we need a nonce, it shall have a minimum entropy of 16 */
|
420
|
+
const generatedNonce = generateRandomAlphaNumericString(16);
|
421
|
+
const presentations = await Promise.all(credentialAndDescriptors.map(async item => {
|
422
|
+
var _descriptor$format3, _descriptor$format4;
|
423
|
+
const descriptor = item.inputDescriptor;
|
424
|
+
if ((_descriptor$format3 = descriptor.format) !== null && _descriptor$format3 !== void 0 && _descriptor$format3.mso_mdoc) {
|
425
|
+
const {
|
426
|
+
vp_token
|
427
|
+
} = await prepareVpTokenMdoc(authRequestObject.nonce, generatedNonce, authRequestObject.clientId, authRequestObject.responseUri, descriptor.id, item.keyTag, [item.credential, item.requestedClaims, createCryptoContextFor(item.keyTag)]);
|
428
|
+
return {
|
429
|
+
requestedClaims: item.requestedClaims,
|
430
|
+
inputDescriptor: descriptor,
|
431
|
+
vpToken: vp_token,
|
432
|
+
format: "mso_mdoc"
|
433
|
+
};
|
434
|
+
}
|
435
|
+
if ((_descriptor$format4 = descriptor.format) !== null && _descriptor$format4 !== void 0 && _descriptor$format4["vc+sd-jwt"]) {
|
436
|
+
const {
|
437
|
+
vp_token
|
438
|
+
} = await prepareVpToken(authRequestObject.nonce, authRequestObject.clientId, [item.credential, item.requestedClaims, createCryptoContextFor(item.keyTag)]);
|
439
|
+
return {
|
440
|
+
requestedClaims: item.requestedClaims,
|
441
|
+
inputDescriptor: descriptor,
|
442
|
+
vpToken: vp_token,
|
443
|
+
format: "vc+sd-jwt"
|
444
|
+
};
|
445
|
+
}
|
446
|
+
throw new CredentialNotFoundError(`${descriptor.format} format is not supported.`);
|
447
|
+
}));
|
159
448
|
return {
|
160
|
-
|
161
|
-
|
162
|
-
unrequestedDisclosures
|
449
|
+
presentations,
|
450
|
+
generatedNonce
|
163
451
|
};
|
164
452
|
};
|
165
453
|
//# sourceMappingURL=07-evaluate-input-descriptor.js.map
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"names":["JSONPath","MissingDataError","Ajv","ajv","allErrors","INDEX_CLAIM_NAME","mapDisclosuresToObject","disclosures","reduce","obj","_ref","decoded","claimName","claimValue","findMatchedClaim","paths","payload","matchedPath","matchedValue","some","singlePath","result","path","json","length","error","extractClaimName","regex","match","Error","evaluateInputDescriptorForSdJwt4VC","inputDescriptor","payloadCredential","_inputDescriptor$cons","constraints","fields","requiredDisclosures","optionalDisclosures","unrequestedDisclosures","requiredClaimNames","optionalClaimNames","disclosuresAsPayload","allFieldsValid","every","field","optional","push","filter","validateSchema","compile","disclosure","includes","isNotLimitDisclosure","limit_disclosure"],"sourceRoot":"../../../../src","sources":["credential/presentation/07-evaluate-input-descriptor.ts"],"mappings":"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"}
|
1
|
+
{"version":3,"names":["decode","prepareVpToken","createCryptoContextFor","JSONPath","MissingDataError","CredentialNotFoundError","Ajv","CBOR","prepareVpTokenMdoc","generateRandomAlphaNumericString","ajv","allErrors","disclosureWithEncodedToEvaluatedDisclosure","disclosure","claimName","claimValue","decoded","name","value","mapDisclosuresToObject","disclosures","reduce","obj","_ref","mapNamespacesToObject","namespaces","Object","entries","_ref2","namespace","elements","fromEntries","map","element","elementIdentifier","elementValue","findMatchedClaim","paths","payload","matchedPath","matchedValue","some","singlePath","result","path","json","length","error","extractClaimName","regex","match","Error","extractNamespaceAndClaimName","nameSpace","propertyName","evaluateInputDescriptorForMdoc","inputDescriptor","issuerSigned","_inputDescriptor$cons","constraints","fields","requiredDisclosures","optionalDisclosures","namespacesAsPayload","nameSpaces","allFieldsValid","every","field","undefined","optional","push","filter","validateSchema","compile","evaluateInputDescriptorForSdJwt4VC","payloadCredential","_inputDescriptor$cons2","disclosuresAsPayload","findCredentialSdJwt","decodedSdJwtCredentials","keyTag","credential","sdJwt","evaluatedDisclosure","matchedEvaluation","matchedKeyTag","matchedCredential","findCredentialMDoc","decodedMDocCredentials","evaluateInputDescriptors","inputDescriptors","credentialsSdJwt","credentialsMdoc","_ref3","decodedMdocCredentials","Promise","all","_ref4","decodeIssuerSigned","results","descriptor","_descriptor$format","_descriptor$format2","format","mso_mdoc","prepareRemotePresentations","credentialAndDescriptors","authRequestObject","generatedNonce","presentations","item","_descriptor$format3","_descriptor$format4","vp_token","nonce","clientId","responseUri","id","requestedClaims","vpToken"],"sourceRoot":"../../../../src","sources":["credential/presentation/07-evaluate-input-descriptor.ts"],"mappings":"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"}
|
@@ -1,9 +1,9 @@
|
|
1
|
-
import { EncryptJwe
|
1
|
+
import { EncryptJwe } from "@pagopa/io-react-native-jwt";
|
2
2
|
import uuid from "react-native-uuid";
|
3
3
|
import { NoSuitableKeysFoundInEntityConfiguration } from "./errors";
|
4
4
|
import { hasStatusOrThrow } from "../../utils/misc";
|
5
|
-
import { disclose } from "../../sd-jwt";
|
6
5
|
import * as z from "zod";
|
6
|
+
import { Base64 } from "js-base64";
|
7
7
|
export const AuthorizationResponse = z.object({
|
8
8
|
status: z.string().optional(),
|
9
9
|
response_code: z.string() /**
|
@@ -32,69 +32,6 @@ export const choosePublicKeyToEncrypt = rpJwkKeys => {
|
|
32
32
|
throw new NoSuitableKeysFoundInEntityConfiguration("No suitable public key found for encryption.");
|
33
33
|
};
|
34
34
|
|
35
|
-
/**
|
36
|
-
* Prepares a Verified Presentation (VP) token to be sent as part of an
|
37
|
-
* authorization response in an OpenID 4 Verifiable Presentations flow.
|
38
|
-
*
|
39
|
-
* @param requestObject - The request object containing the nonce, response URI, and other necessary info.
|
40
|
-
* @param presentationTuple - A tuple containing a verifiable credential, the claims to disclose,
|
41
|
-
* and a cryptographic context for signing.
|
42
|
-
* @returns An object containing the signed VP token (`vp_token`) and a `presentation_submission` object.
|
43
|
-
* @param presentationDefinition - Definition outlining presentation requirements.
|
44
|
-
* @param presentationTuple - Tuple containing:
|
45
|
-
* - A verifiable credential.
|
46
|
-
* - Claims that should be disclosed.
|
47
|
-
* - Cryptographic context for signing.
|
48
|
-
* @returns An object with:
|
49
|
-
* - `vp_token`: The signed VP token.
|
50
|
-
* - `presentation_submission`: Object mapping disclosed credentials to the request.
|
51
|
-
*
|
52
|
-
* @remarks
|
53
|
-
* 1. The `disclose()` function is used to produce a token with only the requested claims.
|
54
|
-
* 2. A new JWT is then signed, including the VP, `jti`, `iss`, `nonce`, audience, and expiration.
|
55
|
-
* 3. The `presentation_submission` object follows the OpenID 4 VP specification for describing
|
56
|
-
* how the disclosed credentials map to the request.
|
57
|
-
*
|
58
|
-
* @todo [SIW-353] Support multiple verifiable credentials in a single request.
|
59
|
-
*/
|
60
|
-
export const prepareVpToken = async (requestObject, presentationDefinition, _ref) => {
|
61
|
-
var _presentationDefiniti;
|
62
|
-
let [verifiableCredential, requestedClaims, cryptoContext] = _ref;
|
63
|
-
// Produce a VP token with only requested claims from the verifiable credential
|
64
|
-
const {
|
65
|
-
token: vp
|
66
|
-
} = await disclose(verifiableCredential, requestedClaims);
|
67
|
-
|
68
|
-
// <Issuer-signed JWT>~<Disclosure 1>~<Disclosure N>~
|
69
|
-
const sd_hash = await sha256ToBase64(`${vp}~`);
|
70
|
-
const kbJwt = await new SignJWT(cryptoContext).setProtectedHeader({
|
71
|
-
typ: "kb+jwt",
|
72
|
-
alg: "ES256"
|
73
|
-
}).setPayload({
|
74
|
-
sd_hash,
|
75
|
-
nonce: requestObject.nonce
|
76
|
-
}).setAudience(requestObject.client_id).setIssuedAt().sign();
|
77
|
-
|
78
|
-
// <Issuer-signed JWT>~<Disclosure 1>~...~<Disclosure N>~<KB-JWT>
|
79
|
-
const vp_token = [vp, kbJwt].join("~");
|
80
|
-
|
81
|
-
// Determine the descriptor ID to use for mapping. Fallback to first input descriptor ID if not specified
|
82
|
-
// We support only one credential for now, so we get first input_descriptor and create just one descriptor_map
|
83
|
-
const presentation_submission = {
|
84
|
-
id: uuid.v4(),
|
85
|
-
definition_id: presentationDefinition.id,
|
86
|
-
descriptor_map: [{
|
87
|
-
id: presentationDefinition === null || presentationDefinition === void 0 || (_presentationDefiniti = presentationDefinition.input_descriptors[0]) === null || _presentationDefiniti === void 0 ? void 0 : _presentationDefiniti.id,
|
88
|
-
path: `$`,
|
89
|
-
format: "vc+sd-jwt"
|
90
|
-
}]
|
91
|
-
};
|
92
|
-
return {
|
93
|
-
vp_token,
|
94
|
-
presentation_submission
|
95
|
-
};
|
96
|
-
};
|
97
|
-
|
98
35
|
/**
|
99
36
|
* Builds a URL-encoded form body for a direct POST response without encryption.
|
100
37
|
*
|
@@ -104,10 +41,12 @@ export const prepareVpToken = async (requestObject, presentationDefinition, _ref
|
|
104
41
|
*/
|
105
42
|
export const buildDirectPostBody = async (requestObject, payload) => {
|
106
43
|
const formUrlEncodedBody = new URLSearchParams({
|
107
|
-
|
108
|
-
|
109
|
-
|
110
|
-
|
44
|
+
...(requestObject.state ? {
|
45
|
+
state: requestObject.state
|
46
|
+
} : {}),
|
47
|
+
...Object.fromEntries(Object.entries(payload).map(_ref => {
|
48
|
+
let [key, value] = _ref;
|
49
|
+
return [key, Array.isArray(value) || typeof value === "object" ? JSON.stringify(value) : value];
|
111
50
|
}))
|
112
51
|
});
|
113
52
|
return formUrlEncodedBody.toString();
|
@@ -119,10 +58,11 @@ export const buildDirectPostBody = async (requestObject, payload) => {
|
|
119
58
|
* @param jwkKeys - Array of JWKs from the Relying Party for encryption.
|
120
59
|
* @param requestObject - Contains state, nonce, and other relevant info.
|
121
60
|
* @param payload - Object that contains either the VP token to encrypt and the mapping of the credential disclosures or the error code
|
61
|
+
* @param generatedNonce - Optional nonce for the `apu` claim in the JWE header, it is used during ISO 18013-7.
|
122
62
|
* @returns A URL-encoded string for an `application/x-www-form-urlencoded` POST body,
|
123
63
|
* where `response` contains the encrypted JWE.
|
124
64
|
*/
|
125
|
-
export const buildDirectPostJwtBody = async (jwkKeys, requestObject, payload) => {
|
65
|
+
export const buildDirectPostJwtBody = async (jwkKeys, requestObject, payload, generatedNonce) => {
|
126
66
|
// Prepare the authorization response payload to be encrypted
|
127
67
|
const authzResponsePayload = JSON.stringify({
|
128
68
|
state: requestObject.state,
|
@@ -131,7 +71,6 @@ export const buildDirectPostJwtBody = async (jwkKeys, requestObject, payload) =>
|
|
131
71
|
|
132
72
|
// Choose a suitable RSA public key for encryption
|
133
73
|
const encPublicJwk = choosePublicKeyToEncrypt(jwkKeys);
|
134
|
-
|
135
74
|
// Encrypt the authorization payload
|
136
75
|
const {
|
137
76
|
client_metadata
|
@@ -139,13 +78,20 @@ export const buildDirectPostJwtBody = async (jwkKeys, requestObject, payload) =>
|
|
139
78
|
const encryptedResponse = await new EncryptJwe(authzResponsePayload, {
|
140
79
|
alg: (client_metadata === null || client_metadata === void 0 ? void 0 : client_metadata.authorization_encrypted_response_alg) || "RSA-OAEP-256",
|
141
80
|
enc: (client_metadata === null || client_metadata === void 0 ? void 0 : client_metadata.authorization_encrypted_response_enc) || "A256CBC-HS512",
|
142
|
-
kid: encPublicJwk.kid
|
81
|
+
kid: encPublicJwk.kid,
|
82
|
+
/* ISO 18013-7 */
|
83
|
+
apv: Base64.encodeURI(requestObject.nonce),
|
84
|
+
...(generatedNonce ? {
|
85
|
+
apu: Base64.encodeURI(generatedNonce)
|
86
|
+
} : {})
|
143
87
|
}).encrypt(encPublicJwk);
|
144
88
|
|
145
89
|
// Build the x-www-form-urlencoded form body
|
146
90
|
const formBody = new URLSearchParams({
|
147
91
|
response: encryptedResponse,
|
148
|
-
|
92
|
+
...(requestObject.state ? {
|
93
|
+
state: requestObject.state
|
94
|
+
} : {})
|
149
95
|
});
|
150
96
|
return formBody.toString();
|
151
97
|
};
|
@@ -166,33 +112,52 @@ export const buildDirectPostJwtBody = async (jwkKeys, requestObject, payload) =>
|
|
166
112
|
* @param context - Contains optional custom fetch implementation.
|
167
113
|
* @returns Parsed and validated authorization response from the Relying Party.
|
168
114
|
*/
|
169
|
-
export const sendAuthorizationResponse = async function (requestObject,
|
115
|
+
export const sendAuthorizationResponse = async function (requestObject, presentationDefinitionId, jwkKeys, remotePresentation) {
|
116
|
+
var _presentations$;
|
170
117
|
let {
|
171
118
|
appFetch = fetch
|
172
119
|
} = arguments.length > 4 && arguments[4] !== undefined ? arguments[4] : {};
|
173
|
-
// 1. Create the VP token and associated submission mapping
|
174
120
|
const {
|
175
|
-
|
176
|
-
|
177
|
-
} =
|
121
|
+
generatedNonce,
|
122
|
+
presentations
|
123
|
+
} = remotePresentation;
|
124
|
+
/**
|
125
|
+
* 1. Prepare the VP token and presentation submission
|
126
|
+
* If there is only one credential, `vpToken` is a single string.
|
127
|
+
* If there are multiple credential, `vpToken` is an array of string.
|
128
|
+
**/
|
129
|
+
const vp_token = (presentations === null || presentations === void 0 ? void 0 : presentations.length) === 1 ? (_presentations$ = presentations[0]) === null || _presentations$ === void 0 ? void 0 : _presentations$.vpToken : presentations.map(presentation => presentation.vpToken);
|
130
|
+
const descriptor_map = presentations.map((presentation, index) => ({
|
131
|
+
id: presentation.inputDescriptor.id,
|
132
|
+
path: (presentations === null || presentations === void 0 ? void 0 : presentations.length) === 1 ? `$` : `$[${index}]`,
|
133
|
+
format: presentation.format
|
134
|
+
}));
|
135
|
+
const presentation_submission = {
|
136
|
+
id: uuid.v4(),
|
137
|
+
definition_id: presentationDefinitionId,
|
138
|
+
descriptor_map
|
139
|
+
};
|
178
140
|
|
179
141
|
// 2. Choose the appropriate request body builder based on response mode
|
180
142
|
const requestBody = requestObject.response_mode === "direct_post.jwt" ? await buildDirectPostJwtBody(jwkKeys, requestObject, {
|
181
143
|
vp_token,
|
182
144
|
presentation_submission
|
183
|
-
}) : await buildDirectPostBody(requestObject, {
|
145
|
+
}, generatedNonce) : await buildDirectPostBody(requestObject, {
|
184
146
|
vp_token,
|
185
147
|
presentation_submission: presentation_submission
|
186
148
|
});
|
187
149
|
|
188
150
|
// 3. Send the authorization response via HTTP POST and validate the response
|
189
|
-
|
151
|
+
const authResponse = await appFetch(requestObject.response_uri, {
|
190
152
|
method: "POST",
|
191
153
|
headers: {
|
192
154
|
"Content-Type": "application/x-www-form-urlencoded"
|
193
155
|
},
|
194
156
|
body: requestBody
|
195
|
-
}).then(hasStatusOrThrow(200)).then(res => res.json()).then(AuthorizationResponse.
|
157
|
+
}).then(hasStatusOrThrow(200)).then(res => res.json()).then(AuthorizationResponse.safeParse);
|
158
|
+
|
159
|
+
// Some Relying Parties may return an empty body.
|
160
|
+
return authResponse.success ? authResponse.data : {};
|
196
161
|
};
|
197
162
|
|
198
163
|
/**
|