Skip to content

Commit 449364b

Browse files
committed
feat: Unify how we get types from different spec versions
1 parent 039b622 commit 449364b

3 files changed

Lines changed: 44 additions & 39 deletions

File tree

packages/client/lib/OpenID4VCIClient.ts

Lines changed: 2 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ import {
1919
getIssuerFromCredentialOfferPayload,
2020
getSupportedCredentials,
2121
getTypesFromCredentialSupported,
22+
getTypesFromObject,
2223
JWK,
2324
KID_JWK_X5C_ERROR,
2425
NotificationRequest,
@@ -482,17 +483,7 @@ export class OpenID4VCIClient {
482483
result[0] = types;
483484
return result;
484485
} else if (this.credentialOffer.version < OpenId4VCIVersion.VER_1_0_13) {
485-
return (this.credentialOffer.credential_offer as CredentialOfferPayloadV1_0_11).credentials.map((c) => {
486-
if (typeof c === 'string') {
487-
return [c];
488-
} else if ('types' in c) {
489-
return c.types;
490-
} else if ('vct' in c) {
491-
return [c.vct];
492-
} else {
493-
return c.credential_definition.types;
494-
}
495-
});
486+
return (this.credentialOffer.credential_offer as CredentialOfferPayloadV1_0_11).credentials.map((c) => getTypesFromObject(c) ?? []);
496487
}
497488
// we don't have this for v13. v13 only has credential_configuration_ids which is not translatable to type
498489
return undefined;

packages/client/lib/OpenID4VCIClientV1_0_11.ts

Lines changed: 4 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ import {
1717
getIssuerFromCredentialOfferPayload,
1818
getSupportedCredentials,
1919
getTypesFromCredentialSupported,
20+
getTypesFromObject,
2021
JWK,
2122
KID_JWK_X5C_ERROR,
2223
OID4VCICredentialFormat,
@@ -479,20 +480,10 @@ export class OpenID4VCIClientV1_0_11 {
479480
result[0] = types;
480481
return result;
481482
} else if (this.credentialOffer.version < OpenId4VCIVersion.VER_1_0_13) {
482-
return (this.credentialOffer.credential_offer as CredentialOfferPayloadV1_0_11).credentials.map((c) => {
483-
if (typeof c === 'string') {
484-
return [c];
485-
} else if ('types' in c) {
486-
return c.types;
487-
} else if ('vct' in c) {
488-
return [c.vct];
489-
} else {
490-
return c.credential_definition.types;
491-
}
492-
});
483+
return (this.credentialOffer.credential_offer as CredentialOfferPayloadV1_0_11).credentials.map((c) => getTypesFromObject(c) ?? []);
493484
}
494-
// we don't have this for v13. v13 only has credential_configuration_ids which is not translatable to type
495-
return [];
485+
// we don't support > V11
486+
throw Error(`This class only supports version 11 and lower! Version: ${this.version()}`);
496487
}
497488

498489
issuerSupportedFlowTypes(): AuthzFlowType[] {

packages/common/lib/functions/IssuerMetadataUtils.ts

Lines changed: 38 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { VCI_LOG_COMMON } from '../index';
1+
import { CredentialDefinitionV1_0_13, CredentialOfferFormat, JsonLdIssuerCredentialDefinition, VCI_LOG_COMMON } from '../index';
22
import {
33
AuthorizationServerMetadata,
44
CredentialConfigurationSupported,
@@ -79,17 +79,22 @@ export function getSupportedCredential(opts?: {
7979

8080
function filterMatchingConfig(config: CredentialConfigurationSupported): CredentialConfigurationSupported | undefined {
8181
let isTypeMatch = normalizedTypes.length === 0;
82+
const types = getTypesFromObject(config);
8283
if (!isTypeMatch) {
8384
if (normalizedTypes.length === 1 && config.id === normalizedTypes[0]) {
8485
isTypeMatch = true;
85-
} else if ('credential_definition' in config) {
86-
isTypeMatch = normalizedTypes.some((type) => config.credential_definition.type?.includes(type));
87-
} else if ('type' in config && Array.isArray(config.type)) {
88-
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
89-
// @ts-ignore
90-
isTypeMatch = normalizedTypes.some((type) => config.type.includes(type));
91-
} else if ('types' in config) {
92-
isTypeMatch = normalizedTypes.some((type) => config.types?.includes(type));
86+
} else if (types) {
87+
isTypeMatch = normalizedTypes.some((type) => types.includes(type));
88+
} else {
89+
if ('credential_definition' in config) {
90+
isTypeMatch = normalizedTypes.some((type) => config.credential_definition.type?.includes(type));
91+
} else if ('type' in config && Array.isArray(config.type)) {
92+
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
93+
// @ts-ignore
94+
isTypeMatch = normalizedTypes.some((type) => config.type.includes(type));
95+
} else if ('types' in config) {
96+
isTypeMatch = normalizedTypes.some((type) => config.types?.includes(type));
97+
}
9398
}
9499
}
95100

@@ -129,12 +134,7 @@ export function getTypesFromCredentialSupported(
129134
credentialSupported.format === 'jwt_vc_json-ld' ||
130135
credentialSupported.format === 'ldp_vc'
131136
) {
132-
types =
133-
(credentialSupported.types
134-
? (credentialSupported.types as string[])
135-
: 'credential_definition' in credentialSupported
136-
? credentialSupported.credential_definition?.type
137-
: []) ?? [];
137+
types = getTypesFromObject(credentialSupported) ?? [];
138138
} else if (credentialSupported.format === 'vc+sd-jwt') {
139139
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
140140
// @ts-ignore
@@ -204,3 +204,26 @@ export function getIssuerName(
204204
}
205205
return url;
206206
}
207+
208+
/**
209+
* The specs had many places where types could be expressed. This method ensures we get them in any way possible
210+
* @param subject
211+
*/
212+
export function getTypesFromObject(
213+
subject: CredentialConfigurationSupported | CredentialOfferFormat | CredentialDefinitionV1_0_13 | JsonLdIssuerCredentialDefinition | string,
214+
): string[] | undefined {
215+
if (typeof subject === 'string') {
216+
return [subject];
217+
} else if ('credential_definition' in subject && subject.credential_definition) {
218+
return getTypesFromObject(subject.credential_definition);
219+
} else if ('types' in subject && subject.types) {
220+
return Array.isArray(subject.types) ? subject.types : [subject.types];
221+
} else if ('type' in subject && subject.type) {
222+
return Array.isArray(subject.type) ? subject.type : [subject.type];
223+
} else if ('vct' in subject && subject.vct) {
224+
return [subject.vct];
225+
}
226+
227+
VCI_LOG_COMMON.warning('Could not deduce credential types. Probably a failure down the line will happen!');
228+
return undefined;
229+
}

0 commit comments

Comments
 (0)