@credo-ts/openid4vc 0.6.1-alpha-20251208105733 → 0.6.1-alpha-20251209100250

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.
@@ -1 +1 @@
1
- {"version":3,"file":"OpenId4VcIssuerApi.d.mts","names":[],"sources":["../../src/openid4vc-issuer/OpenId4VcIssuerApi.ts"],"sourcesContent":[],"mappings":";;;;;;;;;;;;;;;;;;;cAmBa,kBAAA;mBAEe;;EAFf,QAAA,sBAAkB;EAEH,WAAA,CAAA,MAAA,EAAA,2BAAA,EAAA,YAAA,EACF,YADE,EAAA,sBAAA,EAEQ,sBAFR;EAAA,aAAA,CAAA,CAAA,EAKA,OALA,CAE8B,qBAAA,EAF9B,CAAA;EACF,mBAAA,CAAA,QAAA,EAAA,MAAA,CAAA,EAQyB,OARzB,CAIE,qBAAA,CAJF;EACU;;;;EAOe,YAAA,CAAA,OAAA,EAQd,6BARc,CAAA,EAQe,OARf,CAQe,qBAAA,CARf;EAQd;;;EAOsB,2BAAA,CAAA,QAAA,EAAA,MAAA,CAAA,EAAA,OAAA,CAAA,IAAA,CAAA;EAKd,oBAAA,CAAA,OAAA,EAAA,kCAAA,CAAA,EAAkC,OAAlC,CAAA,IAAA,CAAA;EAAkC;;;;EAoCjC,8BAAA,CAAA,OAAA,EAZjC,+CAYiC,GAAA;IAAsC,QAAA,EAAA,MAAA;EAAuB,CAAA,CAAA,EAZxB,OAYwB,CAAA;IAU9F,eAAA,EAAA,MAAA;IAAyC,qBAAA,EAtBM,gCAsBN;;EAAgC;;;;;EAeQ,qBAAA,CAAA,OAAA,EAzBhD,sCAyBgD,GAAA;;MAzBa;qBAAvB;IAuCnC,eAAA,EAAA,MAAA;EAAA,CAAA,CAAA;EAKc;;;oCAlClD;;MAAyE;qBAAhC;;;;;;4CAezC;;MAAiF;qBAAhC;;;uCAcb;0BAd6C,sBAAA,CAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;qDAmB/B,QALd,8BAAA"}
1
+ {"version":3,"file":"OpenId4VcIssuerApi.d.mts","names":[],"sources":["../../src/openid4vc-issuer/OpenId4VcIssuerApi.ts"],"sourcesContent":[],"mappings":";;;;;;;;;;;;;;;;;;;cAmBa,kBAAA;mBAEe;;EAFf,QAAA,sBAAkB;EAEH,WAAA,CAAA,MAAA,EAAA,2BAAA,EAAA,YAAA,EACF,YADE,EAAA,sBAAA,EAEQ,sBAFR;EAAA,aAAA,CAAA,CAAA,EAKA,OALA,CAE8B,qBAAA,EAF9B,CAAA;EACF,mBAAA,CAAA,QAAA,EAAA,MAAA,CAAA,EAQyB,OARzB,CAIE,qBAAA,CAJF;EACU;;;;EAOe,YAAA,CAAA,OAAA,EAQd,6BARc,CAAA,EAQe,OARf,CAQe,qBAAA,CARf;EAQd;;;EAOsB,2BAAA,CAAA,QAAA,EAAA,MAAA,CAAA,EAAA,OAAA,CAAA,IAAA,CAAA;EAKd,oBAAA,CAAA,OAAA,EAAA,kCAAA,CAAA,EAAkC,OAAlC,CAAA,IAAA,CAAA;EAAkC;;;;EAsCjC,8BAAA,CAAA,OAAA,EAZjC,+CAYiC,GAAA;IAAsC,QAAA,EAAA,MAAA;EAAuB,CAAA,CAAA,EAZxB,OAYwB,CAAA;IAU9F,eAAA,EAAA,MAAA;IAAyC,qBAAA,EAtBM,gCAsBN;;EAAgC;;;;;EAeQ,qBAAA,CAAA,OAAA,EAzBhD,sCAyBgD,GAAA;;MAzBa;qBAAvB;IAuCnC,eAAA,EAAA,MAAA;EAAA,CAAA,CAAA;EAKc;;;oCAlClD;;MAAyE;qBAAhC;;;;;;4CAezC;;MAAiF;qBAAhC;;;uCAcb;0BAd6C,sBAAA,CAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;qDAmB/B,QALd,8BAAA"}
@@ -33,12 +33,13 @@ let OpenId4VcIssuerApi = class OpenId4VcIssuerApi$1 {
33
33
  return this.openId4VcIssuerService.rotateAccessTokenSigningKey(this.agentContext, issuer);
34
34
  }
35
35
  async updateIssuerMetadata(options) {
36
- const { issuerId, credentialConfigurationsSupported, display, dpopSigningAlgValuesSupported, batchCredentialIssuance } = options;
36
+ const { issuerId, credentialConfigurationsSupported, display, dpopSigningAlgValuesSupported, batchCredentialIssuance, authorizationServerConfigs } = options;
37
37
  const issuer = await this.openId4VcIssuerService.getIssuerByIssuerId(this.agentContext, issuerId);
38
38
  issuer.credentialConfigurationsSupported = credentialConfigurationsSupported;
39
39
  issuer.display = display;
40
40
  issuer.dpopSigningAlgValuesSupported = dpopSigningAlgValuesSupported;
41
41
  issuer.batchCredentialIssuance = batchCredentialIssuance;
42
+ issuer.authorizationServerConfigs = authorizationServerConfigs;
42
43
  return this.openId4VcIssuerService.updateIssuer(this.agentContext, issuer);
43
44
  }
44
45
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"OpenId4VcIssuerApi.mjs","names":["OpenId4VcIssuerApi","config: OpenId4VcIssuerModuleConfig","agentContext: AgentContext","openId4VcIssuerService: OpenId4VcIssuerService"],"sources":["../../src/openid4vc-issuer/OpenId4VcIssuerApi.ts"],"sourcesContent":["import { AgentContext, injectable } from '@credo-ts/core'\nimport { OpenId4VcIssuerModuleConfig } from './OpenId4VcIssuerModuleConfig'\nimport { OpenId4VcIssuerService } from './OpenId4VcIssuerService'\nimport type {\n OpenId4VciCreateCredentialOfferOptions,\n OpenId4VciCreateCredentialResponseOptions,\n OpenId4VciCreateDeferredCredentialResponseOptions,\n OpenId4VciCreateIssuerOptions,\n OpenId4VciCreateStatelessCredentialOfferOptions,\n OpenId4VcUpdateIssuerRecordOptions,\n} from './OpenId4VcIssuerServiceOptions'\n\n/**\n * @public\n * This class represents the API for interacting with the OpenID4VC Issuer service.\n * It provides methods for creating a credential offer, creating a response to a credential issuance request,\n * and retrieving a credential offer from a URI.\n */\n@injectable()\nexport class OpenId4VcIssuerApi {\n public constructor(\n public readonly config: OpenId4VcIssuerModuleConfig,\n private agentContext: AgentContext,\n private openId4VcIssuerService: OpenId4VcIssuerService\n ) {}\n\n public async getAllIssuers() {\n return this.openId4VcIssuerService.getAllIssuers(this.agentContext)\n }\n\n public async getIssuerByIssuerId(issuerId: string) {\n return this.openId4VcIssuerService.getIssuerByIssuerId(this.agentContext, issuerId)\n }\n\n /**\n * Creates an issuer and stores the corresponding issuer metadata. Multiple issuers can be created, to allow different sets of\n * credentials to be issued with each issuer.\n */\n public async createIssuer(options: OpenId4VciCreateIssuerOptions) {\n return this.openId4VcIssuerService.createIssuer(this.agentContext, options)\n }\n\n /**\n * Rotate the key used for signing access tokens for the issuer with the given issuerId.\n */\n public async rotateAccessTokenSigningKey(issuerId: string) {\n const issuer = await this.openId4VcIssuerService.getIssuerByIssuerId(this.agentContext, issuerId)\n return this.openId4VcIssuerService.rotateAccessTokenSigningKey(this.agentContext, issuer)\n }\n\n public async updateIssuerMetadata(options: OpenId4VcUpdateIssuerRecordOptions) {\n const {\n issuerId,\n credentialConfigurationsSupported,\n display,\n dpopSigningAlgValuesSupported,\n batchCredentialIssuance,\n } = options\n\n const issuer = await this.openId4VcIssuerService.getIssuerByIssuerId(this.agentContext, issuerId)\n\n issuer.credentialConfigurationsSupported = credentialConfigurationsSupported\n issuer.display = display\n issuer.dpopSigningAlgValuesSupported = dpopSigningAlgValuesSupported\n issuer.batchCredentialIssuance = batchCredentialIssuance\n\n return this.openId4VcIssuerService.updateIssuer(this.agentContext, issuer)\n }\n\n /**\n * Creates a stateless credential offer. This can only be used with an external authorization server, as credo only supports stateful\n * credential offers.\n */\n public async createStatelessCredentialOffer(\n options: OpenId4VciCreateStatelessCredentialOfferOptions & { issuerId: string }\n ) {\n const { issuerId, ...rest } = options\n const issuer = await this.openId4VcIssuerService.getIssuerByIssuerId(this.agentContext, issuerId)\n return await this.openId4VcIssuerService.createStatelessCredentialOffer(this.agentContext, { ...rest, issuer })\n }\n\n /**\n * Creates a credential offer. Either the preAuthorizedCodeFlowConfig or the authorizationCodeFlowConfig must be provided.\n *\n * @returns Object containing the payload of the credential offer and the credential offer request, which can be sent to the wallet.\n */\n public async createCredentialOffer(options: OpenId4VciCreateCredentialOfferOptions & { issuerId: string }) {\n const { issuerId, ...rest } = options\n const issuer = await this.openId4VcIssuerService.getIssuerByIssuerId(this.agentContext, issuerId)\n return await this.openId4VcIssuerService.createCredentialOffer(this.agentContext, { ...rest, issuer })\n }\n\n /**\n * This function creates a response which can be sent to the holder after receiving a credential issuance request.\n */\n public async createCredentialResponse(\n options: OpenId4VciCreateCredentialResponseOptions & { issuanceSessionId: string }\n ) {\n const { issuanceSessionId, ...rest } = options\n const issuanceSession = await this.openId4VcIssuerService.getIssuanceSessionById(\n this.agentContext,\n issuanceSessionId\n )\n\n return await this.openId4VcIssuerService.createCredentialResponse(this.agentContext, { ...rest, issuanceSession })\n }\n\n /**\n * This function creates a response which can be sent to the holder after receiving a deferred credential issuance request.\n */\n public async createDeferredCredentialResponse(\n options: OpenId4VciCreateDeferredCredentialResponseOptions & { issuanceSessionId: string }\n ) {\n const { issuanceSessionId, ...rest } = options\n const issuanceSession = await this.openId4VcIssuerService.getIssuanceSessionById(\n this.agentContext,\n issuanceSessionId\n )\n\n return await this.openId4VcIssuerService.createDeferredCredentialResponse(this.agentContext, {\n ...rest,\n issuanceSession,\n })\n }\n\n public async getIssuerMetadata(issuerId: string) {\n const issuer = await this.openId4VcIssuerService.getIssuerByIssuerId(this.agentContext, issuerId)\n return this.openId4VcIssuerService.getIssuerMetadata(this.agentContext, issuer)\n }\n\n public async getIssuanceSessionById(issuanceSessionId: string) {\n return this.openId4VcIssuerService.getIssuanceSessionById(this.agentContext, issuanceSessionId)\n }\n}\n"],"mappings":";;;;;;;;AAmBO,+BAAMA,qBAAmB;CAC9B,AAAO,YACL,AAAgBC,QAChB,AAAQC,cACR,AAAQC,wBACR;EAHgB;EACR;EACA;;CAGV,MAAa,gBAAgB;AAC3B,SAAO,KAAK,uBAAuB,cAAc,KAAK,aAAa;;CAGrE,MAAa,oBAAoB,UAAkB;AACjD,SAAO,KAAK,uBAAuB,oBAAoB,KAAK,cAAc,SAAS;;;;;;CAOrF,MAAa,aAAa,SAAwC;AAChE,SAAO,KAAK,uBAAuB,aAAa,KAAK,cAAc,QAAQ;;;;;CAM7E,MAAa,4BAA4B,UAAkB;EACzD,MAAM,SAAS,MAAM,KAAK,uBAAuB,oBAAoB,KAAK,cAAc,SAAS;AACjG,SAAO,KAAK,uBAAuB,4BAA4B,KAAK,cAAc,OAAO;;CAG3F,MAAa,qBAAqB,SAA6C;EAC7E,MAAM,EACJ,UACA,mCACA,SACA,+BACA,4BACE;EAEJ,MAAM,SAAS,MAAM,KAAK,uBAAuB,oBAAoB,KAAK,cAAc,SAAS;AAEjG,SAAO,oCAAoC;AAC3C,SAAO,UAAU;AACjB,SAAO,gCAAgC;AACvC,SAAO,0BAA0B;AAEjC,SAAO,KAAK,uBAAuB,aAAa,KAAK,cAAc,OAAO;;;;;;CAO5E,MAAa,+BACX,SACA;EACA,MAAM,EAAE,UAAU,GAAG,SAAS;EAC9B,MAAM,SAAS,MAAM,KAAK,uBAAuB,oBAAoB,KAAK,cAAc,SAAS;AACjG,SAAO,MAAM,KAAK,uBAAuB,+BAA+B,KAAK,cAAc;GAAE,GAAG;GAAM;GAAQ,CAAC;;;;;;;CAQjH,MAAa,sBAAsB,SAAwE;EACzG,MAAM,EAAE,UAAU,GAAG,SAAS;EAC9B,MAAM,SAAS,MAAM,KAAK,uBAAuB,oBAAoB,KAAK,cAAc,SAAS;AACjG,SAAO,MAAM,KAAK,uBAAuB,sBAAsB,KAAK,cAAc;GAAE,GAAG;GAAM;GAAQ,CAAC;;;;;CAMxG,MAAa,yBACX,SACA;EACA,MAAM,EAAE,mBAAmB,GAAG,SAAS;EACvC,MAAM,kBAAkB,MAAM,KAAK,uBAAuB,uBACxD,KAAK,cACL,kBACD;AAED,SAAO,MAAM,KAAK,uBAAuB,yBAAyB,KAAK,cAAc;GAAE,GAAG;GAAM;GAAiB,CAAC;;;;;CAMpH,MAAa,iCACX,SACA;EACA,MAAM,EAAE,mBAAmB,GAAG,SAAS;EACvC,MAAM,kBAAkB,MAAM,KAAK,uBAAuB,uBACxD,KAAK,cACL,kBACD;AAED,SAAO,MAAM,KAAK,uBAAuB,iCAAiC,KAAK,cAAc;GAC3F,GAAG;GACH;GACD,CAAC;;CAGJ,MAAa,kBAAkB,UAAkB;EAC/C,MAAM,SAAS,MAAM,KAAK,uBAAuB,oBAAoB,KAAK,cAAc,SAAS;AACjG,SAAO,KAAK,uBAAuB,kBAAkB,KAAK,cAAc,OAAO;;CAGjF,MAAa,uBAAuB,mBAA2B;AAC7D,SAAO,KAAK,uBAAuB,uBAAuB,KAAK,cAAc,kBAAkB;;;iCAjHlG,YAAY"}
1
+ {"version":3,"file":"OpenId4VcIssuerApi.mjs","names":["OpenId4VcIssuerApi","config: OpenId4VcIssuerModuleConfig","agentContext: AgentContext","openId4VcIssuerService: OpenId4VcIssuerService"],"sources":["../../src/openid4vc-issuer/OpenId4VcIssuerApi.ts"],"sourcesContent":["import { AgentContext, injectable } from '@credo-ts/core'\nimport { OpenId4VcIssuerModuleConfig } from './OpenId4VcIssuerModuleConfig'\nimport { OpenId4VcIssuerService } from './OpenId4VcIssuerService'\nimport type {\n OpenId4VciCreateCredentialOfferOptions,\n OpenId4VciCreateCredentialResponseOptions,\n OpenId4VciCreateDeferredCredentialResponseOptions,\n OpenId4VciCreateIssuerOptions,\n OpenId4VciCreateStatelessCredentialOfferOptions,\n OpenId4VcUpdateIssuerRecordOptions,\n} from './OpenId4VcIssuerServiceOptions'\n\n/**\n * @public\n * This class represents the API for interacting with the OpenID4VC Issuer service.\n * It provides methods for creating a credential offer, creating a response to a credential issuance request,\n * and retrieving a credential offer from a URI.\n */\n@injectable()\nexport class OpenId4VcIssuerApi {\n public constructor(\n public readonly config: OpenId4VcIssuerModuleConfig,\n private agentContext: AgentContext,\n private openId4VcIssuerService: OpenId4VcIssuerService\n ) {}\n\n public async getAllIssuers() {\n return this.openId4VcIssuerService.getAllIssuers(this.agentContext)\n }\n\n public async getIssuerByIssuerId(issuerId: string) {\n return this.openId4VcIssuerService.getIssuerByIssuerId(this.agentContext, issuerId)\n }\n\n /**\n * Creates an issuer and stores the corresponding issuer metadata. Multiple issuers can be created, to allow different sets of\n * credentials to be issued with each issuer.\n */\n public async createIssuer(options: OpenId4VciCreateIssuerOptions) {\n return this.openId4VcIssuerService.createIssuer(this.agentContext, options)\n }\n\n /**\n * Rotate the key used for signing access tokens for the issuer with the given issuerId.\n */\n public async rotateAccessTokenSigningKey(issuerId: string) {\n const issuer = await this.openId4VcIssuerService.getIssuerByIssuerId(this.agentContext, issuerId)\n return this.openId4VcIssuerService.rotateAccessTokenSigningKey(this.agentContext, issuer)\n }\n\n public async updateIssuerMetadata(options: OpenId4VcUpdateIssuerRecordOptions) {\n const {\n issuerId,\n credentialConfigurationsSupported,\n display,\n dpopSigningAlgValuesSupported,\n batchCredentialIssuance,\n authorizationServerConfigs,\n } = options\n\n const issuer = await this.openId4VcIssuerService.getIssuerByIssuerId(this.agentContext, issuerId)\n\n issuer.credentialConfigurationsSupported = credentialConfigurationsSupported\n issuer.display = display\n issuer.dpopSigningAlgValuesSupported = dpopSigningAlgValuesSupported\n issuer.batchCredentialIssuance = batchCredentialIssuance\n issuer.authorizationServerConfigs = authorizationServerConfigs\n\n return this.openId4VcIssuerService.updateIssuer(this.agentContext, issuer)\n }\n\n /**\n * Creates a stateless credential offer. This can only be used with an external authorization server, as credo only supports stateful\n * credential offers.\n */\n public async createStatelessCredentialOffer(\n options: OpenId4VciCreateStatelessCredentialOfferOptions & { issuerId: string }\n ) {\n const { issuerId, ...rest } = options\n const issuer = await this.openId4VcIssuerService.getIssuerByIssuerId(this.agentContext, issuerId)\n return await this.openId4VcIssuerService.createStatelessCredentialOffer(this.agentContext, { ...rest, issuer })\n }\n\n /**\n * Creates a credential offer. Either the preAuthorizedCodeFlowConfig or the authorizationCodeFlowConfig must be provided.\n *\n * @returns Object containing the payload of the credential offer and the credential offer request, which can be sent to the wallet.\n */\n public async createCredentialOffer(options: OpenId4VciCreateCredentialOfferOptions & { issuerId: string }) {\n const { issuerId, ...rest } = options\n const issuer = await this.openId4VcIssuerService.getIssuerByIssuerId(this.agentContext, issuerId)\n return await this.openId4VcIssuerService.createCredentialOffer(this.agentContext, { ...rest, issuer })\n }\n\n /**\n * This function creates a response which can be sent to the holder after receiving a credential issuance request.\n */\n public async createCredentialResponse(\n options: OpenId4VciCreateCredentialResponseOptions & { issuanceSessionId: string }\n ) {\n const { issuanceSessionId, ...rest } = options\n const issuanceSession = await this.openId4VcIssuerService.getIssuanceSessionById(\n this.agentContext,\n issuanceSessionId\n )\n\n return await this.openId4VcIssuerService.createCredentialResponse(this.agentContext, { ...rest, issuanceSession })\n }\n\n /**\n * This function creates a response which can be sent to the holder after receiving a deferred credential issuance request.\n */\n public async createDeferredCredentialResponse(\n options: OpenId4VciCreateDeferredCredentialResponseOptions & { issuanceSessionId: string }\n ) {\n const { issuanceSessionId, ...rest } = options\n const issuanceSession = await this.openId4VcIssuerService.getIssuanceSessionById(\n this.agentContext,\n issuanceSessionId\n )\n\n return await this.openId4VcIssuerService.createDeferredCredentialResponse(this.agentContext, {\n ...rest,\n issuanceSession,\n })\n }\n\n public async getIssuerMetadata(issuerId: string) {\n const issuer = await this.openId4VcIssuerService.getIssuerByIssuerId(this.agentContext, issuerId)\n return this.openId4VcIssuerService.getIssuerMetadata(this.agentContext, issuer)\n }\n\n public async getIssuanceSessionById(issuanceSessionId: string) {\n return this.openId4VcIssuerService.getIssuanceSessionById(this.agentContext, issuanceSessionId)\n }\n}\n"],"mappings":";;;;;;;;AAmBO,+BAAMA,qBAAmB;CAC9B,AAAO,YACL,AAAgBC,QAChB,AAAQC,cACR,AAAQC,wBACR;EAHgB;EACR;EACA;;CAGV,MAAa,gBAAgB;AAC3B,SAAO,KAAK,uBAAuB,cAAc,KAAK,aAAa;;CAGrE,MAAa,oBAAoB,UAAkB;AACjD,SAAO,KAAK,uBAAuB,oBAAoB,KAAK,cAAc,SAAS;;;;;;CAOrF,MAAa,aAAa,SAAwC;AAChE,SAAO,KAAK,uBAAuB,aAAa,KAAK,cAAc,QAAQ;;;;;CAM7E,MAAa,4BAA4B,UAAkB;EACzD,MAAM,SAAS,MAAM,KAAK,uBAAuB,oBAAoB,KAAK,cAAc,SAAS;AACjG,SAAO,KAAK,uBAAuB,4BAA4B,KAAK,cAAc,OAAO;;CAG3F,MAAa,qBAAqB,SAA6C;EAC7E,MAAM,EACJ,UACA,mCACA,SACA,+BACA,yBACA,+BACE;EAEJ,MAAM,SAAS,MAAM,KAAK,uBAAuB,oBAAoB,KAAK,cAAc,SAAS;AAEjG,SAAO,oCAAoC;AAC3C,SAAO,UAAU;AACjB,SAAO,gCAAgC;AACvC,SAAO,0BAA0B;AACjC,SAAO,6BAA6B;AAEpC,SAAO,KAAK,uBAAuB,aAAa,KAAK,cAAc,OAAO;;;;;;CAO5E,MAAa,+BACX,SACA;EACA,MAAM,EAAE,UAAU,GAAG,SAAS;EAC9B,MAAM,SAAS,MAAM,KAAK,uBAAuB,oBAAoB,KAAK,cAAc,SAAS;AACjG,SAAO,MAAM,KAAK,uBAAuB,+BAA+B,KAAK,cAAc;GAAE,GAAG;GAAM;GAAQ,CAAC;;;;;;;CAQjH,MAAa,sBAAsB,SAAwE;EACzG,MAAM,EAAE,UAAU,GAAG,SAAS;EAC9B,MAAM,SAAS,MAAM,KAAK,uBAAuB,oBAAoB,KAAK,cAAc,SAAS;AACjG,SAAO,MAAM,KAAK,uBAAuB,sBAAsB,KAAK,cAAc;GAAE,GAAG;GAAM;GAAQ,CAAC;;;;;CAMxG,MAAa,yBACX,SACA;EACA,MAAM,EAAE,mBAAmB,GAAG,SAAS;EACvC,MAAM,kBAAkB,MAAM,KAAK,uBAAuB,uBACxD,KAAK,cACL,kBACD;AAED,SAAO,MAAM,KAAK,uBAAuB,yBAAyB,KAAK,cAAc;GAAE,GAAG;GAAM;GAAiB,CAAC;;;;;CAMpH,MAAa,iCACX,SACA;EACA,MAAM,EAAE,mBAAmB,GAAG,SAAS;EACvC,MAAM,kBAAkB,MAAM,KAAK,uBAAuB,uBACxD,KAAK,cACL,kBACD;AAED,SAAO,MAAM,KAAK,uBAAuB,iCAAiC,KAAK,cAAc;GAC3F,GAAG;GACH;GACD,CAAC;;CAGJ,MAAa,kBAAkB,UAAkB;EAC/C,MAAM,SAAS,MAAM,KAAK,uBAAuB,oBAAoB,KAAK,cAAc,SAAS;AACjG,SAAO,KAAK,uBAAuB,kBAAkB,KAAK,cAAc,OAAO;;CAGjF,MAAa,uBAAuB,mBAA2B;AAC7D,SAAO,KAAK,uBAAuB,uBAAuB,KAAK,cAAc,kBAAkB;;;iCAnHlG,YAAY"}
@@ -334,7 +334,7 @@ type OpenId4VciCreateIssuerOptions = {
334
334
  */
335
335
  metadataSigner?: OpenId4VcJwtIssuer;
336
336
  };
337
- type OpenId4VcUpdateIssuerRecordOptions = Pick<OpenId4VcIssuerRecordProps, 'issuerId' | 'display' | 'dpopSigningAlgValuesSupported' | 'credentialConfigurationsSupported' | 'batchCredentialIssuance'>;
337
+ type OpenId4VcUpdateIssuerRecordOptions = Pick<OpenId4VcIssuerRecordProps, 'issuerId' | 'display' | 'dpopSigningAlgValuesSupported' | 'credentialConfigurationsSupported' | 'batchCredentialIssuance' | 'authorizationServerConfigs'>;
338
338
  //#endregion
339
339
  export { OpenId4VcUpdateIssuerRecordOptions, OpenId4VciAuthorizationCodeFlowConfig, OpenId4VciBatchCredentialIssuanceOptions, OpenId4VciCreateCredentialOfferOptions, OpenId4VciCreateCredentialResponseOptions, OpenId4VciCreateDeferredCredentialResponseOptions, OpenId4VciCreateIssuerOptions, OpenId4VciCreateStatelessCredentialOfferOptions, OpenId4VciCredentialRequestAuthorization, OpenId4VciCredentialRequestToCredentialMapper, OpenId4VciCredentialRequestToCredentialMapperOptions, OpenId4VciDeferredCredentialRequestToCredentialMapper, OpenId4VciDeferredCredentialRequestToCredentialMapperOptions, OpenId4VciDeferredCredentials, OpenId4VciGetVerificationSessionForIssuanceSessionAuthorization, OpenId4VciPreAuthorizedCodeFlowConfig, OpenId4VciSignCredentials, OpenId4VciSignMdocCredentials, OpenId4VciSignSdJwtCredentials, OpenId4VciSignW3cCredentials, OpenId4VciSignW3cV2Credentials, OpenId4VciVersion };
340
340
  //# sourceMappingURL=OpenId4VcIssuerServiceOptions.d.mts.map
@@ -20,6 +20,10 @@ async function handlePushedAuthorizationRequest(agentContext, options) {
20
20
  error: Oauth2ErrorCodes.InvalidScope,
21
21
  error_description: `Missing required 'scope' parameter`
22
22
  });
23
+ if (!parsedAuthorizationRequest.authorizationRequest.redirect_uri) throw new Oauth2ServerErrorResponseError({
24
+ error: Oauth2ErrorCodes.InvalidScope,
25
+ error_description: `Missing required 'redirect_uri' parameter.`
26
+ });
23
27
  const allowedStates = [OpenId4VcIssuanceSessionState.OfferCreated, OpenId4VcIssuanceSessionState.OfferUriRetrieved];
24
28
  if (!allowedStates.includes(issuanceSession.state)) throw new Oauth2ServerErrorResponseError({
25
29
  error: Oauth2ErrorCodes.InvalidRequest,
@@ -1 +1 @@
1
- {"version":3,"file":"pushedAuthorizationRequestEndpoint.mjs","names":["config"],"sources":["../../../src/openid4vc-issuer/router/pushedAuthorizationRequestEndpoint.ts"],"sourcesContent":["import { AgentContext, joinUriParts, utils } from '@credo-ts/core'\nimport type { HttpMethod, ParsePushedAuthorizationRequestResult, RequestLike } from '@openid4vc/oauth2'\nimport {\n Oauth2ErrorCodes,\n Oauth2ServerErrorResponseError,\n pushedAuthorizationRequestUriPrefix,\n} from '@openid4vc/oauth2'\nimport { addSecondsToDate } from '@openid4vc/utils'\nimport type { NextFunction, Response, Router } from 'express'\nimport type { OpenId4VciCredentialConfigurationsSupportedWithFormats } from '../../shared'\nimport {\n getAllowedAndRequestedScopeValues,\n getCredentialConfigurationsSupportedForScopes,\n getOfferedCredentials,\n getScopesFromCredentialConfigurationsSupported,\n} from '../../shared'\nimport {\n getRequestContext,\n sendJsonResponse,\n sendOauth2ErrorResponse,\n sendUnknownServerErrorResponse,\n} from '../../shared/router'\nimport { OpenId4VcIssuanceSessionState } from '../OpenId4VcIssuanceSessionState'\nimport { OpenId4VcIssuerModuleConfig } from '../OpenId4VcIssuerModuleConfig'\nimport { OpenId4VcIssuerService } from '../OpenId4VcIssuerService'\nimport { OpenId4VcIssuanceSessionRecord, OpenId4VcIssuerRecord } from '../repository'\nimport type { OpenId4VcIssuanceRequest } from './requestContext'\n\nexport async function handlePushedAuthorizationRequest(\n agentContext: AgentContext,\n options: {\n issuer: OpenId4VcIssuerRecord\n issuanceSession: OpenId4VcIssuanceSessionRecord\n parsedAuthorizationRequest: ParsePushedAuthorizationRequestResult\n request: RequestLike\n }\n) {\n const openId4VcIssuerService = agentContext.dependencyManager.resolve(OpenId4VcIssuerService)\n const config = agentContext.dependencyManager.resolve(OpenId4VcIssuerModuleConfig)\n\n const { issuanceSession, parsedAuthorizationRequest, issuer, request } = options\n const issuerMetadata = await openId4VcIssuerService.getIssuerMetadata(agentContext, issuer)\n\n if (!parsedAuthorizationRequest.authorizationRequest.scope) {\n throw new Oauth2ServerErrorResponseError({\n error: Oauth2ErrorCodes.InvalidScope,\n error_description: `Missing required 'scope' parameter`,\n })\n }\n\n const allowedStates = [OpenId4VcIssuanceSessionState.OfferCreated, OpenId4VcIssuanceSessionState.OfferUriRetrieved]\n if (!allowedStates.includes(issuanceSession.state)) {\n throw new Oauth2ServerErrorResponseError(\n {\n error: Oauth2ErrorCodes.InvalidRequest,\n error_description: `Invalid 'issuer_state' parameter`,\n },\n {\n internalMessage: `Issuance session '${issuanceSession.id}' has state '${\n issuanceSession.state\n }' but expected one of ${allowedStates.join(', ')}`,\n }\n )\n }\n\n if (!issuanceSession.chainedIdentity?.externalAuthorizationServerUrl) {\n throw new Oauth2ServerErrorResponseError(\n {\n error: Oauth2ErrorCodes.InvalidRequest,\n error_description: `Unexpected redirect call for session.`,\n },\n {\n internalMessage: `Issuance session '${issuanceSession.id}' is not configured to use chained identity for authorization.`,\n }\n )\n }\n\n const authorizationServer = openId4VcIssuerService.getOauth2AuthorizationServer(agentContext, {\n issuanceSessionId: issuanceSession.id,\n })\n\n const { clientAttestation, dpop } = await authorizationServer.verifyPushedAuthorizationRequest({\n authorizationRequest: parsedAuthorizationRequest.authorizationRequest,\n // First authorization server is the internal authorization server\n authorizationServerMetadata: issuerMetadata.authorizationServers[0],\n request,\n clientAttestation: {\n ...parsedAuthorizationRequest.clientAttestation,\n // First session config, fall back to global config\n required: issuanceSession.walletAttestation?.required ?? config.walletAttestationsRequired,\n },\n dpop: {\n ...parsedAuthorizationRequest.dpop,\n // First session config, fall back to global config\n required: issuanceSession.dpop?.required ?? config.dpopRequired,\n },\n })\n\n if (dpop) {\n // Bind dpop jwk thumbprint to session\n issuanceSession.dpop = {\n // If dpop is provided at the start, it's required from now on.\n required: true,\n dpopJkt: dpop.jwkThumbprint,\n }\n }\n\n if (clientAttestation) {\n issuanceSession.walletAttestation = {\n // If client attestation is provided at the start, it's required from now on.\n required: true,\n }\n }\n\n const offeredCredentialConfigurations = getOfferedCredentials(\n issuanceSession.credentialOfferPayload.credential_configuration_ids,\n issuerMetadata.credentialIssuer.credential_configurations_supported\n )\n const allowedScopes = getScopesFromCredentialConfigurationsSupported(offeredCredentialConfigurations)\n const requestedScopes = getAllowedAndRequestedScopeValues({\n allowedScopes,\n requestedScope: parsedAuthorizationRequest.authorizationRequest.scope,\n })\n const requestedCredentialConfigurations = getCredentialConfigurationsSupportedForScopes(\n offeredCredentialConfigurations,\n requestedScopes\n ) as OpenId4VciCredentialConfigurationsSupportedWithFormats\n if (requestedScopes.length === 0 || Object.keys(requestedCredentialConfigurations).length === 0) {\n throw new Oauth2ServerErrorResponseError({\n error: Oauth2ErrorCodes.InvalidScope,\n error_description: `No requested 'scope' values match with offered credential configurations.`,\n })\n }\n\n issuanceSession.authorization = {\n ...issuanceSession.authorization,\n scopes: requestedScopes,\n }\n\n // If client attestation is used we have verified this client_id matches with the sub\n // of the wallet attestation\n issuanceSession.clientId =\n clientAttestation?.clientAttestation.payload.sub ?? parsedAuthorizationRequest.authorizationRequest.client_id\n\n const oauth2Client = openId4VcIssuerService.getOauth2Client(agentContext, issuer)\n const authorizationServerUrl = issuanceSession.chainedIdentity.externalAuthorizationServerUrl\n\n const authorizationServerConfig = issuer.chainedAuthorizationServerConfigs?.find(\n (config) => config.issuer === authorizationServerUrl\n )\n if (!authorizationServerConfig) {\n throw new Oauth2ServerErrorResponseError(\n {\n error: Oauth2ErrorCodes.ServerError,\n },\n {\n internalMessage: `Issuer '${issuer.issuerId}' does not have a chained authorization server config for issuer '${authorizationServerUrl}'`,\n }\n )\n }\n\n const authorizationServerMetadata = await oauth2Client.fetchAuthorizationServerMetadata(\n authorizationServerConfig.issuer\n )\n if (!authorizationServerMetadata) {\n throw new Oauth2ServerErrorResponseError(\n {\n error: Oauth2ErrorCodes.ServerError,\n error_description: `Unable to retrieve authorization server metadata from external identity provider.`,\n },\n {\n internalMessage: `Unable to retrieve authorization server metadata from '${authorizationServerConfig.issuer}'`,\n }\n )\n }\n\n const redirectUri = joinUriParts(config.baseUrl, [issuer.issuerId, 'redirect'])\n const chainedIdentityState = utils.uuid()\n\n const scopes = requestedScopes.flatMap((scope) => {\n if (scope in authorizationServerConfig.scopesMapping) {\n return authorizationServerConfig.scopesMapping[scope]\n }\n\n throw new Oauth2ServerErrorResponseError(\n {\n error: Oauth2ErrorCodes.ServerError,\n },\n {\n internalMessage: `Issuer '${issuer.issuerId}' does not have a scope mapping for scope '${scope}' for external authorization server '${authorizationServerConfig.issuer}'`,\n }\n )\n })\n\n // TODO: add support for DPoP\n const { authorizationRequestUrl, pkce } = await oauth2Client.initiateAuthorization({\n authorizationServerMetadata,\n clientId: authorizationServerConfig.clientAuthentication.clientId,\n redirectUri,\n state: chainedIdentityState,\n scope: scopes.join(' '),\n })\n\n issuanceSession.chainedIdentity = {\n ...issuanceSession.chainedIdentity,\n requestUriReferenceValue: utils.uuid(),\n externalAuthorizationRequestUrl: authorizationRequestUrl,\n requestUriExpiresAt: addSecondsToDate(new Date(), config.requestUriExpiresInSeconds),\n pkceCodeVerifier: pkce?.codeVerifier,\n externalState: chainedIdentityState,\n state: parsedAuthorizationRequest.authorizationRequest.state,\n redirectUri: parsedAuthorizationRequest.authorizationRequest.redirect_uri,\n externalAuthorizationServerMetadata: authorizationServerMetadata,\n }\n\n const { pushedAuthorizationResponse } = authorizationServer.createPushedAuthorizationResponse({\n expiresInSeconds: config.requestUriExpiresInSeconds,\n requestUri: pushedAuthorizationRequestUriPrefix + issuanceSession.chainedIdentity.requestUriReferenceValue,\n })\n\n await openId4VcIssuerService.updateState(\n agentContext,\n issuanceSession,\n OpenId4VcIssuanceSessionState.AuthorizationInitiated\n )\n\n return { pushedAuthorizationResponse }\n}\n\nexport function configurePushedAuthorizationRequestEndpoint(router: Router, config: OpenId4VcIssuerModuleConfig) {\n router.post(\n config.pushedAuthorizationRequestEndpoint,\n async (request: OpenId4VcIssuanceRequest, response: Response, next: NextFunction) => {\n const requestContext = getRequestContext(request)\n const { agentContext, issuer } = requestContext\n\n try {\n const config = agentContext.dependencyManager.resolve(OpenId4VcIssuerModuleConfig)\n const openId4VcIssuerService = agentContext.dependencyManager.resolve(OpenId4VcIssuerService)\n const issuerMetadata = await openId4VcIssuerService.getIssuerMetadata(agentContext, issuer)\n const authorizationServer = openId4VcIssuerService.getOauth2AuthorizationServer(agentContext)\n const fullRequestUrl = joinUriParts(issuerMetadata.credentialIssuer.credential_issuer, [\n config.pushedAuthorizationRequestEndpoint,\n ])\n\n const requestLike = {\n headers: new Headers(request.headers as Record<string, string>),\n method: request.method as HttpMethod,\n url: fullRequestUrl,\n } as const\n\n const parseResult = await authorizationServer.parsePushedAuthorizationRequest({\n authorizationRequest: request.body,\n request: requestLike,\n })\n\n if (parseResult.authorizationRequestJwt) {\n throw new Oauth2ServerErrorResponseError({\n error: Oauth2ErrorCodes.InvalidRequest,\n error_description: `Using JWT-secured authorization request is not supported.`,\n })\n }\n\n // TODO: we could allow dynamic issuance sessions here. Maybe based on a callback?\n // Not sure how to decide which credentials are allowed to be requested dynamically\n if (!parseResult.authorizationRequest.issuer_state) {\n throw new Oauth2ServerErrorResponseError({\n error: Oauth2ErrorCodes.InvalidRequest,\n error_description: `Missing required 'issuer_state' parameter. Only requests initiated by a credential offer are supported for pushed authorization requests.`,\n })\n }\n\n if (!parseResult.authorizationRequest.scope) {\n throw new Oauth2ServerErrorResponseError({\n error: Oauth2ErrorCodes.InvalidScope,\n error_description: `Missing required 'scope' parameter`,\n })\n }\n\n const issuanceSession = await openId4VcIssuerService.findSingleIssuanceSessionByQuery(agentContext, {\n issuerId: issuer.issuerId,\n issuerState: parseResult.authorizationRequest.issuer_state,\n })\n\n if (!issuanceSession) {\n throw new Oauth2ServerErrorResponseError(\n {\n error: Oauth2ErrorCodes.InvalidRequest,\n error_description: `Invalid 'issuer_state' parameter`,\n },\n {\n internalMessage: `Issuance session not found for 'issuer_state' parameter '${parseResult.authorizationRequest.issuer_state}'`,\n }\n )\n }\n\n const { pushedAuthorizationResponse } = await handlePushedAuthorizationRequest(agentContext, {\n issuanceSession,\n issuer,\n parsedAuthorizationRequest: parseResult,\n request: requestLike,\n })\n\n return sendJsonResponse(response, next, pushedAuthorizationResponse)\n } catch (error) {\n if (error instanceof Oauth2ServerErrorResponseError) {\n return sendOauth2ErrorResponse(response, next, agentContext.config.logger, error)\n }\n return sendUnknownServerErrorResponse(response, next, agentContext.config.logger, error)\n }\n }\n )\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"pushedAuthorizationRequestEndpoint.mjs","names":["config"],"sources":["../../../src/openid4vc-issuer/router/pushedAuthorizationRequestEndpoint.ts"],"sourcesContent":["import { AgentContext, joinUriParts, utils } from '@credo-ts/core'\nimport type { HttpMethod, ParsePushedAuthorizationRequestResult, RequestLike } from '@openid4vc/oauth2'\nimport {\n Oauth2ErrorCodes,\n Oauth2ServerErrorResponseError,\n pushedAuthorizationRequestUriPrefix,\n} from '@openid4vc/oauth2'\nimport { addSecondsToDate } from '@openid4vc/utils'\nimport type { NextFunction, Response, Router } from 'express'\nimport type { OpenId4VciCredentialConfigurationsSupportedWithFormats } from '../../shared'\nimport {\n getAllowedAndRequestedScopeValues,\n getCredentialConfigurationsSupportedForScopes,\n getOfferedCredentials,\n getScopesFromCredentialConfigurationsSupported,\n} from '../../shared'\nimport {\n getRequestContext,\n sendJsonResponse,\n sendOauth2ErrorResponse,\n sendUnknownServerErrorResponse,\n} from '../../shared/router'\nimport { OpenId4VcIssuanceSessionState } from '../OpenId4VcIssuanceSessionState'\nimport { OpenId4VcIssuerModuleConfig } from '../OpenId4VcIssuerModuleConfig'\nimport { OpenId4VcIssuerService } from '../OpenId4VcIssuerService'\nimport { OpenId4VcIssuanceSessionRecord, OpenId4VcIssuerRecord } from '../repository'\nimport type { OpenId4VcIssuanceRequest } from './requestContext'\n\nexport async function handlePushedAuthorizationRequest(\n agentContext: AgentContext,\n options: {\n issuer: OpenId4VcIssuerRecord\n issuanceSession: OpenId4VcIssuanceSessionRecord\n parsedAuthorizationRequest: ParsePushedAuthorizationRequestResult\n request: RequestLike\n }\n) {\n const openId4VcIssuerService = agentContext.dependencyManager.resolve(OpenId4VcIssuerService)\n const config = agentContext.dependencyManager.resolve(OpenId4VcIssuerModuleConfig)\n\n const { issuanceSession, parsedAuthorizationRequest, issuer, request } = options\n const issuerMetadata = await openId4VcIssuerService.getIssuerMetadata(agentContext, issuer)\n\n if (!parsedAuthorizationRequest.authorizationRequest.scope) {\n throw new Oauth2ServerErrorResponseError({\n error: Oauth2ErrorCodes.InvalidScope,\n error_description: `Missing required 'scope' parameter`,\n })\n }\n\n if (!parsedAuthorizationRequest.authorizationRequest.redirect_uri) {\n throw new Oauth2ServerErrorResponseError({\n error: Oauth2ErrorCodes.InvalidScope,\n error_description: `Missing required 'redirect_uri' parameter.`,\n })\n }\n\n const allowedStates = [OpenId4VcIssuanceSessionState.OfferCreated, OpenId4VcIssuanceSessionState.OfferUriRetrieved]\n if (!allowedStates.includes(issuanceSession.state)) {\n throw new Oauth2ServerErrorResponseError(\n {\n error: Oauth2ErrorCodes.InvalidRequest,\n error_description: `Invalid 'issuer_state' parameter`,\n },\n {\n internalMessage: `Issuance session '${issuanceSession.id}' has state '${\n issuanceSession.state\n }' but expected one of ${allowedStates.join(', ')}`,\n }\n )\n }\n\n if (!issuanceSession.chainedIdentity?.externalAuthorizationServerUrl) {\n throw new Oauth2ServerErrorResponseError(\n {\n error: Oauth2ErrorCodes.InvalidRequest,\n error_description: `Unexpected redirect call for session.`,\n },\n {\n internalMessage: `Issuance session '${issuanceSession.id}' is not configured to use chained identity for authorization.`,\n }\n )\n }\n\n const authorizationServer = openId4VcIssuerService.getOauth2AuthorizationServer(agentContext, {\n issuanceSessionId: issuanceSession.id,\n })\n\n const { clientAttestation, dpop } = await authorizationServer.verifyPushedAuthorizationRequest({\n authorizationRequest: parsedAuthorizationRequest.authorizationRequest,\n // First authorization server is the internal authorization server\n authorizationServerMetadata: issuerMetadata.authorizationServers[0],\n request,\n clientAttestation: {\n ...parsedAuthorizationRequest.clientAttestation,\n // First session config, fall back to global config\n required: issuanceSession.walletAttestation?.required ?? config.walletAttestationsRequired,\n },\n dpop: {\n ...parsedAuthorizationRequest.dpop,\n // First session config, fall back to global config\n required: issuanceSession.dpop?.required ?? config.dpopRequired,\n },\n })\n\n if (dpop) {\n // Bind dpop jwk thumbprint to session\n issuanceSession.dpop = {\n // If dpop is provided at the start, it's required from now on.\n required: true,\n dpopJkt: dpop.jwkThumbprint,\n }\n }\n\n if (clientAttestation) {\n issuanceSession.walletAttestation = {\n // If client attestation is provided at the start, it's required from now on.\n required: true,\n }\n }\n\n const offeredCredentialConfigurations = getOfferedCredentials(\n issuanceSession.credentialOfferPayload.credential_configuration_ids,\n issuerMetadata.credentialIssuer.credential_configurations_supported\n )\n const allowedScopes = getScopesFromCredentialConfigurationsSupported(offeredCredentialConfigurations)\n const requestedScopes = getAllowedAndRequestedScopeValues({\n allowedScopes,\n requestedScope: parsedAuthorizationRequest.authorizationRequest.scope,\n })\n const requestedCredentialConfigurations = getCredentialConfigurationsSupportedForScopes(\n offeredCredentialConfigurations,\n requestedScopes\n ) as OpenId4VciCredentialConfigurationsSupportedWithFormats\n if (requestedScopes.length === 0 || Object.keys(requestedCredentialConfigurations).length === 0) {\n throw new Oauth2ServerErrorResponseError({\n error: Oauth2ErrorCodes.InvalidScope,\n error_description: `No requested 'scope' values match with offered credential configurations.`,\n })\n }\n\n issuanceSession.authorization = {\n ...issuanceSession.authorization,\n scopes: requestedScopes,\n }\n\n // If client attestation is used we have verified this client_id matches with the sub\n // of the wallet attestation\n issuanceSession.clientId =\n clientAttestation?.clientAttestation.payload.sub ?? parsedAuthorizationRequest.authorizationRequest.client_id\n\n const oauth2Client = openId4VcIssuerService.getOauth2Client(agentContext, issuer)\n const authorizationServerUrl = issuanceSession.chainedIdentity.externalAuthorizationServerUrl\n\n const authorizationServerConfig = issuer.chainedAuthorizationServerConfigs?.find(\n (config) => config.issuer === authorizationServerUrl\n )\n if (!authorizationServerConfig) {\n throw new Oauth2ServerErrorResponseError(\n {\n error: Oauth2ErrorCodes.ServerError,\n },\n {\n internalMessage: `Issuer '${issuer.issuerId}' does not have a chained authorization server config for issuer '${authorizationServerUrl}'`,\n }\n )\n }\n\n const authorizationServerMetadata = await oauth2Client.fetchAuthorizationServerMetadata(\n authorizationServerConfig.issuer\n )\n if (!authorizationServerMetadata) {\n throw new Oauth2ServerErrorResponseError(\n {\n error: Oauth2ErrorCodes.ServerError,\n error_description: `Unable to retrieve authorization server metadata from external identity provider.`,\n },\n {\n internalMessage: `Unable to retrieve authorization server metadata from '${authorizationServerConfig.issuer}'`,\n }\n )\n }\n\n const redirectUri = joinUriParts(config.baseUrl, [issuer.issuerId, 'redirect'])\n const chainedIdentityState = utils.uuid()\n\n const scopes = requestedScopes.flatMap((scope) => {\n if (scope in authorizationServerConfig.scopesMapping) {\n return authorizationServerConfig.scopesMapping[scope]\n }\n\n throw new Oauth2ServerErrorResponseError(\n {\n error: Oauth2ErrorCodes.ServerError,\n },\n {\n internalMessage: `Issuer '${issuer.issuerId}' does not have a scope mapping for scope '${scope}' for external authorization server '${authorizationServerConfig.issuer}'`,\n }\n )\n })\n\n // TODO: add support for DPoP\n const { authorizationRequestUrl, pkce } = await oauth2Client.initiateAuthorization({\n authorizationServerMetadata,\n clientId: authorizationServerConfig.clientAuthentication.clientId,\n redirectUri,\n state: chainedIdentityState,\n scope: scopes.join(' '),\n })\n\n issuanceSession.chainedIdentity = {\n ...issuanceSession.chainedIdentity,\n requestUriReferenceValue: utils.uuid(),\n externalAuthorizationRequestUrl: authorizationRequestUrl,\n requestUriExpiresAt: addSecondsToDate(new Date(), config.requestUriExpiresInSeconds),\n pkceCodeVerifier: pkce?.codeVerifier,\n externalState: chainedIdentityState,\n state: parsedAuthorizationRequest.authorizationRequest.state,\n redirectUri: parsedAuthorizationRequest.authorizationRequest.redirect_uri,\n externalAuthorizationServerMetadata: authorizationServerMetadata,\n }\n\n const { pushedAuthorizationResponse } = authorizationServer.createPushedAuthorizationResponse({\n expiresInSeconds: config.requestUriExpiresInSeconds,\n requestUri: pushedAuthorizationRequestUriPrefix + issuanceSession.chainedIdentity.requestUriReferenceValue,\n })\n\n await openId4VcIssuerService.updateState(\n agentContext,\n issuanceSession,\n OpenId4VcIssuanceSessionState.AuthorizationInitiated\n )\n\n return { pushedAuthorizationResponse }\n}\n\nexport function configurePushedAuthorizationRequestEndpoint(router: Router, config: OpenId4VcIssuerModuleConfig) {\n router.post(\n config.pushedAuthorizationRequestEndpoint,\n async (request: OpenId4VcIssuanceRequest, response: Response, next: NextFunction) => {\n const requestContext = getRequestContext(request)\n const { agentContext, issuer } = requestContext\n\n try {\n const config = agentContext.dependencyManager.resolve(OpenId4VcIssuerModuleConfig)\n const openId4VcIssuerService = agentContext.dependencyManager.resolve(OpenId4VcIssuerService)\n const issuerMetadata = await openId4VcIssuerService.getIssuerMetadata(agentContext, issuer)\n const authorizationServer = openId4VcIssuerService.getOauth2AuthorizationServer(agentContext)\n const fullRequestUrl = joinUriParts(issuerMetadata.credentialIssuer.credential_issuer, [\n config.pushedAuthorizationRequestEndpoint,\n ])\n\n const requestLike = {\n headers: new Headers(request.headers as Record<string, string>),\n method: request.method as HttpMethod,\n url: fullRequestUrl,\n } as const\n\n const parseResult = await authorizationServer.parsePushedAuthorizationRequest({\n authorizationRequest: request.body,\n request: requestLike,\n })\n\n if (parseResult.authorizationRequestJwt) {\n throw new Oauth2ServerErrorResponseError({\n error: Oauth2ErrorCodes.InvalidRequest,\n error_description: `Using JWT-secured authorization request is not supported.`,\n })\n }\n\n // TODO: we could allow dynamic issuance sessions here. Maybe based on a callback?\n // Not sure how to decide which credentials are allowed to be requested dynamically\n if (!parseResult.authorizationRequest.issuer_state) {\n throw new Oauth2ServerErrorResponseError({\n error: Oauth2ErrorCodes.InvalidRequest,\n error_description: `Missing required 'issuer_state' parameter. Only requests initiated by a credential offer are supported for pushed authorization requests.`,\n })\n }\n\n if (!parseResult.authorizationRequest.scope) {\n throw new Oauth2ServerErrorResponseError({\n error: Oauth2ErrorCodes.InvalidScope,\n error_description: `Missing required 'scope' parameter`,\n })\n }\n\n const issuanceSession = await openId4VcIssuerService.findSingleIssuanceSessionByQuery(agentContext, {\n issuerId: issuer.issuerId,\n issuerState: parseResult.authorizationRequest.issuer_state,\n })\n\n if (!issuanceSession) {\n throw new Oauth2ServerErrorResponseError(\n {\n error: Oauth2ErrorCodes.InvalidRequest,\n error_description: `Invalid 'issuer_state' parameter`,\n },\n {\n internalMessage: `Issuance session not found for 'issuer_state' parameter '${parseResult.authorizationRequest.issuer_state}'`,\n }\n )\n }\n\n const { pushedAuthorizationResponse } = await handlePushedAuthorizationRequest(agentContext, {\n issuanceSession,\n issuer,\n parsedAuthorizationRequest: parseResult,\n request: requestLike,\n })\n\n return sendJsonResponse(response, next, pushedAuthorizationResponse)\n } catch (error) {\n if (error instanceof Oauth2ServerErrorResponseError) {\n return sendOauth2ErrorResponse(response, next, agentContext.config.logger, error)\n }\n return sendUnknownServerErrorResponse(response, next, agentContext.config.logger, error)\n }\n }\n )\n}\n"],"mappings":"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"}
package/package.json CHANGED
@@ -4,7 +4,7 @@
4
4
  ".": "./build/index.mjs",
5
5
  "./package.json": "./package.json"
6
6
  },
7
- "version": "0.6.1-alpha-20251208105733",
7
+ "version": "0.6.1-alpha-20251209100250",
8
8
  "files": [
9
9
  "build"
10
10
  ],
@@ -36,12 +36,12 @@
36
36
  "@openid4vc/utils": "^0.4.1",
37
37
  "@types/express": "^5.0.6",
38
38
  "express": "^5.2.0",
39
- "@credo-ts/core": "0.6.1-alpha-20251208105733"
39
+ "@credo-ts/core": "0.6.1-alpha-20251209100250"
40
40
  },
41
41
  "devDependencies": {
42
42
  "nock": "^14.0.10",
43
43
  "typescript": "~5.9.3",
44
- "@credo-ts/tenants": "0.6.1-alpha-20251208105733"
44
+ "@credo-ts/tenants": "0.6.1-alpha-20251209100250"
45
45
  },
46
46
  "scripts": {
47
47
  "build": "tsdown --config-loader unconfig"