@sphereon/ssi-sdk.w3c-vc-api 0.13.0 → 0.13.1-next.10

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.
@@ -0,0 +1,183 @@
1
+ import { CredentialPayload, VerifiableCredential } from '@veramo/core'
2
+ import { W3CVerifiableCredential } from '@veramo/core/src/types/vc-data-model'
3
+ import { Request, Response, Router } from 'express'
4
+ import { v4 } from 'uuid'
5
+ import { IRequiredContext, IVCAPIIssueOpts } from './types'
6
+
7
+ export function issueCredentialEndpoint(
8
+ router: Router,
9
+ context: IRequiredContext,
10
+ opts?: {
11
+ issueCredentialOpts?: IVCAPIIssueOpts
12
+ issueCredentialPath?: string
13
+ persistIssuedCredentials?: boolean
14
+ }
15
+ ) {
16
+ router.post(opts?.issueCredentialPath ?? '/credentials/issue', async (request: Request, response: Response) => {
17
+ try {
18
+ const credential: CredentialPayload = request.body.credential
19
+ if (!credential) {
20
+ return sendErrorResponse(response, 400, 'No credential supplied')
21
+ }
22
+ if (!credential.id) {
23
+ credential.id = `urn:uuid:${v4()}`
24
+ }
25
+ const issueOpts: IVCAPIIssueOpts | undefined = opts?.issueCredentialOpts
26
+ const vc = await context.agent.createVerifiableCredential({
27
+ credential,
28
+ save: opts?.persistIssuedCredentials ?? true,
29
+ proofFormat: issueOpts?.proofFormat ?? 'lds',
30
+ fetchRemoteContexts: issueOpts?.fetchRemoteContexts || true,
31
+ })
32
+ response.statusCode = 201
33
+ return response.send({ verifiableCredential: vc })
34
+ } catch (e) {
35
+ return sendErrorResponse(response, 500, e.message as string, e)
36
+ }
37
+ })
38
+ }
39
+
40
+ export function getCredentialsEndpoint(
41
+ router: Router,
42
+ context: IRequiredContext,
43
+ opts?: {
44
+ getCredentialsPath?: string
45
+ }
46
+ ) {
47
+ router.get(opts?.getCredentialsPath ?? '/credentials', async (request: Request, response: Response) => {
48
+ try {
49
+ const uniqueVCs = await context.agent.dataStoreORMGetVerifiableCredentials()
50
+ response.statusCode = 202
51
+ return response.send(uniqueVCs.map((uVC) => uVC.verifiableCredential))
52
+ } catch (e) {
53
+ return sendErrorResponse(response, 500, e.message as string, e)
54
+ }
55
+ })
56
+ }
57
+
58
+ export function getCredentialEndpoint(
59
+ router: Router,
60
+ context: IRequiredContext,
61
+ opts?: {
62
+ getCredentialPath?: string
63
+ }
64
+ ) {
65
+ router.get(opts?.getCredentialPath ?? '/credentials/:id', async (request: Request, response: Response) => {
66
+ try {
67
+ const id = request.params.id
68
+ if (!id) {
69
+ return sendErrorResponse(response, 400, 'no id provided')
70
+ }
71
+ let vcInfo = await getCredentialByIdOrHash(context, id)
72
+ if (!vcInfo.vc) {
73
+ return sendErrorResponse(response, 404, `id ${id} not found`)
74
+ }
75
+ response.statusCode = 200
76
+ return response.send(vcInfo.vc)
77
+ } catch (e) {
78
+ return sendErrorResponse(response, 500, e.message as string, e)
79
+ }
80
+ })
81
+ }
82
+
83
+ export function verifyCredentialEndpoint(
84
+ router: Router,
85
+ context: IRequiredContext,
86
+ opts?: {
87
+ verifyCredentialPath?: string
88
+ fetchRemoteContexts?: boolean
89
+ }
90
+ ) {
91
+ router.post(opts?.verifyCredentialPath ?? '/credentials/verify', async (request: Request, response: Response) => {
92
+ try {
93
+ console.log(request.body)
94
+ const credential: W3CVerifiableCredential = request.body.verifiableCredential
95
+ // const options: IIssueOptionsPayload = request.body.options
96
+ if (!credential) {
97
+ return sendErrorResponse(response, 400, 'No verifiable credential supplied')
98
+ }
99
+ const verifyResult = await context.agent.verifyCredential({
100
+ credential,
101
+ fetchRemoteContexts: opts?.fetchRemoteContexts !== false,
102
+ })
103
+
104
+ response.statusCode = 200
105
+ return response.send(verifyResult)
106
+ } catch (e) {
107
+ return sendErrorResponse(response, 500, e.message as string, e)
108
+ }
109
+ })
110
+ }
111
+
112
+ export function deleteCredentialEndpoint(
113
+ router: Router,
114
+ context: IRequiredContext,
115
+ opts?: {
116
+ deleteCredentialsPath?: string
117
+ }
118
+ ) {
119
+ router.delete(opts?.deleteCredentialsPath ?? '/credentials/:id', async (request: Request, response: Response) => {
120
+ try {
121
+ const id = request.params.id
122
+ if (!id) {
123
+ return sendErrorResponse(response, 400, 'no id provided')
124
+ }
125
+ let vcInfo = await getCredentialByIdOrHash(context, id)
126
+ if (!vcInfo.vc || !vcInfo.hash) {
127
+ return sendErrorResponse(response, 404, `id ${id} not found`)
128
+ }
129
+ const success = context.agent.dataStoreDeleteVerifiableCredential({ hash: vcInfo.hash })
130
+ if (!success) {
131
+ return sendErrorResponse(response, 400, `Could not delete Verifiable Credential with id ${id}`)
132
+ }
133
+ response.statusCode = 200
134
+ return response.send()
135
+ } catch (e) {
136
+ return sendErrorResponse(response, 500, e.message as string, e)
137
+ }
138
+ })
139
+ }
140
+
141
+ function sendErrorResponse(response: Response, statusCode: number, message: string, error?: Error) {
142
+ console.log(message)
143
+ if (error) {
144
+ console.log(error)
145
+ }
146
+ response.statusCode = statusCode
147
+ return response.status(statusCode).send(message)
148
+ }
149
+
150
+ export async function getCredentialByIdOrHash(
151
+ context: IRequiredContext,
152
+ idOrHash: string
153
+ ): Promise<{
154
+ id: string
155
+ hash?: string
156
+ vc?: VerifiableCredential
157
+ }> {
158
+ let vc: VerifiableCredential
159
+ let hash: string
160
+ const uniqueVCs = await context.agent.dataStoreORMGetVerifiableCredentials({
161
+ where: [
162
+ {
163
+ column: 'id',
164
+ value: [idOrHash],
165
+ op: 'Equal',
166
+ },
167
+ ],
168
+ })
169
+ if (uniqueVCs.length === 0) {
170
+ hash = idOrHash
171
+ vc = await context.agent.dataStoreGetVerifiableCredential({ hash })
172
+ } else {
173
+ const uniqueVC = uniqueVCs[0]
174
+ hash = uniqueVC.hash
175
+ vc = uniqueVC.verifiableCredential
176
+ }
177
+
178
+ return {
179
+ vc,
180
+ id: idOrHash,
181
+ hash,
182
+ }
183
+ }
package/src/index.ts CHANGED
@@ -1,5 +1,6 @@
1
1
  /**
2
2
  * @public
3
3
  */
4
- export * from './VCAPIServer'
4
+ export * from './vc-api-server'
5
5
  export * from './types'
6
+ export * from './api-functions'
package/src/types.ts CHANGED
@@ -10,6 +10,7 @@ import {
10
10
  IResolver,
11
11
  } from '@veramo/core'
12
12
  import { IPresentationExchange } from '@sphereon/ssi-sdk.presentation-exchange'
13
+ import { ProofFormat } from '@veramo/core/src/types/ICredentialIssuer'
13
14
 
14
15
  export type IRequiredPlugins = IDataStore &
15
16
  IDataStoreORM &
@@ -21,3 +22,70 @@ export type IRequiredPlugins = IDataStore &
21
22
  ICredentialPlugin &
22
23
  IResolver
23
24
  export type IRequiredContext = IAgentContext<IRequiredPlugins>
25
+
26
+ export interface IVCAPIOpts {
27
+ pathOpts?: IVCAPIPathOpts
28
+ issueCredentialOpts?: IVCAPIIssueOpts
29
+
30
+ serverOpts?: IServerOpts
31
+ }
32
+
33
+ export interface IServerOpts {
34
+ port?: number // The port to listen on
35
+ cookieSigningKey?: string
36
+ hostname?: string // defaults to "0.0.0.0", meaning it will listen on all IP addresses. Can be an IP address or hostname
37
+ }
38
+
39
+ export interface IVCAPIPathOpts {
40
+ basePath?: string
41
+ issueCredentialPath?: string
42
+ getCredentialsPath?: string
43
+ getCredentialPath?: string
44
+ deleteCredentialPath?: string
45
+ verifyCredentialPath?: string
46
+ verifyPresentationPath?: string
47
+ }
48
+
49
+ export interface IVCAPIIssueOpts {
50
+ persistIssuedCredentials?: boolean // Whether the issuer persists issued credentials or not. Defaults to true
51
+
52
+ /**
53
+ * The desired format for the VerifiablePresentation to be created.
54
+ */
55
+ proofFormat: ProofFormat
56
+
57
+ /**
58
+ * Remove payload members during JWT-JSON transformation. Defaults to `true`.
59
+ * See https://www.w3.org/TR/vc-data-model/#jwt-encoding
60
+ */
61
+ removeOriginalFields?: boolean
62
+
63
+ /**
64
+ * [Optional] The ID of the key that should sign this credential.
65
+ * If this is not specified, the first matching key will be used.
66
+ */
67
+ keyRef?: string
68
+
69
+ /**
70
+ * When dealing with JSON-LD you also MUST provide the proper contexts.
71
+ * Set this to `true` ONLY if you want the `@context` URLs to be fetched in case they are not preloaded.
72
+ * The context definitions SHOULD rather be provided at startup instead of being fetched.
73
+ *
74
+ * Defaults to `false`
75
+ */
76
+ fetchRemoteContexts?: boolean
77
+ }
78
+
79
+ export interface IIssueOptionsPayload {
80
+ created?: string
81
+ challenge?: string
82
+ domain?: string
83
+ credentialStatus?: {
84
+ type: string
85
+ }
86
+ }
87
+
88
+ export interface ChallengeOptsPayload {
89
+ challenge?: string
90
+ domain?: string
91
+ }
@@ -0,0 +1,85 @@
1
+ import { agentContext } from '@sphereon/ssi-sdk.core'
2
+ import { TAgent } from '@veramo/core'
3
+ import bodyParser from 'body-parser'
4
+ import cookieParser from 'cookie-parser'
5
+ import * as dotenv from 'dotenv-flow'
6
+ import express, { Express } from 'express'
7
+ import {
8
+ deleteCredentialEndpoint,
9
+ getCredentialEndpoint,
10
+ getCredentialsEndpoint,
11
+ issueCredentialEndpoint,
12
+ verifyCredentialEndpoint,
13
+ } from './api-functions'
14
+ import { IRequiredPlugins, IVCAPIOpts } from './types'
15
+
16
+ export class VcApiServer {
17
+ private readonly _express: Express
18
+ private readonly _agent: TAgent<IRequiredPlugins>
19
+ private readonly _opts?: IVCAPIOpts
20
+
21
+ constructor(args: { agent: TAgent<IRequiredPlugins>; express?: Express; opts?: IVCAPIOpts }) {
22
+ const { agent, opts } = args
23
+ this._agent = agent
24
+ this._opts = opts
25
+ const existingExpress = !!args.express
26
+ this._express = args.express ?? express()
27
+ this.setupExpress(existingExpress)
28
+ const router = express.Router()
29
+ const context = agentContext(agent)
30
+
31
+ // Credential endpoints
32
+ issueCredentialEndpoint(router, context, {
33
+ issueCredentialOpts: opts?.issueCredentialOpts,
34
+ issueCredentialPath: opts?.pathOpts?.issueCredentialPath,
35
+ })
36
+ getCredentialEndpoint(router, context, { getCredentialPath: opts?.pathOpts?.getCredentialPath })
37
+ getCredentialsEndpoint(router, context, { getCredentialsPath: opts?.pathOpts?.getCredentialsPath })
38
+ deleteCredentialEndpoint(router, context, { deleteCredentialsPath: opts?.pathOpts?.deleteCredentialPath }) // not in spec. TODO: Authz
39
+ verifyCredentialEndpoint(router, context, {
40
+ verifyCredentialPath: opts?.pathOpts?.verifyCredentialPath,
41
+ fetchRemoteContexts: opts?.issueCredentialOpts?.fetchRemoteContexts,
42
+ })
43
+ this._express.use(opts?.pathOpts?.basePath ?? '', router)
44
+ }
45
+
46
+ get agent(): TAgent<IRequiredPlugins> {
47
+ return this._agent
48
+ }
49
+
50
+ get opts(): IVCAPIOpts | undefined {
51
+ return this._opts
52
+ }
53
+
54
+ get express(): Express {
55
+ return this._express
56
+ }
57
+
58
+ private setupExpress(existingExpress: boolean) {
59
+ dotenv.config()
60
+ if (!existingExpress) {
61
+ const port = this.opts?.serverOpts?.port || process.env.PORT || 5000
62
+ const secret = this.opts?.serverOpts?.cookieSigningKey || process.env.COOKIE_SIGNING_KEY
63
+ const hostname = this.opts?.serverOpts?.hostname || '0.0.0.0'
64
+ this._express.use((req, res, next) => {
65
+ res.header('Access-Control-Allow-Origin', '*')
66
+ // Request methods you wish to allow
67
+ res.setHeader('Access-Control-Allow-Methods', 'GET, POST, OPTIONS, PUT, PATCH, DELETE')
68
+
69
+ // Request headers you wish to allow
70
+ res.setHeader('Access-Control-Allow-Headers', 'X-Requested-With,content-type')
71
+
72
+ // Set to true if you need the website to include cookies in the requests sent
73
+ // to the API (e.g. in case you use sessions)
74
+ res.setHeader('Access-Control-Allow-Credentials', 'true')
75
+ next()
76
+ })
77
+ // this.express.use(cors({ credentials: true }));
78
+ // this.express.use('/proxy', proxy('www.gssoogle.com'));
79
+ this._express.use(bodyParser.urlencoded({ extended: true }))
80
+ this._express.use(bodyParser.json())
81
+ this._express.use(cookieParser(secret))
82
+ this._express.listen(port as number, hostname, () => console.log(`Listening on ${hostname}, port ${port}`))
83
+ }
84
+ }
85
+ }
@@ -1,78 +0,0 @@
1
- import { TAgent } from '@veramo/core';
2
- import { ProofFormat } from '@veramo/core/src/types/ICredentialIssuer';
3
- import { Express } from 'express';
4
- import { IRequiredPlugins } from './types';
5
- export interface IVCAPIOpts {
6
- issueCredentialOpts?: IIssueOpts;
7
- serverOpts?: IServerOpts;
8
- }
9
- export interface IServerOpts {
10
- port?: number;
11
- cookieSigningKey?: string;
12
- hostname?: string;
13
- }
14
- export interface IIssueOpts {
15
- issueCredentialPath?: string;
16
- getCredentialsPath?: string;
17
- getCredentialPath?: string;
18
- deleteCredentialPath?: string;
19
- verifyCredentialPath?: string;
20
- verifyPresentationPath?: string;
21
- persistIssuedCredentials?: boolean;
22
- /**
23
- * The desired format for the VerifiablePresentation to be created.
24
- */
25
- proofFormat: ProofFormat;
26
- /**
27
- * Remove payload members during JWT-JSON transformation. Defaults to `true`.
28
- * See https://www.w3.org/TR/vc-data-model/#jwt-encoding
29
- */
30
- removeOriginalFields?: boolean;
31
- /**
32
- * [Optional] The ID of the key that should sign this credential.
33
- * If this is not specified, the first matching key will be used.
34
- */
35
- keyRef?: string;
36
- /**
37
- * When dealing with JSON-LD you also MUST provide the proper contexts.
38
- * Set this to `true` ONLY if you want the `@context` URLs to be fetched in case they are not preloaded.
39
- * The context definitions SHOULD rather be provided at startup instead of being fetched.
40
- *
41
- * Defaults to `false`
42
- */
43
- fetchRemoteContexts?: boolean;
44
- }
45
- export interface IIssueOptionsPayload {
46
- created?: string;
47
- challenge?: string;
48
- domain?: string;
49
- credentialStatus?: {
50
- type: string;
51
- };
52
- }
53
- export interface ChallengeOptsPayload {
54
- challenge?: string;
55
- domain?: string;
56
- }
57
- export declare class VCAPIServer {
58
- private readonly _express;
59
- private readonly _agent;
60
- private readonly _opts?;
61
- constructor(args: {
62
- agent: TAgent<IRequiredPlugins>;
63
- express?: Express;
64
- opts?: IVCAPIOpts;
65
- });
66
- get agent(): TAgent<IRequiredPlugins>;
67
- get opts(): IVCAPIOpts | undefined;
68
- get express(): Express;
69
- private setupExpress;
70
- private static sendErrorResponse;
71
- private getCredentialsEndpoint;
72
- private getCredentialEndpoint;
73
- private verifyCredentialEndpoint;
74
- private deleteCredentialEndpoint;
75
- private issueCredentialEndpoint;
76
- private getCredentialByIdOrHash;
77
- }
78
- //# sourceMappingURL=VCAPIServer.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"VCAPIServer.d.ts","sourceRoot":"","sources":["../src/VCAPIServer.ts"],"names":[],"mappings":"AAEA,OAAO,EAAqB,MAAM,EAAwB,MAAM,cAAc,CAAA;AAC9E,OAAO,EAAE,WAAW,EAAE,MAAM,0CAA0C,CAAA;AAKtE,OAAgB,EAAE,OAAO,EAAqB,MAAM,SAAS,CAAA;AAE7D,OAAO,EAAE,gBAAgB,EAAE,MAAM,SAAS,CAAA;AAE1C,MAAM,WAAW,UAAU;IACzB,mBAAmB,CAAC,EAAE,UAAU,CAAA;IAChC,UAAU,CAAC,EAAE,WAAW,CAAA;CACzB;AAED,MAAM,WAAW,WAAW;IAC1B,IAAI,CAAC,EAAE,MAAM,CAAA;IACb,gBAAgB,CAAC,EAAE,MAAM,CAAA;IACzB,QAAQ,CAAC,EAAE,MAAM,CAAA;CAClB;AAED,MAAM,WAAW,UAAU;IACzB,mBAAmB,CAAC,EAAE,MAAM,CAAA;IAC5B,kBAAkB,CAAC,EAAE,MAAM,CAAA;IAC3B,iBAAiB,CAAC,EAAE,MAAM,CAAA;IAC1B,oBAAoB,CAAC,EAAE,MAAM,CAAA;IAC7B,oBAAoB,CAAC,EAAE,MAAM,CAAA;IAC7B,sBAAsB,CAAC,EAAE,MAAM,CAAA;IAE/B,wBAAwB,CAAC,EAAE,OAAO,CAAA;IAElC;;OAEG;IACH,WAAW,EAAE,WAAW,CAAA;IAExB;;;OAGG;IACH,oBAAoB,CAAC,EAAE,OAAO,CAAA;IAE9B;;;OAGG;IACH,MAAM,CAAC,EAAE,MAAM,CAAA;IAEf;;;;;;OAMG;IACH,mBAAmB,CAAC,EAAE,OAAO,CAAA;CAC9B;AAED,MAAM,WAAW,oBAAoB;IACnC,OAAO,CAAC,EAAE,MAAM,CAAA;IAChB,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,MAAM,CAAC,EAAE,MAAM,CAAA;IACf,gBAAgB,CAAC,EAAE;QACjB,IAAI,EAAE,MAAM,CAAA;KACb,CAAA;CACF;AAED,MAAM,WAAW,oBAAoB;IACnC,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,MAAM,CAAC,EAAE,MAAM,CAAA;CAChB;AAED,qBAAa,WAAW;IACtB,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAS;IAClC,OAAO,CAAC,QAAQ,CAAC,MAAM,CAA0B;IACjD,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAY;gBAEvB,IAAI,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC,gBAAgB,CAAC,CAAC;QAAC,OAAO,CAAC,EAAE,OAAO,CAAC;QAAC,IAAI,CAAC,EAAE,UAAU,CAAA;KAAE;IAgB3F,IAAI,KAAK,IAAI,MAAM,CAAC,gBAAgB,CAAC,CAEpC;IAED,IAAI,IAAI,IAAI,UAAU,GAAG,SAAS,CAEjC;IAED,IAAI,OAAO,IAAI,OAAO,CAErB;IAED,OAAO,CAAC,YAAY;IA4BpB,OAAO,CAAC,MAAM,CAAC,iBAAiB;IAMhC,OAAO,CAAC,sBAAsB;IAa9B,OAAO,CAAC,qBAAqB;IAoB7B,OAAO,CAAC,wBAAwB;IA0BhC,OAAO,CAAC,wBAAwB;IAwBhC,OAAO,CAAC,uBAAuB;YA2BjB,uBAAuB;CA+BtC"}
@@ -1,245 +0,0 @@
1
- "use strict";
2
- // noinspection JSUnusedGlobalSymbols
3
- var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
4
- if (k2 === undefined) k2 = k;
5
- var desc = Object.getOwnPropertyDescriptor(m, k);
6
- if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
7
- desc = { enumerable: true, get: function() { return m[k]; } };
8
- }
9
- Object.defineProperty(o, k2, desc);
10
- }) : (function(o, m, k, k2) {
11
- if (k2 === undefined) k2 = k;
12
- o[k2] = m[k];
13
- }));
14
- var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
15
- Object.defineProperty(o, "default", { enumerable: true, value: v });
16
- }) : function(o, v) {
17
- o["default"] = v;
18
- });
19
- var __importStar = (this && this.__importStar) || function (mod) {
20
- if (mod && mod.__esModule) return mod;
21
- var result = {};
22
- if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
23
- __setModuleDefault(result, mod);
24
- return result;
25
- };
26
- var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
27
- function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
28
- return new (P || (P = Promise))(function (resolve, reject) {
29
- function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
30
- function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
31
- function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
32
- step((generator = generator.apply(thisArg, _arguments || [])).next());
33
- });
34
- };
35
- var __importDefault = (this && this.__importDefault) || function (mod) {
36
- return (mod && mod.__esModule) ? mod : { "default": mod };
37
- };
38
- Object.defineProperty(exports, "__esModule", { value: true });
39
- exports.VCAPIServer = void 0;
40
- const body_parser_1 = __importDefault(require("body-parser"));
41
- const cookie_parser_1 = __importDefault(require("cookie-parser"));
42
- const dotenv = __importStar(require("dotenv-flow"));
43
- const express_1 = __importDefault(require("express"));
44
- const uuid_1 = require("uuid");
45
- class VCAPIServer {
46
- constructor(args) {
47
- var _a;
48
- const { agent, opts } = args;
49
- this._agent = agent;
50
- this._opts = opts;
51
- const existingExpress = !!args.express;
52
- this._express = (_a = args.express) !== null && _a !== void 0 ? _a : (0, express_1.default)();
53
- this.setupExpress(existingExpress);
54
- // Credential endpoints
55
- this.issueCredentialEndpoint();
56
- this.getCredentialEndpoint();
57
- this.getCredentialsEndpoint();
58
- this.deleteCredentialEndpoint(); // not in spec. TODO: Authz
59
- this.verifyCredentialEndpoint();
60
- }
61
- get agent() {
62
- return this._agent;
63
- }
64
- get opts() {
65
- return this._opts;
66
- }
67
- get express() {
68
- return this._express;
69
- }
70
- setupExpress(existingExpress) {
71
- var _a, _b, _c, _d, _e, _f;
72
- dotenv.config();
73
- if (!existingExpress) {
74
- const port = ((_b = (_a = this.opts) === null || _a === void 0 ? void 0 : _a.serverOpts) === null || _b === void 0 ? void 0 : _b.port) || process.env.PORT || 5000;
75
- const secret = ((_d = (_c = this.opts) === null || _c === void 0 ? void 0 : _c.serverOpts) === null || _d === void 0 ? void 0 : _d.cookieSigningKey) || process.env.COOKIE_SIGNING_KEY;
76
- const hostname = ((_f = (_e = this.opts) === null || _e === void 0 ? void 0 : _e.serverOpts) === null || _f === void 0 ? void 0 : _f.hostname) || '0.0.0.0';
77
- this._express.use((req, res, next) => {
78
- res.header('Access-Control-Allow-Origin', '*');
79
- // Request methods you wish to allow
80
- res.setHeader('Access-Control-Allow-Methods', 'GET, POST, OPTIONS, PUT, PATCH, DELETE');
81
- // Request headers you wish to allow
82
- res.setHeader('Access-Control-Allow-Headers', 'X-Requested-With,content-type');
83
- // Set to true if you need the website to include cookies in the requests sent
84
- // to the API (e.g. in case you use sessions)
85
- res.setHeader('Access-Control-Allow-Credentials', 'true');
86
- next();
87
- });
88
- // this.express.use(cors({ credentials: true }));
89
- // this.express.use('/proxy', proxy('www.gssoogle.com'));
90
- this._express.use(body_parser_1.default.urlencoded({ extended: true }));
91
- this._express.use(body_parser_1.default.json());
92
- this._express.use((0, cookie_parser_1.default)(secret));
93
- this._express.listen(port, hostname, () => console.log(`Listening on ${hostname}, port ${port}`));
94
- }
95
- }
96
- static sendErrorResponse(response, statusCode, message) {
97
- console.log(message);
98
- response.statusCode = statusCode;
99
- response.status(statusCode).send(message);
100
- }
101
- getCredentialsEndpoint() {
102
- var _a, _b, _c;
103
- this._express.get((_c = (_b = (_a = this.opts) === null || _a === void 0 ? void 0 : _a.issueCredentialOpts) === null || _b === void 0 ? void 0 : _b.getCredentialsPath) !== null && _c !== void 0 ? _c : '/credentials', (request, response) => __awaiter(this, void 0, void 0, function* () {
104
- try {
105
- const uniqueVCs = yield this.agent.dataStoreORMGetVerifiableCredentials();
106
- response.statusCode = 202;
107
- return response.send(uniqueVCs.map((uVC) => uVC.verifiableCredential));
108
- }
109
- catch (e) {
110
- console.log(e);
111
- return VCAPIServer.sendErrorResponse(response, 500, e.message);
112
- }
113
- }));
114
- }
115
- getCredentialEndpoint() {
116
- var _a, _b, _c;
117
- this._express.get((_c = (_b = (_a = this.opts) === null || _a === void 0 ? void 0 : _a.issueCredentialOpts) === null || _b === void 0 ? void 0 : _b.getCredentialPath) !== null && _c !== void 0 ? _c : '/credentials/:id', (request, response) => __awaiter(this, void 0, void 0, function* () {
118
- try {
119
- const id = request.params.id;
120
- if (!id) {
121
- return VCAPIServer.sendErrorResponse(response, 400, 'no id provided');
122
- }
123
- let vcInfo = yield this.getCredentialByIdOrHash(id);
124
- if (!vcInfo.vc) {
125
- return VCAPIServer.sendErrorResponse(response, 404, `id ${id} not found`);
126
- }
127
- response.statusCode = 200;
128
- return response.send(vcInfo.vc);
129
- }
130
- catch (e) {
131
- console.log(e);
132
- return VCAPIServer.sendErrorResponse(response, 500, e.message);
133
- }
134
- }));
135
- }
136
- verifyCredentialEndpoint() {
137
- var _a, _b, _c;
138
- this._express.post((_c = (_b = (_a = this.opts) === null || _a === void 0 ? void 0 : _a.issueCredentialOpts) === null || _b === void 0 ? void 0 : _b.verifyCredentialPath) !== null && _c !== void 0 ? _c : '/credentials/verify', (request, response) => __awaiter(this, void 0, void 0, function* () {
139
- var _d, _e;
140
- try {
141
- console.log(request.body);
142
- const credential = request.body.verifiableCredential;
143
- // const options: IIssueOptionsPayload = request.body.options
144
- if (!credential) {
145
- return VCAPIServer.sendErrorResponse(response, 400, 'No verifiable credential supplied');
146
- }
147
- const verifyResult = yield this.agent.verifyCredential({
148
- credential,
149
- fetchRemoteContexts: (_e = (_d = this.opts) === null || _d === void 0 ? void 0 : _d.issueCredentialOpts) === null || _e === void 0 ? void 0 : _e.fetchRemoteContexts,
150
- });
151
- response.statusCode = 200;
152
- return response.send(verifyResult);
153
- }
154
- catch (e) {
155
- console.log(e);
156
- return VCAPIServer.sendErrorResponse(response, 500, e.message);
157
- }
158
- }));
159
- }
160
- deleteCredentialEndpoint() {
161
- var _a, _b, _c;
162
- this._express.delete((_c = (_b = (_a = this.opts) === null || _a === void 0 ? void 0 : _a.issueCredentialOpts) === null || _b === void 0 ? void 0 : _b.getCredentialsPath) !== null && _c !== void 0 ? _c : '/credentials/:id', (request, response) => __awaiter(this, void 0, void 0, function* () {
163
- try {
164
- const id = request.params.id;
165
- if (!id) {
166
- return VCAPIServer.sendErrorResponse(response, 400, 'no id provided');
167
- }
168
- let vcInfo = yield this.getCredentialByIdOrHash(id);
169
- if (!vcInfo.vc || !vcInfo.hash) {
170
- return VCAPIServer.sendErrorResponse(response, 404, `id ${id} not found`);
171
- }
172
- const success = this.agent.dataStoreDeleteVerifiableCredential({ hash: vcInfo.hash });
173
- if (!success) {
174
- return VCAPIServer.sendErrorResponse(response, 400, `Could not delete Verifiable Credential with id ${id}`);
175
- }
176
- response.statusCode = 200;
177
- return response.send();
178
- }
179
- catch (e) {
180
- console.log(e);
181
- return VCAPIServer.sendErrorResponse(response, 500, e.message);
182
- }
183
- }));
184
- }
185
- issueCredentialEndpoint() {
186
- var _a, _b, _c;
187
- this._express.post((_c = (_b = (_a = this.opts) === null || _a === void 0 ? void 0 : _a.issueCredentialOpts) === null || _b === void 0 ? void 0 : _b.issueCredentialPath) !== null && _c !== void 0 ? _c : '/credentials/issue', (request, response) => __awaiter(this, void 0, void 0, function* () {
188
- var _d, _e, _f;
189
- try {
190
- const credential = request.body.credential;
191
- // const options: IIssueOptionsPayload = request.body.options
192
- if (!credential) {
193
- return VCAPIServer.sendErrorResponse(response, 400, 'No credential supplied');
194
- }
195
- if (!credential.id) {
196
- credential.id = `urn:uuid:${(0, uuid_1.v4)()}`;
197
- }
198
- const issueOpts = (_d = this.opts) === null || _d === void 0 ? void 0 : _d.issueCredentialOpts;
199
- const vc = yield this._agent.createVerifiableCredential({
200
- credential,
201
- save: (_e = issueOpts === null || issueOpts === void 0 ? void 0 : issueOpts.persistIssuedCredentials) !== null && _e !== void 0 ? _e : true,
202
- proofFormat: (_f = issueOpts === null || issueOpts === void 0 ? void 0 : issueOpts.proofFormat) !== null && _f !== void 0 ? _f : 'lds',
203
- fetchRemoteContexts: (issueOpts === null || issueOpts === void 0 ? void 0 : issueOpts.fetchRemoteContexts) || true,
204
- });
205
- response.statusCode = 201;
206
- return response.send({ verifiableCredential: vc });
207
- }
208
- catch (e) {
209
- console.log(e);
210
- return VCAPIServer.sendErrorResponse(response, 500, e.message);
211
- }
212
- }));
213
- }
214
- getCredentialByIdOrHash(idOrHash) {
215
- return __awaiter(this, void 0, void 0, function* () {
216
- let vc;
217
- let hash;
218
- const uniqueVCs = yield this.agent.dataStoreORMGetVerifiableCredentials({
219
- where: [
220
- {
221
- column: 'id',
222
- value: [idOrHash],
223
- op: 'Equal',
224
- },
225
- ],
226
- });
227
- if (uniqueVCs.length === 0) {
228
- hash = idOrHash;
229
- vc = yield this.agent.dataStoreGetVerifiableCredential({ hash });
230
- }
231
- else {
232
- const uniqueVC = uniqueVCs[0];
233
- hash = uniqueVC.hash;
234
- vc = uniqueVC.verifiableCredential;
235
- }
236
- return {
237
- vc,
238
- id: idOrHash,
239
- hash,
240
- };
241
- });
242
- }
243
- }
244
- exports.VCAPIServer = VCAPIServer;
245
- //# sourceMappingURL=VCAPIServer.js.map