@trustvc/trustvc 1.0.0-alpha.1 → 1.0.0-alpha.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.
- package/README.md +138 -0
- package/dist/config.d.mts +3 -0
- package/dist/config.d.ts +3 -0
- package/dist/config.js +5 -0
- package/dist/core/decrypt.d.mts +3 -0
- package/dist/core/decrypt.d.ts +3 -0
- package/dist/core/decrypt.js +22 -0
- package/dist/core/encrypt.d.mts +3 -0
- package/dist/core/encrypt.d.ts +3 -0
- package/dist/core/encrypt.js +22 -0
- package/dist/core/fragments/document-integrity/w3cSignatureIntegrity.d.mts +5 -0
- package/dist/core/fragments/document-integrity/w3cSignatureIntegrity.d.ts +5 -0
- package/dist/core/fragments/document-integrity/w3cSignatureIntegrity.js +48 -0
- package/dist/core/fragments/document-status/transferableRecords/transferableRecordVerifier.d.mts +7 -0
- package/dist/core/fragments/document-status/transferableRecords/transferableRecordVerifier.d.ts +7 -0
- package/dist/core/fragments/document-status/transferableRecords/transferableRecordVerifier.js +128 -0
- package/dist/core/fragments/document-status/transferableRecords/transferableRecordVerifier.types.d.mts +30 -0
- package/dist/core/fragments/document-status/transferableRecords/transferableRecordVerifier.types.d.ts +30 -0
- package/dist/core/fragments/document-status/transferableRecords/transferableRecordVerifier.types.js +2 -0
- package/dist/core/fragments/document-status/transferableRecords/utils.d.mts +18 -0
- package/dist/core/fragments/document-status/transferableRecords/utils.d.ts +18 -0
- package/dist/core/fragments/document-status/transferableRecords/utils.js +75 -0
- package/dist/core/fragments/document-status/w3cCredentialStatus.d.mts +5 -0
- package/dist/core/fragments/document-status/w3cCredentialStatus.d.ts +5 -0
- package/dist/core/fragments/document-status/w3cCredentialStatus.js +54 -0
- package/dist/core/fragments/issuer-identity/w3cIssuerIdentity.d.mts +5 -0
- package/dist/core/fragments/issuer-identity/w3cIssuerIdentity.d.ts +5 -0
- package/dist/core/fragments/issuer-identity/w3cIssuerIdentity.js +74 -0
- package/dist/core/index.d.mts +5 -0
- package/dist/core/index.d.ts +5 -0
- package/dist/core/index.js +26 -0
- package/dist/core/verify.d.mts +6 -0
- package/dist/core/verify.d.ts +6 -0
- package/dist/core/verify.js +40 -0
- package/dist/esm/config.js +3 -0
- package/dist/esm/core/decrypt.js +20 -0
- package/dist/esm/core/encrypt.js +20 -0
- package/dist/esm/core/fragments/document-integrity/w3cSignatureIntegrity.js +46 -0
- package/dist/esm/core/fragments/document-status/transferableRecords/transferableRecordVerifier.js +105 -0
- package/dist/esm/core/fragments/document-status/transferableRecords/transferableRecordVerifier.types.js +1 -0
- package/dist/esm/core/fragments/document-status/transferableRecords/utils.js +72 -0
- package/dist/esm/core/fragments/document-status/w3cCredentialStatus.js +52 -0
- package/dist/esm/core/fragments/issuer-identity/w3cIssuerIdentity.js +72 -0
- package/dist/esm/core/index.js +3 -0
- package/dist/esm/core/verify.js +38 -0
- package/dist/esm/index.js +3 -0
- package/dist/esm/open-attestation/index.js +5 -0
- package/dist/esm/open-attestation/sign.js +15 -0
- package/dist/esm/open-attestation/types.js +1 -0
- package/dist/esm/open-attestation/utils.js +1 -0
- package/dist/esm/open-attestation/verify.js +13 -0
- package/dist/esm/open-attestation/wrap.js +33 -0
- package/dist/esm/utils/stringUtils.js +20 -0
- package/dist/esm/w3c/index.js +3 -0
- package/dist/esm/w3c/sign.js +9 -0
- package/dist/esm/w3c/types.js +2 -0
- package/dist/esm/w3c/verify.js +9 -0
- package/dist/index.d.mts +14 -0
- package/dist/index.d.ts +14 -0
- package/dist/index.js +26 -0
- package/dist/open-attestation/index.d.mts +6 -0
- package/dist/open-attestation/index.d.ts +6 -0
- package/dist/open-attestation/index.js +40 -0
- package/dist/open-attestation/sign.d.mts +8 -0
- package/dist/open-attestation/sign.d.ts +8 -0
- package/dist/open-attestation/sign.js +17 -0
- package/dist/open-attestation/types.d.mts +8 -0
- package/dist/open-attestation/types.d.ts +8 -0
- package/dist/open-attestation/types.js +18 -0
- package/dist/open-attestation/utils.d.mts +3 -0
- package/dist/open-attestation/utils.d.ts +3 -0
- package/dist/open-attestation/utils.js +10 -0
- package/dist/open-attestation/verify.d.mts +5 -0
- package/dist/open-attestation/verify.d.ts +5 -0
- package/dist/open-attestation/verify.js +15 -0
- package/dist/open-attestation/wrap.d.mts +9 -0
- package/dist/open-attestation/wrap.d.ts +9 -0
- package/dist/open-attestation/wrap.js +45 -0
- package/dist/utils/stringUtils.d.mts +5 -0
- package/dist/utils/stringUtils.d.ts +5 -0
- package/dist/utils/stringUtils.js +24 -0
- package/dist/w3c/index.d.mts +4 -0
- package/dist/w3c/index.d.ts +4 -0
- package/dist/w3c/index.js +26 -0
- package/dist/w3c/sign.d.mts +6 -0
- package/dist/w3c/sign.d.ts +6 -0
- package/dist/w3c/sign.js +11 -0
- package/dist/w3c/types.d.mts +2 -0
- package/dist/w3c/types.d.ts +2 -0
- package/dist/w3c/types.js +27 -0
- package/dist/w3c/verify.d.mts +5 -0
- package/dist/w3c/verify.d.ts +5 -0
- package/dist/w3c/verify.js +11 -0
- package/package.json +13 -7
package/README.md
CHANGED
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
# TrustVC
|
|
2
|
+
|
|
3
|
+
## About
|
|
4
|
+
TrustVC is a wrapper library that facilitates the signing and verification of TrustVC W3C [Verifiable Credentials (VC)](https://github.com/TrustVC/w3c/tree/alpha) 1.0.0-alpha, adhering to the W3C [VC](https://www.w3.org/TR/vc-data-model/) Data Model v1.1 and OpenAttestation [Verifiable Documents (VD)](https://github.com/Open-Attestation/open-attestation/tree/beta) v6.10.0-beta.
|
|
5
|
+
|
|
6
|
+
|
|
7
|
+
## Functions
|
|
8
|
+
### 1. **Signing**
|
|
9
|
+
|
|
10
|
+
> Independent signing function for TrustVC W3C VC and OpenAttestation VD
|
|
11
|
+
|
|
12
|
+
1. OpenAttestation Signing (signOA), supporting only OA Schema [v4](https://github.com/Open-Attestation/open-attestation/tree/beta/src/4.0)
|
|
13
|
+
|
|
14
|
+
> [!NOTE]
|
|
15
|
+
> Do not confuse OA Schema V4 with OA package version.
|
|
16
|
+
|
|
17
|
+
```ts
|
|
18
|
+
import { wrapOA, signOA } from '@trustvc/trustvc';
|
|
19
|
+
|
|
20
|
+
const rawDocument = {
|
|
21
|
+
'@context': [
|
|
22
|
+
'https://www.w3.org/ns/credentials/v2',
|
|
23
|
+
'https://schemata.openattestation.com/com/openattestation/4.0/context.json',
|
|
24
|
+
],
|
|
25
|
+
type: ['VerifiableCredential', 'OpenAttestationCredential'],
|
|
26
|
+
credentialSubject: {
|
|
27
|
+
id: '0x1234567890123456789012345678901234567890',
|
|
28
|
+
name: 'John Doe',
|
|
29
|
+
country: 'SG',
|
|
30
|
+
},
|
|
31
|
+
issuer: {
|
|
32
|
+
id: 'did:ethr:0xB26B4941941C51a4885E5B7D3A1B861E54405f90',
|
|
33
|
+
type: 'OpenAttestationIssuer',
|
|
34
|
+
name: 'Government Technology Agency of Singapore (GovTech)',
|
|
35
|
+
identityProof: { identityProofType: 'DNS-DID', identifier: 'example.openattestation.com' },
|
|
36
|
+
},
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
const wrappedDocument = await wrapOA(rawDocument);
|
|
40
|
+
|
|
41
|
+
const signedWrappedDocument = await signOA(wrappedDocument, {
|
|
42
|
+
public: 'did:ethr:0xB26B4941941C51a4885E5B7D3A1B861E54405f90#controller',
|
|
43
|
+
private: '<privateKey>',
|
|
44
|
+
});
|
|
45
|
+
```
|
|
46
|
+
|
|
47
|
+
2. TrustVC W3C Signing (signW3C)
|
|
48
|
+
|
|
49
|
+
```ts
|
|
50
|
+
import { signW3C } from '@trustvc/trustvc';
|
|
51
|
+
import { VerificationType } from '@trustvc/w3c-issuer';
|
|
52
|
+
|
|
53
|
+
const rawDocument = {
|
|
54
|
+
'@context': [
|
|
55
|
+
'https://www.w3.org/2018/credentials/v1',
|
|
56
|
+
'https://w3c-ccg.github.io/citizenship-vocab/contexts/citizenship-v1.jsonld',
|
|
57
|
+
'https://w3id.org/security/bbs/v1',
|
|
58
|
+
'https://w3id.org/vc/status-list/2021/v1',
|
|
59
|
+
],
|
|
60
|
+
credentialStatus: {
|
|
61
|
+
id: 'https://trustvc.github.io/did/credentials/statuslist/1#1',
|
|
62
|
+
type: 'StatusList2021Entry',
|
|
63
|
+
statusPurpose: 'revocation',
|
|
64
|
+
statusListIndex: '10',
|
|
65
|
+
statusListCredential: 'https://trustvc.github.io/did/credentials/statuslist/1',
|
|
66
|
+
},
|
|
67
|
+
credentialSubject: {
|
|
68
|
+
name: 'TrustVC',
|
|
69
|
+
birthDate: '2024-04-01T12:19:52Z',
|
|
70
|
+
type: ['PermanentResident', 'Person'],
|
|
71
|
+
},
|
|
72
|
+
expirationDate: '2029-12-03T12:19:52Z',
|
|
73
|
+
issuer: 'did:web:trustvc.github.io:did:1',
|
|
74
|
+
type: ['VerifiableCredential'],
|
|
75
|
+
issuanceDate: '2024-04-01T12:19:52Z'
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
const signingResult = await signW3C(rawDocument, {
|
|
79
|
+
id: 'did:web:trustvc.github.io:did:1#keys-1',
|
|
80
|
+
controller: 'did:web:trustvc.github.io:did:1',
|
|
81
|
+
type: VerificationType.Bls12381G2Key2020,
|
|
82
|
+
publicKeyBase58:
|
|
83
|
+
'oRfEeWFresvhRtXCkihZbxyoi2JER7gHTJ5psXhHsdCoU1MttRMi3Yp9b9fpjmKh7bMgfWKLESiK2YovRd8KGzJsGuamoAXfqDDVhckxuc9nmsJ84skCSTijKeU4pfAcxeJ',
|
|
84
|
+
privateKeyBase58: '<privateKeyBase58>',
|
|
85
|
+
});
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
### 2. **Verifying**
|
|
89
|
+
|
|
90
|
+
> Single verifying function to simplify the process
|
|
91
|
+
|
|
92
|
+
1. Verify
|
|
93
|
+
|
|
94
|
+
```ts
|
|
95
|
+
import { verifyDocument } from '@trustvc/trustvc';
|
|
96
|
+
|
|
97
|
+
const signedDocument = {
|
|
98
|
+
'@context': [
|
|
99
|
+
'https://www.w3.org/2018/credentials/v1',
|
|
100
|
+
'https://w3c-ccg.github.io/citizenship-vocab/contexts/citizenship-v1.jsonld',
|
|
101
|
+
'https://w3id.org/security/bbs/v1',
|
|
102
|
+
'https://w3id.org/vc/status-list/2021/v1',
|
|
103
|
+
],
|
|
104
|
+
credentialStatus: {
|
|
105
|
+
id: 'https://trustvc.github.io/did/credentials/statuslist/1#1',
|
|
106
|
+
type: 'StatusList2021Entry',
|
|
107
|
+
statusPurpose: 'revocation',
|
|
108
|
+
statusListIndex: '10',
|
|
109
|
+
statusListCredential: 'https://trustvc.github.io/did/credentials/statuslist/1',
|
|
110
|
+
},
|
|
111
|
+
credentialSubject: {
|
|
112
|
+
name: 'TrustVC',
|
|
113
|
+
birthDate: '2024-04-01T12:19:52Z',
|
|
114
|
+
type: ['PermanentResident', 'Person'],
|
|
115
|
+
},
|
|
116
|
+
expirationDate: '2029-12-03T12:19:52Z',
|
|
117
|
+
issuer: 'did:web:trustvc.github.io:did:1',
|
|
118
|
+
type: ['VerifiableCredential'],
|
|
119
|
+
issuanceDate: '2024-04-01T12:19:52Z',
|
|
120
|
+
proof: {
|
|
121
|
+
type: 'BbsBlsSignature2020',
|
|
122
|
+
created: '2024-10-14T04:11:49Z',
|
|
123
|
+
proofPurpose: 'assertionMethod',
|
|
124
|
+
proofValue:
|
|
125
|
+
'l79dlFQMowalep+WCFqgCvpVBcCAr0GDEFUV6S7gRVY/TQ+sp/wcwaT61PaD19rJYUHlKfzccE4m7waZyoLEkBLFiK2g54Q2i+CdtYBgDdkUDsoULSBMcH1MwGHwdjfXpldFNFrHFx/IAvLVniyeMQ==',
|
|
126
|
+
verificationMethod: 'did:web:trustvc.github.io:did:1#keys-1',
|
|
127
|
+
},
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
const resultFragments = await verifyDocument(signedDocument);
|
|
131
|
+
```
|
|
132
|
+
|
|
133
|
+
## Running the code
|
|
134
|
+
```
|
|
135
|
+
npm install
|
|
136
|
+
npm run build
|
|
137
|
+
npm run test
|
|
138
|
+
```
|
package/dist/config.d.ts
ADDED
package/dist/config.js
ADDED
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var config = require('../config');
|
|
4
|
+
var stringUtils = require('../utils/stringUtils');
|
|
5
|
+
var tsChacha20 = require('ts-chacha20');
|
|
6
|
+
|
|
7
|
+
var __defProp = Object.defineProperty;
|
|
8
|
+
var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
|
|
9
|
+
function decrypt(encryptedMessage, key, nonce) {
|
|
10
|
+
key = key.length > 0 ? key : config.DEFAULT_KEY;
|
|
11
|
+
key = stringUtils.generate32ByteKey(key);
|
|
12
|
+
nonce = stringUtils.generate12ByteNonce(nonce ?? "");
|
|
13
|
+
const keyBuffer = stringUtils.stringToUint8Array(key);
|
|
14
|
+
const nonceBuffer = stringUtils.stringToUint8Array(nonce);
|
|
15
|
+
const chacha20 = new tsChacha20.Chacha20(keyBuffer, nonceBuffer);
|
|
16
|
+
const encryptedBuffer = new Uint8Array(Buffer.from(encryptedMessage, "hex"));
|
|
17
|
+
const decrypted = chacha20.decrypt(encryptedBuffer);
|
|
18
|
+
return Buffer.from(decrypted).toString("utf-8");
|
|
19
|
+
}
|
|
20
|
+
__name(decrypt, "decrypt");
|
|
21
|
+
|
|
22
|
+
exports.decrypt = decrypt;
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var config = require('../config');
|
|
4
|
+
var stringUtils = require('../utils/stringUtils');
|
|
5
|
+
var tsChacha20 = require('ts-chacha20');
|
|
6
|
+
|
|
7
|
+
var __defProp = Object.defineProperty;
|
|
8
|
+
var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
|
|
9
|
+
function encrypt(message, key, nonce) {
|
|
10
|
+
key = key.length > 0 ? key : config.DEFAULT_KEY;
|
|
11
|
+
key = stringUtils.generate32ByteKey(key);
|
|
12
|
+
nonce = stringUtils.generate12ByteNonce(nonce ?? "");
|
|
13
|
+
const keyBuffer = stringUtils.stringToUint8Array(key);
|
|
14
|
+
const nonceBuffer = stringUtils.stringToUint8Array(nonce);
|
|
15
|
+
const chacha20 = new tsChacha20.Chacha20(keyBuffer, nonceBuffer);
|
|
16
|
+
const messageBuffer = stringUtils.stringToUint8Array(message);
|
|
17
|
+
const encrypted = chacha20.encrypt(messageBuffer);
|
|
18
|
+
return Buffer.from(encrypted).toString("hex");
|
|
19
|
+
}
|
|
20
|
+
__name(encrypt, "encrypt");
|
|
21
|
+
|
|
22
|
+
exports.encrypt = encrypt;
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var __ = require('../../..');
|
|
4
|
+
|
|
5
|
+
var __defProp = Object.defineProperty;
|
|
6
|
+
var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
|
|
7
|
+
const w3cSignatureIntegrity = {
|
|
8
|
+
skip: /* @__PURE__ */ __name(async () => {
|
|
9
|
+
return {
|
|
10
|
+
type: "DOCUMENT_INTEGRITY",
|
|
11
|
+
name: "W3CSignatureIntegrity",
|
|
12
|
+
reason: {
|
|
13
|
+
code: 0,
|
|
14
|
+
codeString: "SKIPPED",
|
|
15
|
+
message: `Document either has no proof or proof.type is not 'BbsBlsSignature2020'.`
|
|
16
|
+
},
|
|
17
|
+
status: "SKIPPED"
|
|
18
|
+
};
|
|
19
|
+
}, "skip"),
|
|
20
|
+
test: /* @__PURE__ */ __name((document) => {
|
|
21
|
+
const doc = document;
|
|
22
|
+
return doc.proof?.type === "BbsBlsSignature2020";
|
|
23
|
+
}, "test"),
|
|
24
|
+
verify: /* @__PURE__ */ __name(async (document) => {
|
|
25
|
+
const doc = document;
|
|
26
|
+
const verificationResult = await __.verifyW3CSignature(doc);
|
|
27
|
+
if (verificationResult.verified) {
|
|
28
|
+
return {
|
|
29
|
+
type: "DOCUMENT_INTEGRITY",
|
|
30
|
+
name: "W3CSignatureIntegrity",
|
|
31
|
+
data: true,
|
|
32
|
+
status: "VALID"
|
|
33
|
+
};
|
|
34
|
+
} else {
|
|
35
|
+
return {
|
|
36
|
+
type: "DOCUMENT_INTEGRITY",
|
|
37
|
+
name: "W3CSignatureIntegrity",
|
|
38
|
+
data: false,
|
|
39
|
+
reason: {
|
|
40
|
+
message: verificationResult.error
|
|
41
|
+
},
|
|
42
|
+
status: "INVALID"
|
|
43
|
+
};
|
|
44
|
+
}
|
|
45
|
+
}, "verify")
|
|
46
|
+
};
|
|
47
|
+
|
|
48
|
+
exports.w3cSignatureIntegrity = w3cSignatureIntegrity;
|
package/dist/core/fragments/document-status/transferableRecords/transferableRecordVerifier.d.mts
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
import { VerifierType } from './transferableRecordVerifier.types.mjs';
|
|
2
|
+
import '@tradetrust-tt/tt-verify';
|
|
3
|
+
|
|
4
|
+
declare const TRANSFERABLE_RECORDS_TYPE = "TransferableRecords";
|
|
5
|
+
declare const credentialStatusTransferableRecordVerifier: VerifierType;
|
|
6
|
+
|
|
7
|
+
export { TRANSFERABLE_RECORDS_TYPE, credentialStatusTransferableRecordVerifier };
|
package/dist/core/fragments/document-status/transferableRecords/transferableRecordVerifier.d.ts
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
import { VerifierType } from './transferableRecordVerifier.types.js';
|
|
2
|
+
import '@tradetrust-tt/tt-verify';
|
|
3
|
+
|
|
4
|
+
declare const TRANSFERABLE_RECORDS_TYPE = "TransferableRecords";
|
|
5
|
+
declare const credentialStatusTransferableRecordVerifier: VerifierType;
|
|
6
|
+
|
|
7
|
+
export { TRANSFERABLE_RECORDS_TYPE, credentialStatusTransferableRecordVerifier };
|
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var ttVerify = require('@tradetrust-tt/tt-verify');
|
|
4
|
+
var w3cVC = require('@trustvc/w3c-vc');
|
|
5
|
+
var utils = require('./utils');
|
|
6
|
+
|
|
7
|
+
function _interopNamespace(e) {
|
|
8
|
+
if (e && e.__esModule) return e;
|
|
9
|
+
var n = Object.create(null);
|
|
10
|
+
if (e) {
|
|
11
|
+
Object.keys(e).forEach(function (k) {
|
|
12
|
+
if (k !== 'default') {
|
|
13
|
+
var d = Object.getOwnPropertyDescriptor(e, k);
|
|
14
|
+
Object.defineProperty(n, k, d.get ? d : {
|
|
15
|
+
enumerable: true,
|
|
16
|
+
get: function () { return e[k]; }
|
|
17
|
+
});
|
|
18
|
+
}
|
|
19
|
+
});
|
|
20
|
+
}
|
|
21
|
+
n.default = e;
|
|
22
|
+
return Object.freeze(n);
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
var w3cVC__namespace = /*#__PURE__*/_interopNamespace(w3cVC);
|
|
26
|
+
|
|
27
|
+
var __defProp = Object.defineProperty;
|
|
28
|
+
var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
|
|
29
|
+
const TRANSFERABLE_RECORDS_TYPE = "TransferableRecords";
|
|
30
|
+
const type = "DOCUMENT_STATUS";
|
|
31
|
+
const name = TRANSFERABLE_RECORDS_TYPE;
|
|
32
|
+
const verify = /* @__PURE__ */ __name(async (document, options) => {
|
|
33
|
+
let signedDocument;
|
|
34
|
+
let tokenId;
|
|
35
|
+
if (w3cVC__namespace.isSignedDocument(document)) {
|
|
36
|
+
signedDocument = document;
|
|
37
|
+
tokenId = "0x" + signedDocument?.credentialStatus?.tokenId;
|
|
38
|
+
}
|
|
39
|
+
const credentialStatus = signedDocument?.credentialStatus;
|
|
40
|
+
if (!credentialStatus?.tokenRegistry) {
|
|
41
|
+
throw new ttVerify.CodedError(
|
|
42
|
+
"Document's credentialStatus does not have tokenRegistry",
|
|
43
|
+
ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.UNRECOGNIZED_DOCUMENT,
|
|
44
|
+
ttVerify.OpenAttestationEthereumTokenRegistryStatusCode[ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.UNRECOGNIZED_DOCUMENT]
|
|
45
|
+
);
|
|
46
|
+
}
|
|
47
|
+
if (!credentialStatus?.tokenNetwork || !credentialStatus?.tokenNetwork?.chainId) {
|
|
48
|
+
throw new ttVerify.CodedError(
|
|
49
|
+
"Document's credentialStatus does not have tokenNetwork.chainId",
|
|
50
|
+
ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.UNRECOGNIZED_DOCUMENT,
|
|
51
|
+
ttVerify.OpenAttestationEthereumTokenRegistryStatusCode[ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.UNRECOGNIZED_DOCUMENT]
|
|
52
|
+
);
|
|
53
|
+
}
|
|
54
|
+
const { provider } = options;
|
|
55
|
+
const mintStatus = await utils.isTokenMintedOnRegistry({
|
|
56
|
+
tokenRegistryAddress: credentialStatus?.tokenRegistry,
|
|
57
|
+
tokenId,
|
|
58
|
+
provider
|
|
59
|
+
});
|
|
60
|
+
const result = {
|
|
61
|
+
name,
|
|
62
|
+
type,
|
|
63
|
+
status: "INVALID",
|
|
64
|
+
data: {
|
|
65
|
+
tokenRegistry: credentialStatus.tokenRegistry
|
|
66
|
+
}
|
|
67
|
+
};
|
|
68
|
+
if (ttVerify.ValidTokenRegistryStatus.guard(mintStatus)) {
|
|
69
|
+
result.status = "VALID";
|
|
70
|
+
} else {
|
|
71
|
+
result.reason = mintStatus.reason;
|
|
72
|
+
}
|
|
73
|
+
return result;
|
|
74
|
+
}, "verify");
|
|
75
|
+
const skip = /* @__PURE__ */ __name(async () => {
|
|
76
|
+
return {
|
|
77
|
+
status: "SKIPPED",
|
|
78
|
+
type,
|
|
79
|
+
name,
|
|
80
|
+
reason: {
|
|
81
|
+
code: ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.SKIPPED,
|
|
82
|
+
codeString: ttVerify.OpenAttestationEthereumTokenRegistryStatusCode[ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.SKIPPED],
|
|
83
|
+
message: `Document does not have TransferableRecords status`
|
|
84
|
+
}
|
|
85
|
+
};
|
|
86
|
+
}, "skip");
|
|
87
|
+
const test = /* @__PURE__ */ __name((document) => {
|
|
88
|
+
if (document?.credentialStatus?.type === TRANSFERABLE_RECORDS_TYPE) {
|
|
89
|
+
return true;
|
|
90
|
+
}
|
|
91
|
+
return false;
|
|
92
|
+
}, "test");
|
|
93
|
+
const credentialStatusTransferableRecordVerifier = {
|
|
94
|
+
skip,
|
|
95
|
+
test,
|
|
96
|
+
verify: /* @__PURE__ */ __name(async (...args) => {
|
|
97
|
+
try {
|
|
98
|
+
return await verify(...args);
|
|
99
|
+
} catch (e) {
|
|
100
|
+
if (e instanceof ttVerify.CodedError) {
|
|
101
|
+
const err = {
|
|
102
|
+
name,
|
|
103
|
+
type,
|
|
104
|
+
status: "ERROR",
|
|
105
|
+
reason: {
|
|
106
|
+
code: e.code,
|
|
107
|
+
codeString: e.codeString,
|
|
108
|
+
message: e.message
|
|
109
|
+
}
|
|
110
|
+
};
|
|
111
|
+
return err;
|
|
112
|
+
}
|
|
113
|
+
return {
|
|
114
|
+
name,
|
|
115
|
+
type,
|
|
116
|
+
status: "ERROR",
|
|
117
|
+
reason: {
|
|
118
|
+
code: ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.UNEXPECTED_ERROR,
|
|
119
|
+
codeString: ttVerify.OpenAttestationEthereumTokenRegistryStatusCode[ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.UNEXPECTED_ERROR],
|
|
120
|
+
message: e instanceof Error ? e.message : "An unexpected error occurred"
|
|
121
|
+
}
|
|
122
|
+
};
|
|
123
|
+
}
|
|
124
|
+
}, "verify")
|
|
125
|
+
};
|
|
126
|
+
|
|
127
|
+
exports.TRANSFERABLE_RECORDS_TYPE = TRANSFERABLE_RECORDS_TYPE;
|
|
128
|
+
exports.credentialStatusTransferableRecordVerifier = credentialStatusTransferableRecordVerifier;
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { OpenAttestationEthereumTokenRegistryStatusCode, VerificationFragment, ErrorVerificationFragment, Verifier } from '@tradetrust-tt/tt-verify';
|
|
2
|
+
|
|
3
|
+
type TransferableRecordsErrorReason = {
|
|
4
|
+
code: OpenAttestationEthereumTokenRegistryStatusCode;
|
|
5
|
+
codeString: string;
|
|
6
|
+
message: string;
|
|
7
|
+
};
|
|
8
|
+
type TransferableRecordsResultFragment = VerificationFragment & {
|
|
9
|
+
status: 'VALID' | 'INVALID';
|
|
10
|
+
data: {
|
|
11
|
+
tokenRegistry: string;
|
|
12
|
+
};
|
|
13
|
+
reason?: TransferableRecordsErrorReason;
|
|
14
|
+
};
|
|
15
|
+
type TransferableRecordsErrorFragment = Omit<ErrorVerificationFragment<never>, 'data'> & {
|
|
16
|
+
data?: never;
|
|
17
|
+
reason: TransferableRecordsErrorReason;
|
|
18
|
+
};
|
|
19
|
+
type TransferableRecordsVerificationFragment = TransferableRecordsResultFragment | TransferableRecordsErrorFragment;
|
|
20
|
+
type VerifierType = Verifier<TransferableRecordsVerificationFragment>;
|
|
21
|
+
type TransferableRecordCredentialStatus = {
|
|
22
|
+
type: 'TransferableRecords';
|
|
23
|
+
tokenRegistry: string;
|
|
24
|
+
tokenNetwork: {
|
|
25
|
+
chainId: number;
|
|
26
|
+
name: string;
|
|
27
|
+
};
|
|
28
|
+
};
|
|
29
|
+
|
|
30
|
+
export type { TransferableRecordCredentialStatus, TransferableRecordsErrorFragment, TransferableRecordsErrorReason, TransferableRecordsResultFragment, TransferableRecordsVerificationFragment, VerifierType };
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { OpenAttestationEthereumTokenRegistryStatusCode, VerificationFragment, ErrorVerificationFragment, Verifier } from '@tradetrust-tt/tt-verify';
|
|
2
|
+
|
|
3
|
+
type TransferableRecordsErrorReason = {
|
|
4
|
+
code: OpenAttestationEthereumTokenRegistryStatusCode;
|
|
5
|
+
codeString: string;
|
|
6
|
+
message: string;
|
|
7
|
+
};
|
|
8
|
+
type TransferableRecordsResultFragment = VerificationFragment & {
|
|
9
|
+
status: 'VALID' | 'INVALID';
|
|
10
|
+
data: {
|
|
11
|
+
tokenRegistry: string;
|
|
12
|
+
};
|
|
13
|
+
reason?: TransferableRecordsErrorReason;
|
|
14
|
+
};
|
|
15
|
+
type TransferableRecordsErrorFragment = Omit<ErrorVerificationFragment<never>, 'data'> & {
|
|
16
|
+
data?: never;
|
|
17
|
+
reason: TransferableRecordsErrorReason;
|
|
18
|
+
};
|
|
19
|
+
type TransferableRecordsVerificationFragment = TransferableRecordsResultFragment | TransferableRecordsErrorFragment;
|
|
20
|
+
type VerifierType = Verifier<TransferableRecordsVerificationFragment>;
|
|
21
|
+
type TransferableRecordCredentialStatus = {
|
|
22
|
+
type: 'TransferableRecords';
|
|
23
|
+
tokenRegistry: string;
|
|
24
|
+
tokenNetwork: {
|
|
25
|
+
chainId: number;
|
|
26
|
+
name: string;
|
|
27
|
+
};
|
|
28
|
+
};
|
|
29
|
+
|
|
30
|
+
export type { TransferableRecordCredentialStatus, TransferableRecordsErrorFragment, TransferableRecordsErrorReason, TransferableRecordsResultFragment, TransferableRecordsVerificationFragment, VerifierType };
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { ValidTokenRegistryStatus, InvalidTokenRegistryStatus } from '@tradetrust-tt/tt-verify';
|
|
2
|
+
import { providers, errors } from 'ethers';
|
|
3
|
+
|
|
4
|
+
type EthersError = {
|
|
5
|
+
message?: string;
|
|
6
|
+
data?: string;
|
|
7
|
+
method?: string;
|
|
8
|
+
reason?: string;
|
|
9
|
+
code?: errors;
|
|
10
|
+
};
|
|
11
|
+
declare const decodeError: (error: EthersError) => "Document has not been issued under token registry" | "Token registry is not found" | "ENS name is not configured" | "Invalid token registry address" | "Invalid contract arguments";
|
|
12
|
+
declare const isTokenMintedOnRegistry: ({ tokenRegistryAddress, tokenId, provider, }: {
|
|
13
|
+
tokenRegistryAddress: string;
|
|
14
|
+
tokenId: string;
|
|
15
|
+
provider: providers.Provider;
|
|
16
|
+
}) => Promise<ValidTokenRegistryStatus | InvalidTokenRegistryStatus>;
|
|
17
|
+
|
|
18
|
+
export { decodeError, isTokenMintedOnRegistry };
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { ValidTokenRegistryStatus, InvalidTokenRegistryStatus } from '@tradetrust-tt/tt-verify';
|
|
2
|
+
import { providers, errors } from 'ethers';
|
|
3
|
+
|
|
4
|
+
type EthersError = {
|
|
5
|
+
message?: string;
|
|
6
|
+
data?: string;
|
|
7
|
+
method?: string;
|
|
8
|
+
reason?: string;
|
|
9
|
+
code?: errors;
|
|
10
|
+
};
|
|
11
|
+
declare const decodeError: (error: EthersError) => "Document has not been issued under token registry" | "Token registry is not found" | "ENS name is not configured" | "Invalid token registry address" | "Invalid contract arguments";
|
|
12
|
+
declare const isTokenMintedOnRegistry: ({ tokenRegistryAddress, tokenId, provider, }: {
|
|
13
|
+
tokenRegistryAddress: string;
|
|
14
|
+
tokenId: string;
|
|
15
|
+
provider: providers.Provider;
|
|
16
|
+
}) => Promise<ValidTokenRegistryStatus | InvalidTokenRegistryStatus>;
|
|
17
|
+
|
|
18
|
+
export { decodeError, isTokenMintedOnRegistry };
|
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var ttVerify = require('@tradetrust-tt/tt-verify');
|
|
4
|
+
var contracts = require('@tradetrust-tt/token-registry/dist/contracts');
|
|
5
|
+
var ethers = require('ethers');
|
|
6
|
+
|
|
7
|
+
var __defProp = Object.defineProperty;
|
|
8
|
+
var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
|
|
9
|
+
const isNonExistentToken = /* @__PURE__ */ __name((error) => {
|
|
10
|
+
const message = error.message;
|
|
11
|
+
if (!message) {
|
|
12
|
+
return error.data && error.data.slice(0, 10) === "0x7e273289";
|
|
13
|
+
}
|
|
14
|
+
return message.includes("owner query for nonexistent token");
|
|
15
|
+
}, "isNonExistentToken");
|
|
16
|
+
const isMissingTokenRegistry = /* @__PURE__ */ __name((error) => {
|
|
17
|
+
return !error.reason && error.method?.toLowerCase() === "ownerOf(uint256)".toLowerCase() && error.code === ethers.errors.CALL_EXCEPTION;
|
|
18
|
+
}, "isMissingTokenRegistry");
|
|
19
|
+
const decodeError = /* @__PURE__ */ __name((error) => {
|
|
20
|
+
const reason = error.reason && Array.isArray(error.reason) ? error.reason[0] : error.reason ?? "";
|
|
21
|
+
switch (true) {
|
|
22
|
+
case isNonExistentToken(error):
|
|
23
|
+
return `Document has not been issued under token registry`;
|
|
24
|
+
case isMissingTokenRegistry(error):
|
|
25
|
+
return `Token registry is not found`;
|
|
26
|
+
case (reason.toLowerCase() === "ENS name not configured".toLowerCase() && error.code === ethers.errors.UNSUPPORTED_OPERATION):
|
|
27
|
+
return "ENS name is not configured";
|
|
28
|
+
case (reason.toLowerCase() === "invalid address".toLowerCase() && error.code === ethers.errors.INVALID_ARGUMENT):
|
|
29
|
+
return `Invalid token registry address`;
|
|
30
|
+
case error.code === ethers.errors.INVALID_ARGUMENT:
|
|
31
|
+
return `Invalid contract arguments`;
|
|
32
|
+
case error.code === ethers.errors.SERVER_ERROR:
|
|
33
|
+
case error.code === ethers.errors.NETWORK_ERROR:
|
|
34
|
+
throw new ttVerify.CodedError(
|
|
35
|
+
"Unable to connect to the network, please try again later",
|
|
36
|
+
ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.SERVER_ERROR,
|
|
37
|
+
ttVerify.OpenAttestationEthereumTokenRegistryStatusCode[ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.SERVER_ERROR]
|
|
38
|
+
);
|
|
39
|
+
default:
|
|
40
|
+
throw error;
|
|
41
|
+
}
|
|
42
|
+
}, "decodeError");
|
|
43
|
+
const isTokenMintedOnRegistry = /* @__PURE__ */ __name(async ({
|
|
44
|
+
tokenRegistryAddress,
|
|
45
|
+
tokenId,
|
|
46
|
+
provider
|
|
47
|
+
}) => {
|
|
48
|
+
try {
|
|
49
|
+
const tokenRegistryContract = contracts.TradeTrustToken__factory.connect(tokenRegistryAddress, provider);
|
|
50
|
+
const minted = await tokenRegistryContract.ownerOf(tokenId).then((owner) => owner !== ethers.constants.AddressZero);
|
|
51
|
+
return minted ? { minted, address: tokenRegistryAddress } : {
|
|
52
|
+
minted,
|
|
53
|
+
address: tokenRegistryAddress,
|
|
54
|
+
reason: {
|
|
55
|
+
code: ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.DOCUMENT_NOT_MINTED,
|
|
56
|
+
codeString: ttVerify.OpenAttestationEthereumTokenRegistryStatusCode[ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.DOCUMENT_NOT_MINTED],
|
|
57
|
+
message: `Document ${tokenId} has not been issued under contract ${tokenRegistryAddress}`
|
|
58
|
+
}
|
|
59
|
+
};
|
|
60
|
+
} catch (error) {
|
|
61
|
+
return {
|
|
62
|
+
minted: false,
|
|
63
|
+
address: tokenRegistryAddress,
|
|
64
|
+
reason: {
|
|
65
|
+
message: decodeError(error),
|
|
66
|
+
// message: (error as Error).message,
|
|
67
|
+
code: ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.DOCUMENT_NOT_MINTED,
|
|
68
|
+
codeString: ttVerify.OpenAttestationEthereumTokenRegistryStatusCode[ttVerify.OpenAttestationEthereumTokenRegistryStatusCode.DOCUMENT_NOT_MINTED]
|
|
69
|
+
}
|
|
70
|
+
};
|
|
71
|
+
}
|
|
72
|
+
}, "isTokenMintedOnRegistry");
|
|
73
|
+
|
|
74
|
+
exports.decodeError = decodeError;
|
|
75
|
+
exports.isTokenMintedOnRegistry = isTokenMintedOnRegistry;
|