@sphereon/ssi-sdk.siopv2-oid4vp-rp-rest-api 0.34.1-feature.SSISDK.45.94 → 0.34.1-feature.SSISDK.46.41

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sphereon/ssi-sdk.siopv2-oid4vp-rp-rest-api",
3
- "version": "0.34.1-feature.SSISDK.45.94+24a0078a",
3
+ "version": "0.34.1-feature.SSISDK.46.41+1e7378b3",
4
4
  "source": "src/index.ts",
5
5
  "type": "module",
6
6
  "main": "./dist/index.cjs",
@@ -23,39 +23,42 @@
23
23
  "start:dev": "ts-node __tests__/RestAPI.ts"
24
24
  },
25
25
  "dependencies": {
26
- "@sphereon/did-auth-siop": "0.19.1-feature.SSISDK.45.91",
27
- "@sphereon/ssi-express-support": "0.34.1-feature.SSISDK.45.94+24a0078a",
28
- "@sphereon/ssi-sdk.core": "0.34.1-feature.SSISDK.45.94+24a0078a",
29
- "@sphereon/ssi-sdk.credential-validation": "0.34.1-feature.SSISDK.45.94+24a0078a",
30
- "@sphereon/ssi-sdk.kv-store-temp": "0.34.1-feature.SSISDK.45.94+24a0078a",
31
- "@sphereon/ssi-sdk.pd-manager": "0.34.1-feature.SSISDK.45.94+24a0078a",
32
- "@sphereon/ssi-sdk.presentation-exchange": "0.34.1-feature.SSISDK.45.94+24a0078a",
33
- "@sphereon/ssi-sdk.siopv2-oid4vp-common": "0.34.1-feature.SSISDK.45.94+24a0078a",
34
- "@sphereon/ssi-sdk.siopv2-oid4vp-rp-auth": "0.34.1-feature.SSISDK.45.94+24a0078a",
35
- "@sphereon/ssi-types": "0.34.1-feature.SSISDK.45.94+24a0078a",
26
+ "@sphereon/did-auth-siop": "0.19.1-feature.SSISDK.46.5",
27
+ "@sphereon/ssi-express-support": "0.34.1-feature.SSISDK.46.41+1e7378b3",
28
+ "@sphereon/ssi-sdk.core": "0.34.1-feature.SSISDK.46.41+1e7378b3",
29
+ "@sphereon/ssi-sdk.credential-validation": "0.34.1-feature.SSISDK.46.41+1e7378b3",
30
+ "@sphereon/ssi-sdk.kv-store-temp": "0.34.1-feature.SSISDK.46.41+1e7378b3",
31
+ "@sphereon/ssi-sdk.pd-manager": "0.34.1-feature.SSISDK.46.41+1e7378b3",
32
+ "@sphereon/ssi-sdk.presentation-exchange": "0.34.1-feature.SSISDK.46.41+1e7378b3",
33
+ "@sphereon/ssi-sdk.siopv2-oid4vp-common": "0.34.1-feature.SSISDK.46.41+1e7378b3",
34
+ "@sphereon/ssi-sdk.siopv2-oid4vp-rp-auth": "0.34.1-feature.SSISDK.46.41+1e7378b3",
35
+ "@sphereon/ssi-types": "0.34.1-feature.SSISDK.46.41+1e7378b3",
36
36
  "@veramo/core": "4.2.0",
37
37
  "@veramo/credential-w3c": "4.2.0",
38
38
  "awesome-qr": "^2.1.5-rc.0",
39
39
  "body-parser": "^1.20.2",
40
40
  "cookie-parser": "^1.4.6",
41
41
  "cors": "^2.8.5",
42
- "cross-fetch": "^4.1.0",
42
+ "cross-fetch": "^3.1.8",
43
43
  "dotenv-flow": "^3.3.0",
44
44
  "express": "^4.19.2",
45
45
  "short-uuid": "^4.2.2",
46
46
  "swagger-ui-express": "^5.0.1",
47
- "uuid": "^9.0.1"
47
+ "uuid": "^9.0.1",
48
+ "zod": "^4.1.5"
48
49
  },
49
50
  "devDependencies": {
50
51
  "@decentralized-identity/ion-sdk": "^0.6.0",
51
- "@sphereon/did-auth-siop-adapter": "0.19.1-feature.SSISDK.45.91",
52
+ "@sphereon/did-auth-siop-adapter": "0.19.1-feature.SSISDK.46.5",
52
53
  "@sphereon/did-uni-client": "^0.6.3",
53
54
  "@sphereon/pex": "5.0.0-unstable.28",
54
55
  "@sphereon/pex-models": "^2.3.2",
55
- "@sphereon/ssi-sdk-ext.did-provider-jwk": "0.34.1-feature.SSISDK.45.94+24a0078a",
56
- "@sphereon/ssi-sdk.credential-vcdm": "0.34.1-feature.SSISDK.45.94+24a0078a",
57
- "@sphereon/ssi-sdk.credential-vcdm-jsonld-provider": "0.34.1-feature.SSISDK.45.94+24a0078a",
58
- "@sphereon/ssi-sdk.data-store": "0.34.1-feature.SSISDK.45.94+24a0078a",
56
+ "@sphereon/ssi-sdk-ext.did-provider-jwk": "0.34.1-feature.SSISDK.46.41+1e7378b3",
57
+ "@sphereon/ssi-sdk-ext.identifier-resolution": "0.34.1-feature.SSISDK.46.41+1e7378b3",
58
+ "@sphereon/ssi-sdk-ext.jwt-service": "0.34.1-feature.SSISDK.46.41+1e7378b3",
59
+ "@sphereon/ssi-sdk.credential-vcdm": "0.34.1-feature.SSISDK.46.41+1e7378b3",
60
+ "@sphereon/ssi-sdk.credential-vcdm-jsonld-provider": "0.34.1-feature.SSISDK.46.41+1e7378b3",
61
+ "@sphereon/ssi-sdk.data-store": "0.34.1-feature.SSISDK.46.41+1e7378b3",
59
62
  "@types/body-parser": "^1.19.5",
60
63
  "@types/cookie-parser": "^1.4.7",
61
64
  "@types/cors": "^2.8.17",
@@ -114,5 +117,5 @@
114
117
  "OpenID Connect",
115
118
  "Authenticator"
116
119
  ],
117
- "gitHead": "24a0078a739502cd84e93cc2d4c3938c8854087a"
120
+ "gitHead": "1e7378b3f12474c82c0563d3fd8d73f5452aa410"
118
121
  }
package/src/index.ts CHANGED
@@ -2,6 +2,6 @@
2
2
  * @public
3
3
  */
4
4
  export * from './siop-api-functions'
5
- export * from './webapp-api-functions'
5
+ export * from './universal-oid4vp-api-functions'
6
6
  export * from './types'
7
7
  export * from './siopv2-rp-api-server'
@@ -0,0 +1,20 @@
1
+ import { Request, Response, NextFunction } from 'express';
2
+ import { z, ZodError } from 'zod';
3
+
4
+ export const validateData = (schema: z.ZodObject<any, any>) => {
5
+ return (req: Request, res: Response, next: NextFunction) => {
6
+ try {
7
+ schema.parse(req.body);
8
+ next();
9
+ } catch (error) {
10
+ if (error instanceof ZodError) {
11
+ const errorMessages = error.issues.map((issue: any) => ({
12
+ message: `${issue.path.join('.')} is ${issue.message}`,
13
+ }))
14
+ res.status(400).json({ status: 400, message: 'Invalid data', error_details: errorMessages[0].message });
15
+ } else {
16
+ res.status(500).json({ status: 500, message: 'Internal Server Error' });
17
+ }
18
+ }
19
+ };
20
+ }
@@ -0,0 +1,50 @@
1
+ import { z } from 'zod';
2
+ import {
3
+ authorizationRequestStatuses,
4
+ authorizationResponseStatuses
5
+ } from '@sphereon/ssi-sdk.siopv2-oid4vp-common'
6
+ import { ResponseMode, ResponseType, RequestUriMethod } from '@sphereon/did-auth-siop'
7
+
8
+ export const ResponseTypeSchema = z.enum([ResponseType.VP_TOKEN]);
9
+
10
+ export const ResponseModeSchema = z.enum([ResponseMode.DIRECT_POST, ResponseMode.DIRECT_POST_JWT]);
11
+
12
+ export const RequestUriMethodSchema = z.enum([RequestUriMethod.GET, RequestUriMethod.POST]);
13
+
14
+ export const AuthorizationStatusSchema = z.enum([
15
+ ...authorizationRequestStatuses,
16
+ ...authorizationResponseStatuses
17
+ ]);
18
+
19
+ export const CallbackOptsSchema = z.object({
20
+ url: z.string(),
21
+ status: z.array(AuthorizationStatusSchema).optional(),
22
+ });
23
+
24
+ export const QRCodeOptsSchema = z.object({
25
+ size: z.number().optional(),
26
+ color_dark: z.string().optional(),
27
+ color_light: z.string().optional(),
28
+ });
29
+
30
+ export const CreateAuthorizationRequestBodySchema = z.object({
31
+ query_id: z.string(),
32
+ client_id: z.string().optional(),
33
+ request_uri_base: z.string().optional(),
34
+ correlation_id: z.string().optional(),
35
+ request_uri_method: RequestUriMethodSchema.optional(),
36
+ response_type: ResponseTypeSchema.optional(),
37
+ response_mode: ResponseModeSchema.optional(),
38
+ transaction_data: z.array(z.string()).optional(),
39
+ qr_code: QRCodeOptsSchema.optional(),
40
+ direct_post_response_redirect_uri: z.string().optional(),
41
+ callback: CallbackOptsSchema.optional(),
42
+ });
43
+
44
+ export const CreateAuthorizationResponseSchema = z.object({
45
+ correlation_id: z.string(),
46
+ query_id: z.string(),
47
+ request_uri: z.string(),
48
+ status_uri: z.string(),
49
+ qr_uri: z.string().optional(),
50
+ });
@@ -1,4 +1,4 @@
1
- import { AuthorizationResponsePayload } from '@sphereon/did-auth-siop'
1
+ import { AuthorizationResponsePayload, PresentationDefinitionLocation } from '@sphereon/did-auth-siop'
2
2
  import { checkAuth, ISingleEndpointOpts, sendErrorResponse } from '@sphereon/ssi-express-support'
3
3
  import { CredentialMapper } from '@sphereon/ssi-types'
4
4
  import { AuthorizationChallengeValidationResponse } from '@sphereon/ssi-sdk.siopv2-oid4vp-common'
@@ -41,7 +41,11 @@ const parseAuthorizationResponse = (request: Request): AuthorizationResponsePayl
41
41
  )
42
42
  }
43
43
 
44
- export function verifyAuthResponseSIOPv2Endpoint(router: Router, context: IRequiredContext, opts?: ISingleEndpointOpts) {
44
+ export function verifyAuthResponseSIOPv2Endpoint(
45
+ router: Router,
46
+ context: IRequiredContext,
47
+ opts?: ISingleEndpointOpts & { presentationDefinitionLocation?: PresentationDefinitionLocation },
48
+ ) {
45
49
  if (opts?.enabled === false) {
46
50
  console.log(`verifyAuthResponse SIOP endpoint is disabled`)
47
51
  return
@@ -49,7 +53,7 @@ export function verifyAuthResponseSIOPv2Endpoint(router: Router, context: IRequi
49
53
  const path = opts?.path ?? '/siop/definitions/:definitionId/auth-responses/:correlationId'
50
54
  router.post(path, checkAuth(opts?.endpoint), async (request: Request, response: Response) => {
51
55
  try {
52
- const { correlationId, definitionId, tenantId, version, credentialQueryId } = request.params // TODO Can credentialQueryId be a request param
56
+ const { correlationId, definitionId, tenantId, version } = request.params
53
57
  if (!correlationId || !definitionId) {
54
58
  console.log(`No authorization request could be found for the given url. correlationId: ${correlationId}, definitionId: ${definitionId}`)
55
59
  return sendErrorResponse(response, 404, 'No authorization request could be found')
@@ -71,11 +75,17 @@ export function verifyAuthResponseSIOPv2Endpoint(router: Router, context: IRequi
71
75
  const verifiedResponse = await context.agent.siopVerifyAuthResponse({
72
76
  authorizationResponse,
73
77
  correlationId,
74
- definitionId,
78
+ queryId: definitionId,
79
+ presentationDefinitions: [
80
+ {
81
+ location: opts?.presentationDefinitionLocation ?? PresentationDefinitionLocation.TOPLEVEL_PRESENTATION_DEF,
82
+ definition: definitionItem.definitionPayload,
83
+ },
84
+ ],
75
85
  dcqlQuery: definitionItem.dcqlPayload,
76
86
  })
77
87
 
78
- const wrappedPresentation = verifiedResponse?.oid4vpSubmission?.presentation[credentialQueryId]
88
+ const wrappedPresentation = verifiedResponse?.oid4vpSubmission?.presentations[0]
79
89
  if (wrappedPresentation) {
80
90
  // const credentialSubject = wrappedPresentation.presentation.verifiableCredential[0]?.credential?.credentialSubject
81
91
  // console.log(JSON.stringify(credentialSubject, null, 2))
@@ -90,7 +100,7 @@ export function verifyAuthResponseSIOPv2Endpoint(router: Router, context: IRequi
90
100
  return response.send(JSON.stringify(authorizationChallengeValidationResponse))
91
101
  }
92
102
 
93
- const responseRedirectURI = await context.agent.siopGetRedirectURI({ correlationId, definitionId, state: verifiedResponse.state })
103
+ const responseRedirectURI = await context.agent.siopGetRedirectURI({ correlationId, queryId: definitionId, state: verifiedResponse.state })
94
104
  if (responseRedirectURI) {
95
105
  response.setHeader('Content-Type', 'application/json')
96
106
  return response.send(JSON.stringify({ redirect_uri: responseRedirectURI }))
@@ -125,7 +135,7 @@ export function getAuthRequestSIOPv2Endpoint(router: Router, context: IRequiredC
125
135
  }
126
136
  const requestState = await context.agent.siopGetAuthRequestState({
127
137
  correlationId,
128
- definitionId,
138
+ queryId: definitionId,
129
139
  errorOnNotFound: false,
130
140
  })
131
141
  if (!requestState) {
@@ -149,8 +159,8 @@ export function getAuthRequestSIOPv2Endpoint(router: Router, context: IRequiredC
149
159
  } finally {
150
160
  await context.agent.siopUpdateAuthRequestState({
151
161
  correlationId,
152
- definitionId,
153
- state: 'sent',
162
+ queryId: definitionId,
163
+ state: 'authorization_request_created',
154
164
  error,
155
165
  })
156
166
  }
@@ -7,11 +7,11 @@ import express, { Express, Request, Response, Router } from 'express'
7
7
  import { getAuthRequestSIOPv2Endpoint, verifyAuthResponseSIOPv2Endpoint } from './siop-api-functions'
8
8
  import { IRequiredPlugins, ISIOPv2RPRestAPIOpts } from './types'
9
9
  import {
10
- authStatusWebappEndpoint,
11
- createAuthRequestWebappEndpoint,
10
+ authStatusUniversalOID4VPEndpoint,
11
+ createAuthRequestUniversalOID4VPEndpoint,
12
12
  getDefinitionsEndpoint,
13
- removeAuthRequestStateWebappEndpoint,
14
- } from './webapp-api-functions'
13
+ removeAuthRequestStateUniversalOID4VPEndpoint,
14
+ } from './universal-oid4vp-api-functions'
15
15
  import swaggerUi from 'swagger-ui-express'
16
16
 
17
17
  export class SIOPv2RPApiServer {
@@ -40,9 +40,9 @@ export class SIOPv2RPApiServer {
40
40
 
41
41
  // Webapp endpoints
42
42
  if (features.includes('rp-status')) {
43
- createAuthRequestWebappEndpoint(this._router, context, opts?.endpointOpts?.webappCreateAuthRequest)
44
- authStatusWebappEndpoint(this._router, context, opts?.endpointOpts?.webappAuthStatus)
45
- removeAuthRequestStateWebappEndpoint(this._router, context, opts?.endpointOpts?.webappDeleteAuthRequest)
43
+ createAuthRequestUniversalOID4VPEndpoint(this._router, context, opts?.endpointOpts?.webappCreateAuthRequest)
44
+ authStatusUniversalOID4VPEndpoint(this._router, context, opts?.endpointOpts?.webappAuthStatus)
45
+ removeAuthRequestStateUniversalOID4VPEndpoint(this._router, context, opts?.endpointOpts?.webappDeleteAuthRequest)
46
46
  getDefinitionsEndpoint(this._router, context, opts?.endpointOpts?.webappGetDefinitions)
47
47
  }
48
48
 
@@ -1,11 +1,17 @@
1
+ import { IAgentContext, ICredentialVerifier } from '@veramo/core'
1
2
  import { GenericAuthArgs, ISingleEndpointOpts } from '@sphereon/ssi-express-support'
2
3
  import { IPresentationExchange } from '@sphereon/ssi-sdk.presentation-exchange'
3
4
  import { ISIOPv2RP } from '@sphereon/ssi-sdk.siopv2-oid4vp-rp-auth'
4
- import { IAgentContext, ICredentialVerifier } from '@veramo/core'
5
5
  import { IPDManager } from '@sphereon/ssi-sdk.pd-manager'
6
+ import { AdditionalClaims } from '@sphereon/ssi-types'
7
+ import { AuthorizationRequestStateStatus, AuthorizationResponseStateStatus } from '@sphereon/ssi-sdk.siopv2-oid4vp-common'
8
+ import { Request, Response } from 'express'
9
+ import { z } from 'zod'
10
+ import { CreateAuthorizationRequestBodySchema, CreateAuthorizationResponseSchema } from '../schemas'
6
11
  import { QRCodeOpts } from './QRCode.types'
7
12
 
8
13
  export type SiopFeatures = 'rp-status' | 'siop'
14
+
9
15
  export interface ISIOPv2RPRestAPIOpts {
10
16
  enableFeatures?: SiopFeatures[]
11
17
  endpointOpts?: {
@@ -30,3 +36,38 @@ export interface ICreateAuthRequestWebappEndpointOpts extends ISingleEndpointOpt
30
36
 
31
37
  export type IRequiredPlugins = ICredentialVerifier & ISIOPv2RP & IPresentationExchange & IPDManager
32
38
  export type IRequiredContext = IAgentContext<IRequiredPlugins>
39
+
40
+ export type CreateAuthorizationRequest = Request<Record<string, never>, any, CreateAuthorizationRequestBody, Record<string, never>>
41
+
42
+ export type CreateAuthorizationRequestBody = z.infer<typeof CreateAuthorizationRequestBodySchema>;
43
+
44
+ export type CreateAuthorizationResponse = Response<CreateAuthorizationRequestResponse>
45
+
46
+ export type CreateAuthorizationRequestResponse = z.infer<typeof CreateAuthorizationResponseSchema>;
47
+
48
+ export type DeleteAuthorizationRequest = Request<DeleteAuthorizationRequestPathParameters, any, Record<string, any>, Record<string, any>>
49
+
50
+ export type DeleteAuthorizationRequestPathParameters = {
51
+ correlationId: string;
52
+ }
53
+
54
+ export type GetAuthorizationRequestStatus = Request<GetAuthorizationRequestStatusPathParameters, any, Record<string, any>, Record<string, any>>
55
+
56
+ export type GetAuthorizationRequestStatusPathParameters = {
57
+ correlationId: string;
58
+ }
59
+
60
+ export type RequestError = {
61
+ status: number
62
+ message: string
63
+ error_details?: string
64
+ }
65
+
66
+ export interface GetAuthStatusResponse {
67
+ status: AuthorizationRequestStateStatus | AuthorizationResponseStateStatus
68
+ correlation_id: string
69
+ query_id: string
70
+ last_updated: number
71
+ verified_data?: AdditionalClaims
72
+ error?: RequestError
73
+ }
@@ -0,0 +1,172 @@
1
+ import { AuthorizationResponseStateStatus } from '@sphereon/did-auth-siop'
2
+ import { checkAuth, ISingleEndpointOpts, sendErrorResponse } from '@sphereon/ssi-express-support'
3
+ import { uriWithBase } from '@sphereon/ssi-sdk.siopv2-oid4vp-common'
4
+ import { Request, Response, Router } from 'express'
5
+ import uuid from 'short-uuid'
6
+ import { validateData } from './middleware/validationMiddleware'
7
+ import { CreateAuthorizationRequestBodySchema } from './schemas'
8
+ import {
9
+ CreateAuthorizationRequest,
10
+ CreateAuthorizationRequestResponse,
11
+ CreateAuthorizationResponse,
12
+ DeleteAuthorizationRequest,
13
+ GetAuthorizationRequestStatus,
14
+ GetAuthStatusResponse,
15
+ ICreateAuthRequestWebappEndpointOpts,
16
+ IRequiredContext
17
+ } from './types'
18
+
19
+ export function createAuthRequestUniversalOID4VPEndpoint(router: Router, context: IRequiredContext, opts?: ICreateAuthRequestWebappEndpointOpts) {
20
+ if (opts?.enabled === false) {
21
+ console.log(`createAuthRequest universal OID4VP endpoint is disabled`)
22
+ return
23
+ }
24
+
25
+ const path = opts?.path ?? '/backend/auth/requests'
26
+ router.post(path, checkAuth(opts?.endpoint), validateData(CreateAuthorizationRequestBodySchema), async (request: CreateAuthorizationRequest, response: CreateAuthorizationResponse) => {
27
+ try {
28
+ const correlationId = request.body.correlation_id ?? uuid.uuid()
29
+ const qrCodeOpts = request.body.qr_code ?? opts?.qrCodeOpts
30
+ const queryId = request.body.query_id
31
+ const directPostResponseRedirectUri = request.body.direct_post_response_redirect_uri // TODO Uri not URI
32
+ const requestUriBase = request.body.request_uri_base
33
+
34
+ try {
35
+ await context.agent.pdmGetDefinition({ itemId: queryId })
36
+ } catch(e) {
37
+ console.log(`No query could be found for the given id. Query id: ${queryId}`)
38
+ return sendErrorResponse(response, 404, { status: 404, message: 'No query could be found' })
39
+ }
40
+
41
+ const requestByReferenceURI = uriWithBase(`/siop/definitions/${queryId}/auth-requests/${correlationId}`, {
42
+ baseURI: requestUriBase ?? opts?.siopBaseURI,
43
+ })
44
+ const responseURI = uriWithBase(`/siop/definitions/${queryId}/auth-responses/${correlationId}`, { baseURI: opts?.siopBaseURI })
45
+
46
+ const authRequestURI = await context.agent.siopCreateAuthRequestURI({
47
+ queryId,
48
+ correlationId,
49
+ nonce: uuid.uuid(),
50
+ requestByReferenceURI,
51
+ responseURIType: 'response_uri',
52
+ responseURI,
53
+ ...(directPostResponseRedirectUri && { responseRedirectURI: directPostResponseRedirectUri }),
54
+ })
55
+
56
+ let qrCodeDataUri: string | undefined
57
+ if (qrCodeOpts) {
58
+ const { AwesomeQR } = await import('awesome-qr')
59
+ const qrCode = new AwesomeQR({ ...qrCodeOpts, text: authRequestURI })
60
+ qrCodeDataUri = `data:image/png;base64,${(await qrCode.draw())!.toString('base64')}`
61
+ }
62
+
63
+ const authRequestBody = {
64
+ query_id: queryId,
65
+ correlation_id: correlationId,
66
+ request_uri: authRequestURI,
67
+ status_uri: `${uriWithBase(opts?.webappAuthStatusPath ?? `/backend/auth/status/${correlationId}`, { baseURI: opts?.webappBaseURI })}`,
68
+ ...(qrCodeDataUri && { qr_uri: qrCodeDataUri }),
69
+ } satisfies CreateAuthorizationRequestResponse
70
+ console.log(`Auth Request URI data to send back: ${JSON.stringify(authRequestBody)}`)
71
+
72
+ return response.status(201).json(authRequestBody)
73
+ } catch (error) {
74
+ return sendErrorResponse(response, 500, { status: 500, message: 'Could not create an authorization request URI' }, error)
75
+ }
76
+ })
77
+ }
78
+
79
+ export function removeAuthRequestStateUniversalOID4VPEndpoint(router: Router, context: IRequiredContext, opts?: ISingleEndpointOpts) {
80
+ if (opts?.enabled === false) {
81
+ console.log(`removeAuthStatus universal OID4VP endpoint is disabled`)
82
+ return
83
+ }
84
+
85
+ const path = opts?.path ?? '/backend/auth/requests/:correlationId'
86
+ router.delete(path, checkAuth(opts?.endpoint), async (request: DeleteAuthorizationRequest, response: Response) => {
87
+ try {
88
+ const correlationId: string = request.params.correlationId
89
+
90
+ const authRequestState = await context.agent.siopGetAuthRequestState({
91
+ correlationId,
92
+ errorOnNotFound: false
93
+ })
94
+ if (!authRequestState) {
95
+ console.log(`No authorization request could be found for the given correlationId. correlationId: ${correlationId}`)
96
+ return sendErrorResponse(response, 404, { status: 404, message: 'No authorization request could be found' })
97
+ }
98
+
99
+ await context.agent.siopDeleteAuthState({ correlationId })
100
+
101
+ return response.status(204).json()
102
+ } catch (error) {
103
+ return sendErrorResponse(response, 500, { status: 500, message: error.message }, error)
104
+ }
105
+ })
106
+ }
107
+
108
+ export function authStatusUniversalOID4VPEndpoint(router: Router, context: IRequiredContext, opts?: ISingleEndpointOpts) {
109
+ if (opts?.enabled === false) {
110
+ console.log(`authStatus universal OID4VP endpoint is disabled`)
111
+ return
112
+ }
113
+
114
+ const path = opts?.path ?? '/backend/auth/status/:correlationId'
115
+ router.get(path, checkAuth(opts?.endpoint), async (request: GetAuthorizationRequestStatus, response: Response) => {
116
+ try {
117
+ console.log('Received auth-status request...')
118
+ const correlationId: string = request.params.correlationId
119
+
120
+ const requestState = await context.agent.siopGetAuthRequestState({
121
+ correlationId,
122
+ errorOnNotFound: false
123
+ })
124
+
125
+ if (!requestState) {
126
+ console.log(`No authorization request could be found for the given correlationId. correlationId: ${correlationId}`)
127
+ return sendErrorResponse(response, 404, { status: 404, message: 'No authorization request could be found' })
128
+ }
129
+
130
+ let responseState
131
+ if (requestState.status === 'authorization_request_created') {
132
+ responseState = (await context.agent.siopGetAuthResponseState({ correlationId, errorOnNotFound: false }))
133
+ }
134
+ const overallState = responseState ?? requestState
135
+
136
+ const statusBody = {
137
+ status: overallState.status,
138
+ correlation_id: overallState.correlationId,
139
+ query_id: overallState.queryId,
140
+ last_updated: overallState.lastUpdated,
141
+ ...((responseState?.status === AuthorizationResponseStateStatus.VERIFIED && responseState.verifiedData !== undefined) && { verifiedData: responseState.verifiedData }),
142
+ ...(overallState.error && { message: overallState.error.message })
143
+ } satisfies GetAuthStatusResponse
144
+ console.debug(`Will send auth status: ${JSON.stringify(statusBody)}`)
145
+
146
+ if (overallState.status === 'error') {
147
+ return response.status(500).json(statusBody)
148
+ }
149
+ return response.status(200).json(statusBody)
150
+ } catch (error) {
151
+ return sendErrorResponse(response, 500, { status: 500, message: error.message }, error)
152
+ }
153
+ })
154
+ }
155
+
156
+ export function getDefinitionsEndpoint(router: Router, context: IRequiredContext, opts?: ISingleEndpointOpts) {
157
+ if (opts?.enabled === false) {
158
+ console.log(`getDefinitions universal OID4VP endpoint is disabled`)
159
+ return
160
+ }
161
+
162
+ const path = opts?.path ?? '/backend/definitions'
163
+ router.get(path, checkAuth(opts?.endpoint), async (request: Request, response: Response) => {
164
+ try {
165
+ const definitions = await context.agent.pdmGetDefinitions()
166
+ response.statusCode = 200
167
+ return response.json(definitions)
168
+ } catch (error) {
169
+ return sendErrorResponse(response, 500, { status: 500, message: error.message }, error)
170
+ }
171
+ })
172
+ }