@notabene/verify-proof 1.0.0-preview.2
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/.node-version +1 -0
- package/README.md +72 -0
- package/dist/index.cjs +2 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.js +2 -0
- package/dist/index.js.map +1 -0
- package/dist/index.modern.js +2 -0
- package/dist/index.modern.js.map +1 -0
- package/dist/index.test.d.ts +1 -0
- package/dist/index.umd.js +2 -0
- package/dist/index.umd.js.map +1 -0
- package/package.json +29 -0
- package/src/index.test.ts +154 -0
- package/src/index.ts +54 -0
- package/tsconfig.json +32 -0
package/.node-version
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
v20.17.0
|
package/README.md
ADDED
@@ -0,0 +1,72 @@
|
|
1
|
+
# @notabene/verify-proof
|
2
|
+
|
3
|
+
This package provides functionality to verify ownership proofs for the Notabene SDK.
|
4
|
+
|
5
|
+
## Description
|
6
|
+
|
7
|
+
The `@notabene/verify-proof` package is designed to work with the Notabene SDK, offering methods to verify various types of ownership proofs used in blockchain transactions and identity verification.
|
8
|
+
|
9
|
+
## Installation
|
10
|
+
|
11
|
+
```bash
|
12
|
+
npm install @notabene/verify-proof
|
13
|
+
```
|
14
|
+
|
15
|
+
or
|
16
|
+
|
17
|
+
```bash
|
18
|
+
yarn add @notabene/verify-proof
|
19
|
+
```
|
20
|
+
|
21
|
+
## Usage
|
22
|
+
|
23
|
+
Here's a basic example of how to use the `verifyProof` function:
|
24
|
+
|
25
|
+
```typescript
|
26
|
+
import { verifyProof } from '@notabene/verify-proof';
|
27
|
+
import { OwnershipProof } from '@notabene/javascript-sdk';
|
28
|
+
|
29
|
+
async function checkProof(proof: OwnershipProof) {
|
30
|
+
const verifiedProof = await verifyProof(proof);
|
31
|
+
console.log(verifiedProof.status);
|
32
|
+
}
|
33
|
+
```
|
34
|
+
|
35
|
+
## Supported Proof Types
|
36
|
+
|
37
|
+
- Checkbox Confirmation (`ProofTypes.CheckboxConfirmation`)
|
38
|
+
- Screenshot (`ProofTypes.Screenshot`)
|
39
|
+
- Personal Sign EIP191 (`ProofTypes.PersonalSignEIP191`)
|
40
|
+
- Personal Sign EIP712 (`ProofTypes.PersonalSignEIP712`)
|
41
|
+
- Personal Sign BIP137 (`ProofTypes.PersonalSignBIP137`)
|
42
|
+
- Personal Sign XPUB (`ProofTypes.PersonalSignXPUB`)
|
43
|
+
- Micro Transfer (`ProofTypes.MicroTransfer`)
|
44
|
+
|
45
|
+
## Development
|
46
|
+
|
47
|
+
To set up the development environment:
|
48
|
+
|
49
|
+
1. Clone the repository
|
50
|
+
2. Install dependencies: `yarn install`
|
51
|
+
3. Run tests: `yarn test`
|
52
|
+
|
53
|
+
## Scripts
|
54
|
+
|
55
|
+
- `yarn dev`: Start development server
|
56
|
+
- `yarn build`: Build the project
|
57
|
+
- `yarn lint`: Run linter
|
58
|
+
- `yarn test`: Run tests
|
59
|
+
|
60
|
+
## Dependencies
|
61
|
+
|
62
|
+
- `@notabene/javascript-sdk`: Notabene JavaScript SDK
|
63
|
+
- `viem`: Ethereum utility library
|
64
|
+
- `bitcoinjs-message`: Bitcoin message signing and verification
|
65
|
+
|
66
|
+
## License
|
67
|
+
|
68
|
+
This project is private and not publicly licensed.
|
69
|
+
|
70
|
+
## Author
|
71
|
+
|
72
|
+
Pelle Braendgaard
|
package/dist/index.cjs
ADDED
@@ -0,0 +1,2 @@
|
|
1
|
+
var r=require("@notabene/javascript-sdk/src/types"),e=require("viem");function t(){return t=Object.assign?Object.assign.bind():function(r){for(var e=1;e<arguments.length;e++){var t=arguments[e];for(var s in t)({}).hasOwnProperty.call(t,s)&&(r[s]=t[s])}return r},t.apply(null,arguments)}exports.verifyProof=function(s){try{switch(s.type){case r.ProofTypes.SelfDeclaration:return Promise.resolve(t({},s,{status:s.confirmed?r.ProofStatus.VERIFIED:r.ProofStatus.FAILED}));case r.ProofTypes.Screenshot:return Promise.resolve(t({},s,{status:s.url?r.ProofStatus.FLAGGED:r.ProofStatus.FAILED}));case r.ProofTypes.PersonalSignEIP191:return function(s){try{return Promise.resolve(e.verifyMessage({address:s.address,message:s.attestation,signature:s.proof})).then(function(e){return t({},s,{status:e?r.ProofStatus.VERIFIED:r.ProofStatus.FAILED})})}catch(r){return Promise.reject(r)}}(s)}return Promise.resolve(s)}catch(r){return Promise.reject(r)}};
|
2
|
+
//# sourceMappingURL=index.cjs.map
|
@@ -0,0 +1 @@
|
|
1
|
+
{"version":3,"file":"index.cjs","sources":["../src/index.ts"],"sourcesContent":["import {\n DeclarationProof,\n ProofStatus,\n ProofTypes,\n ScreenshotProof,\n SignatureProof,\n type OwnershipProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { verifyMessage } from \"viem\";\n\nexport async function verifyProof(\n proof: OwnershipProof,\n): Promise<OwnershipProof> {\n switch (proof.type) {\n case ProofTypes.SelfDeclaration:\n return {\n ...proof,\n status: (proof as DeclarationProof).confirmed\n ? ProofStatus.VERIFIED\n : ProofStatus.FAILED,\n };\n case ProofTypes.Screenshot:\n return {\n ...proof,\n status: (proof as ScreenshotProof).url\n ? ProofStatus.FLAGGED\n : ProofStatus.FAILED,\n };\n case ProofTypes.PersonalSignEIP191:\n return verifyPersonalSignEIP191(proof as SignatureProof);\n case ProofTypes.PersonalSignEIP712:\n case ProofTypes.PersonalSignBIP137:\n case ProofTypes.PersonalSignXPUB:\n case ProofTypes.MicroTransfer:\n }\n return proof;\n}\n\nasync function verifyPersonalSignEIP191(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const verified = await verifyMessage({\n address: proof.address as `0x${string}`,\n message: proof.attestation,\n signature: proof.proof as `0x${string}`,\n });\n return {\n ...proof,\n status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,\n };\n}\n"],"names":["proof","type","ProofTypes","SelfDeclaration","Promise","resolve","_extends","status","confirmed","ProofStatus","VERIFIED","FAILED","Screenshot","url","FLAGGED","PersonalSignEIP191","verifyMessage","address","message","attestation","signature","then","verified","e","reject","verifyPersonalSignEIP191"],"mappings":"kTAUsB,SACpBA,GAAqB,IAErB,OAAQA,EAAMC,MACZ,KAAKC,EAAUA,WAACC,gBACd,OAAAC,QAAAC,QAAAC,EACKN,CAAAA,EAAAA,GACHO,OAASP,EAA2BQ,UAChCC,cAAYC,SACZD,EAAAA,YAAYE,UAEpB,KAAKT,EAAUA,WAACU,WACd,OAAAR,QAAAC,QAAAC,EACKN,CAAAA,EAAAA,EACHO,CAAAA,OAASP,EAA0Ba,IAC/BJ,EAAAA,YAAYK,QACZL,EAAWA,YAACE,UAEpB,KAAKT,EAAAA,WAAWa,mBACd,gBAUJf,GAAqB,IAAAI,OAAAA,QAAAC,QAEEW,EAAAA,cAAc,CACnCC,QAASjB,EAAMiB,QACfC,QAASlB,EAAMmB,YACfC,UAAWpB,EAAMA,SACjBqB,KAAA,SAJIC,GAKN,OAAAhB,EACKN,CAAAA,EAAAA,GACHO,OAAQe,EAAWb,EAAAA,YAAYC,SAAWD,EAAWA,YAACE,QACtD,EACJ,CAAC,MAAAY,GAAA,OAAAnB,QAAAoB,OAAAD,IArBYE,CAAyBzB,GAMpC,OAAAI,QAAAC,QAAOL,EACT,CAAC,MAAAuB,UAAAnB,QAAAoB,OAAAD,EAAA,CAAA"}
|
package/dist/index.d.ts
ADDED
package/dist/index.js
ADDED
@@ -0,0 +1,2 @@
|
|
1
|
+
import{ProofTypes as r,ProofStatus as e}from"@notabene/javascript-sdk/src/types";import{verifyMessage as t}from"viem";function s(){return s=Object.assign?Object.assign.bind():function(r){for(var e=1;e<arguments.length;e++){var t=arguments[e];for(var s in t)({}).hasOwnProperty.call(t,s)&&(r[s]=t[s])}return r},s.apply(null,arguments)}var n=function(n){try{switch(n.type){case r.SelfDeclaration:return Promise.resolve(s({},n,{status:n.confirmed?e.VERIFIED:e.FAILED}));case r.Screenshot:return Promise.resolve(s({},n,{status:n.url?e.FLAGGED:e.FAILED}));case r.PersonalSignEIP191:return function(r){try{return Promise.resolve(t({address:r.address,message:r.attestation,signature:r.proof})).then(function(t){return s({},r,{status:t?e.VERIFIED:e.FAILED})})}catch(r){return Promise.reject(r)}}(n)}return Promise.resolve(n)}catch(r){return Promise.reject(r)}};export{n as verifyProof};
|
2
|
+
//# sourceMappingURL=index.js.map
|
@@ -0,0 +1 @@
|
|
1
|
+
{"version":3,"file":"index.js","sources":["../src/index.ts"],"sourcesContent":["import {\n DeclarationProof,\n ProofStatus,\n ProofTypes,\n ScreenshotProof,\n SignatureProof,\n type OwnershipProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { verifyMessage } from \"viem\";\n\nexport async function verifyProof(\n proof: OwnershipProof,\n): Promise<OwnershipProof> {\n switch (proof.type) {\n case ProofTypes.SelfDeclaration:\n return {\n ...proof,\n status: (proof as DeclarationProof).confirmed\n ? ProofStatus.VERIFIED\n : ProofStatus.FAILED,\n };\n case ProofTypes.Screenshot:\n return {\n ...proof,\n status: (proof as ScreenshotProof).url\n ? ProofStatus.FLAGGED\n : ProofStatus.FAILED,\n };\n case ProofTypes.PersonalSignEIP191:\n return verifyPersonalSignEIP191(proof as SignatureProof);\n case ProofTypes.PersonalSignEIP712:\n case ProofTypes.PersonalSignBIP137:\n case ProofTypes.PersonalSignXPUB:\n case ProofTypes.MicroTransfer:\n }\n return proof;\n}\n\nasync function verifyPersonalSignEIP191(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const verified = await verifyMessage({\n address: proof.address as `0x${string}`,\n message: proof.attestation,\n signature: proof.proof as `0x${string}`,\n });\n return {\n ...proof,\n status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,\n };\n}\n"],"names":["verifyProof","proof","type","ProofTypes","SelfDeclaration","Promise","resolve","_extends","status","confirmed","ProofStatus","VERIFIED","FAILED","Screenshot","url","FLAGGED","PersonalSignEIP191","verifyMessage","address","message","attestation","signature","then","verified","e","reject","verifyPersonalSignEIP191"],"mappings":"8UAQqC,IAEfA,EAAA,SACpBC,GAAqB,IAErB,OAAQA,EAAMC,MACZ,KAAKC,EAAWC,gBACd,OAAAC,QAAAC,QAAAC,EACKN,CAAAA,EAAAA,GACHO,OAASP,EAA2BQ,UAChCC,EAAYC,SACZD,EAAYE,UAEpB,KAAKT,EAAWU,WACd,OAAAR,QAAAC,QAAAC,EACKN,CAAAA,EAAAA,EACHO,CAAAA,OAASP,EAA0Ba,IAC/BJ,EAAYK,QACZL,EAAYE,UAEpB,KAAKT,EAAWa,mBACd,gBAUJf,GAAqB,IAAAI,OAAAA,QAAAC,QAEEW,EAAc,CACnCC,QAASjB,EAAMiB,QACfC,QAASlB,EAAMmB,YACfC,UAAWpB,EAAMA,SACjBqB,KAAA,SAJIC,GAKN,OAAAhB,EACKN,CAAAA,EAAAA,GACHO,OAAQe,EAAWb,EAAYC,SAAWD,EAAYE,QACtD,EACJ,CAAC,MAAAY,GAAA,OAAAnB,QAAAoB,OAAAD,IArBYE,CAAyBzB,GAMpC,OAAAI,QAAAC,QAAOL,EACT,CAAC,MAAAuB,UAAAnB,QAAAoB,OAAAD,EAAA,CAAA"}
|
@@ -0,0 +1,2 @@
|
|
1
|
+
import{ProofTypes as r,ProofStatus as t}from"@notabene/javascript-sdk/src/types";import{verifyMessage as n}from"viem";function e(){return e=Object.assign?Object.assign.bind():function(r){for(var t=1;t<arguments.length;t++){var n=arguments[t];for(var e in n)({}).hasOwnProperty.call(n,e)&&(r[e]=n[e])}return r},e.apply(null,arguments)}async function s(s){switch(s.type){case r.SelfDeclaration:return e({},s,{status:s.confirmed?t.VERIFIED:t.FAILED});case r.Screenshot:return e({},s,{status:s.url?t.FLAGGED:t.FAILED});case r.PersonalSignEIP191:return async function(r){return e({},r,{status:await n({address:r.address,message:r.attestation,signature:r.proof})?t.VERIFIED:t.FAILED})}(s)}return s}export{s as verifyProof};
|
2
|
+
//# sourceMappingURL=index.modern.js.map
|
@@ -0,0 +1 @@
|
|
1
|
+
{"version":3,"file":"index.modern.js","sources":["../src/index.ts"],"sourcesContent":["import {\n DeclarationProof,\n ProofStatus,\n ProofTypes,\n ScreenshotProof,\n SignatureProof,\n type OwnershipProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { verifyMessage } from \"viem\";\n\nexport async function verifyProof(\n proof: OwnershipProof,\n): Promise<OwnershipProof> {\n switch (proof.type) {\n case ProofTypes.SelfDeclaration:\n return {\n ...proof,\n status: (proof as DeclarationProof).confirmed\n ? ProofStatus.VERIFIED\n : ProofStatus.FAILED,\n };\n case ProofTypes.Screenshot:\n return {\n ...proof,\n status: (proof as ScreenshotProof).url\n ? ProofStatus.FLAGGED\n : ProofStatus.FAILED,\n };\n case ProofTypes.PersonalSignEIP191:\n return verifyPersonalSignEIP191(proof as SignatureProof);\n case ProofTypes.PersonalSignEIP712:\n case ProofTypes.PersonalSignBIP137:\n case ProofTypes.PersonalSignXPUB:\n case ProofTypes.MicroTransfer:\n }\n return proof;\n}\n\nasync function verifyPersonalSignEIP191(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const verified = await verifyMessage({\n address: proof.address as `0x${string}`,\n message: proof.attestation,\n signature: proof.proof as `0x${string}`,\n });\n return {\n ...proof,\n status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,\n };\n}\n"],"names":["async","verifyProof","proof","type","ProofTypes","SelfDeclaration","_extends","status","confirmed","ProofStatus","VERIFIED","FAILED","Screenshot","url","FLAGGED","PersonalSignEIP191","verifyMessage","address","message","attestation","signature","verifyPersonalSignEIP191"],"mappings":"8UAUOA,eAAeC,EACpBC,GAEA,OAAQA,EAAMC,MACZ,KAAKC,EAAWC,gBACd,OAAAC,KACKJ,EAAK,CACRK,OAASL,EAA2BM,UAChCC,EAAYC,SACZD,EAAYE,SAEpB,KAAKP,EAAWQ,WACd,OAAAN,EACKJ,GAAAA,GACHK,OAASL,EAA0BW,IAC/BJ,EAAYK,QACZL,EAAYE,SAEpB,KAAKP,EAAWW,mBACd,OASNf,eACEE,GAOA,OAAAI,EACKJ,CAAAA,EAAAA,GACHK,aAPqBS,EAAc,CACnCC,QAASf,EAAMe,QACfC,QAAShB,EAAMiB,YACfC,UAAWlB,EAAMA,QAIEO,EAAYC,SAAWD,EAAYE,QAE1D,CArBaU,CAAyBnB,GAMpC,OAAOA,CACT"}
|
@@ -0,0 +1 @@
|
|
1
|
+
export {};
|
@@ -0,0 +1,2 @@
|
|
1
|
+
!function(e,r){"object"==typeof exports&&"undefined"!=typeof module?r(exports,require("@notabene/javascript-sdk/src/types"),require("viem")):"function"==typeof define&&define.amd?define(["exports","@notabene/javascript-sdk/src/types","viem"],r):r((e||self).verifyProof={},e.types,e.viem)}(this,function(e,r,t){function o(){return o=Object.assign?Object.assign.bind():function(e){for(var r=1;r<arguments.length;r++){var t=arguments[r];for(var o in t)({}).hasOwnProperty.call(t,o)&&(e[o]=t[o])}return e},o.apply(null,arguments)}e.verifyProof=function(e){try{switch(e.type){case r.ProofTypes.SelfDeclaration:return Promise.resolve(o({},e,{status:e.confirmed?r.ProofStatus.VERIFIED:r.ProofStatus.FAILED}));case r.ProofTypes.Screenshot:return Promise.resolve(o({},e,{status:e.url?r.ProofStatus.FLAGGED:r.ProofStatus.FAILED}));case r.ProofTypes.PersonalSignEIP191:return function(e){try{return Promise.resolve(t.verifyMessage({address:e.address,message:e.attestation,signature:e.proof})).then(function(t){return o({},e,{status:t?r.ProofStatus.VERIFIED:r.ProofStatus.FAILED})})}catch(e){return Promise.reject(e)}}(e)}return Promise.resolve(e)}catch(e){return Promise.reject(e)}}});
|
2
|
+
//# sourceMappingURL=index.umd.js.map
|
@@ -0,0 +1 @@
|
|
1
|
+
{"version":3,"file":"index.umd.js","sources":["../src/index.ts"],"sourcesContent":["import {\n DeclarationProof,\n ProofStatus,\n ProofTypes,\n ScreenshotProof,\n SignatureProof,\n type OwnershipProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { verifyMessage } from \"viem\";\n\nexport async function verifyProof(\n proof: OwnershipProof,\n): Promise<OwnershipProof> {\n switch (proof.type) {\n case ProofTypes.SelfDeclaration:\n return {\n ...proof,\n status: (proof as DeclarationProof).confirmed\n ? ProofStatus.VERIFIED\n : ProofStatus.FAILED,\n };\n case ProofTypes.Screenshot:\n return {\n ...proof,\n status: (proof as ScreenshotProof).url\n ? ProofStatus.FLAGGED\n : ProofStatus.FAILED,\n };\n case ProofTypes.PersonalSignEIP191:\n return verifyPersonalSignEIP191(proof as SignatureProof);\n case ProofTypes.PersonalSignEIP712:\n case ProofTypes.PersonalSignBIP137:\n case ProofTypes.PersonalSignXPUB:\n case ProofTypes.MicroTransfer:\n }\n return proof;\n}\n\nasync function verifyPersonalSignEIP191(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const verified = await verifyMessage({\n address: proof.address as `0x${string}`,\n message: proof.attestation,\n signature: proof.proof as `0x${string}`,\n });\n return {\n ...proof,\n status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,\n };\n}\n"],"names":["proof","type","ProofTypes","SelfDeclaration","Promise","resolve","_extends","status","confirmed","ProofStatus","VERIFIED","FAILED","Screenshot","url","FLAGGED","PersonalSignEIP191","verifyMessage","address","message","attestation","signature","then","verified","e","reject","verifyPersonalSignEIP191"],"mappings":"wkBAUsB,SACpBA,GAAqB,IAErB,OAAQA,EAAMC,MACZ,KAAKC,EAAUA,WAACC,gBACd,OAAAC,QAAAC,QAAAC,EACKN,CAAAA,EAAAA,GACHO,OAASP,EAA2BQ,UAChCC,cAAYC,SACZD,EAAAA,YAAYE,UAEpB,KAAKT,EAAUA,WAACU,WACd,OAAAR,QAAAC,QAAAC,EACKN,CAAAA,EAAAA,EACHO,CAAAA,OAASP,EAA0Ba,IAC/BJ,EAAAA,YAAYK,QACZL,EAAWA,YAACE,UAEpB,KAAKT,EAAAA,WAAWa,mBACd,gBAUJf,GAAqB,IAAAI,OAAAA,QAAAC,QAEEW,EAAAA,cAAc,CACnCC,QAASjB,EAAMiB,QACfC,QAASlB,EAAMmB,YACfC,UAAWpB,EAAMA,SACjBqB,KAAA,SAJIC,GAKN,OAAAhB,EACKN,CAAAA,EAAAA,GACHO,OAAQe,EAAWb,EAAAA,YAAYC,SAAWD,EAAWA,YAACE,QACtD,EACJ,CAAC,MAAAY,GAAA,OAAAnB,QAAAoB,OAAAD,IArBYE,CAAyBzB,GAMpC,OAAAI,QAAAC,QAAOL,EACT,CAAC,MAAAuB,UAAAnB,QAAAoB,OAAAD,EAAA,CAAA"}
|
package/package.json
ADDED
@@ -0,0 +1,29 @@
|
|
1
|
+
{
|
2
|
+
"name": "@notabene/verify-proof",
|
3
|
+
"version": "1.0.0-preview.2",
|
4
|
+
"description": "Verify ownership proofs",
|
5
|
+
"source": "src/index.ts",
|
6
|
+
"type": "module",
|
7
|
+
"module": "dist/index.js",
|
8
|
+
"main": "dist/index.cjs",
|
9
|
+
"author": "Pelle Braendgaard",
|
10
|
+
"license": "Apache-2.0",
|
11
|
+
"scripts": {
|
12
|
+
"build:dev": "yarn build && yarn dev",
|
13
|
+
"build:clean": "rimraf dist/ ts-out",
|
14
|
+
"build": "microbundle",
|
15
|
+
"lint": "eslint .",
|
16
|
+
"test": "vitest"
|
17
|
+
},
|
18
|
+
"devDependencies": {
|
19
|
+
"eslint": "^9.9.0",
|
20
|
+
"microbundle": "^0.15.1",
|
21
|
+
"typescript": "^5.5.4",
|
22
|
+
"vitest": "^2.0.5"
|
23
|
+
},
|
24
|
+
"dependencies": {
|
25
|
+
"@notabene/javascript-sdk": "^2.0.0-next.4",
|
26
|
+
"bitcoinjs-message": "^2.2.0",
|
27
|
+
"viem": "^2.19.8"
|
28
|
+
}
|
29
|
+
}
|
@@ -0,0 +1,154 @@
|
|
1
|
+
import { describe, it, expect, vi } from "vitest";
|
2
|
+
import { verifyProof } from "./index";
|
3
|
+
import {
|
4
|
+
type DeclarationProof,
|
5
|
+
type ScreenshotProof,
|
6
|
+
type SignatureProof,
|
7
|
+
ProofStatus,
|
8
|
+
ProofTypes,
|
9
|
+
} from "@notabene/javascript-sdk/src/types";
|
10
|
+
import { verifyMessage } from "viem";
|
11
|
+
|
12
|
+
// Mock viem's verifyMessage function
|
13
|
+
vi.mock("viem", () => ({
|
14
|
+
verifyMessage: vi.fn(),
|
15
|
+
}));
|
16
|
+
|
17
|
+
describe("verifyProof", () => {
|
18
|
+
it("should verify a confirmed checkbox proof", async () => {
|
19
|
+
const proof: DeclarationProof = {
|
20
|
+
type: ProofTypes.SelfDeclaration,
|
21
|
+
status: ProofStatus.PENDING,
|
22
|
+
attestation: "I solemly swear",
|
23
|
+
did: "did:example:123",
|
24
|
+
address: "eip155:1:0x1234567890123456789012345678901234567890",
|
25
|
+
confirmed: true,
|
26
|
+
};
|
27
|
+
|
28
|
+
const result = await verifyProof(proof);
|
29
|
+
|
30
|
+
expect(result.status).toBe(ProofStatus.VERIFIED);
|
31
|
+
});
|
32
|
+
|
33
|
+
it("should fail an unconfirmed checkbox proof", async () => {
|
34
|
+
const proof: DeclarationProof = {
|
35
|
+
type: ProofTypes.SelfDeclaration,
|
36
|
+
status: ProofStatus.PENDING,
|
37
|
+
attestation: "I solemly swear",
|
38
|
+
did: "did:example:123",
|
39
|
+
address: "eip155:1:0x1234567890123456789012345678901234567890",
|
40
|
+
confirmed: false,
|
41
|
+
};
|
42
|
+
|
43
|
+
const result = await verifyProof(proof);
|
44
|
+
|
45
|
+
expect(result.status).toBe(ProofStatus.FAILED);
|
46
|
+
});
|
47
|
+
|
48
|
+
it("should flag a screenshot proof with a URL", async () => {
|
49
|
+
const proof: ScreenshotProof = {
|
50
|
+
type: ProofTypes.Screenshot,
|
51
|
+
status: ProofStatus.PENDING,
|
52
|
+
did: "did:example:123",
|
53
|
+
address: "eip155:1:0x1234567890123456789012345678901234567890",
|
54
|
+
url: "https://example.com/screenshot.png",
|
55
|
+
};
|
56
|
+
|
57
|
+
const result = await verifyProof(proof);
|
58
|
+
|
59
|
+
expect(result.status).toBe(ProofStatus.FLAGGED);
|
60
|
+
});
|
61
|
+
|
62
|
+
it("should fail a screenshot proof without a URL", async () => {
|
63
|
+
const proof: ScreenshotProof = {
|
64
|
+
type: ProofTypes.Screenshot,
|
65
|
+
status: ProofStatus.PENDING,
|
66
|
+
did: "did:example:123",
|
67
|
+
address: "eip155:1:0x1234567890123456789012345678901234567890",
|
68
|
+
url: "",
|
69
|
+
};
|
70
|
+
|
71
|
+
const result = await verifyProof(proof);
|
72
|
+
|
73
|
+
expect(result.status).toBe(ProofStatus.FAILED);
|
74
|
+
});
|
75
|
+
|
76
|
+
it("should return the original proof for unknown proof types", async () => {
|
77
|
+
const proof = {
|
78
|
+
type: "UnknownProofType",
|
79
|
+
status: ProofStatus.PENDING,
|
80
|
+
did: "did:example:123",
|
81
|
+
address: "eip155:1:0x1234567890123456789012345678901234567890",
|
82
|
+
};
|
83
|
+
|
84
|
+
// @ts-ignore
|
85
|
+
const result = await verifyProof(proof);
|
86
|
+
|
87
|
+
expect(result).toEqual(proof);
|
88
|
+
});
|
89
|
+
|
90
|
+
it("should verify a valid PersonalSignEIP191 proof", async () => {
|
91
|
+
const proof: SignatureProof = {
|
92
|
+
type: ProofTypes.PersonalSignEIP191,
|
93
|
+
status: ProofStatus.PENDING,
|
94
|
+
did: "did:example:123",
|
95
|
+
address: "eip155:1:0x1234567890123456789012345678901234567890",
|
96
|
+
proof: "0x1234567890",
|
97
|
+
attestation: "I own this address",
|
98
|
+
wallet_provider: "MetaMask",
|
99
|
+
};
|
100
|
+
|
101
|
+
// Mock successful verification
|
102
|
+
(verifyMessage as jest.Mock).mockResolvedValue(true);
|
103
|
+
|
104
|
+
const result = await verifyProof(proof);
|
105
|
+
|
106
|
+
expect(result.status).toBe(ProofStatus.VERIFIED);
|
107
|
+
expect(verifyMessage).toHaveBeenCalledWith({
|
108
|
+
address: "0x1234567890123456789012345678901234567890",
|
109
|
+
message: proof.attestation,
|
110
|
+
signature: proof.proof,
|
111
|
+
});
|
112
|
+
});
|
113
|
+
|
114
|
+
it("should fail an invalid PersonalSignEIP191 proof", async () => {
|
115
|
+
const proof: SignatureProof = {
|
116
|
+
type: ProofTypes.PersonalSignEIP191,
|
117
|
+
status: ProofStatus.PENDING,
|
118
|
+
did: "did:example:123",
|
119
|
+
address: "eip155:1:0x1234567890123456789012345678901234567890",
|
120
|
+
proof: "0x1234567890",
|
121
|
+
attestation: "I own this address",
|
122
|
+
wallet_provider: "MetaMask",
|
123
|
+
};
|
124
|
+
|
125
|
+
// Mock failed verification
|
126
|
+
(verifyMessage as jest.Mock).mockResolvedValue(false);
|
127
|
+
|
128
|
+
const result = await verifyProof(proof);
|
129
|
+
|
130
|
+
expect(result.status).toBe(ProofStatus.FAILED);
|
131
|
+
expect(verifyMessage).toHaveBeenCalledWith({
|
132
|
+
address: "0x1234567890123456789012345678901234567890",
|
133
|
+
message: proof.attestation,
|
134
|
+
signature: proof.proof,
|
135
|
+
});
|
136
|
+
});
|
137
|
+
|
138
|
+
it("should fail if not eip155 proof", async () => {
|
139
|
+
const proof: SignatureProof = {
|
140
|
+
type: ProofTypes.PersonalSignEIP191,
|
141
|
+
status: ProofStatus.PENDING,
|
142
|
+
did: "did:example:123",
|
143
|
+
address:
|
144
|
+
"bip122:000000000019d6689c085ae165831e93:128Lkh3S7CkDTBZ8W7BbpsN3YYizJMp8p6",
|
145
|
+
proof: "0x1234567890",
|
146
|
+
attestation: "I own this address",
|
147
|
+
wallet_provider: "MetaMask",
|
148
|
+
};
|
149
|
+
|
150
|
+
const result = await verifyProof(proof);
|
151
|
+
|
152
|
+
expect(result.status).toBe(ProofStatus.FAILED);
|
153
|
+
});
|
154
|
+
});
|
package/src/index.ts
ADDED
@@ -0,0 +1,54 @@
|
|
1
|
+
import {
|
2
|
+
DeclarationProof,
|
3
|
+
ProofStatus,
|
4
|
+
ProofTypes,
|
5
|
+
ScreenshotProof,
|
6
|
+
SignatureProof,
|
7
|
+
type OwnershipProof,
|
8
|
+
} from "@notabene/javascript-sdk/src/types";
|
9
|
+
import { verifyMessage } from "viem";
|
10
|
+
|
11
|
+
export async function verifyProof(
|
12
|
+
proof: OwnershipProof,
|
13
|
+
): Promise<OwnershipProof> {
|
14
|
+
switch (proof.type) {
|
15
|
+
case ProofTypes.SelfDeclaration:
|
16
|
+
return {
|
17
|
+
...proof,
|
18
|
+
status: (proof as DeclarationProof).confirmed
|
19
|
+
? ProofStatus.VERIFIED
|
20
|
+
: ProofStatus.FAILED,
|
21
|
+
};
|
22
|
+
case ProofTypes.Screenshot:
|
23
|
+
return {
|
24
|
+
...proof,
|
25
|
+
status: (proof as ScreenshotProof).url
|
26
|
+
? ProofStatus.FLAGGED
|
27
|
+
: ProofStatus.FAILED,
|
28
|
+
};
|
29
|
+
case ProofTypes.PersonalSignEIP191:
|
30
|
+
return verifyPersonalSignEIP191(proof as SignatureProof);
|
31
|
+
case ProofTypes.PersonalSignEIP712:
|
32
|
+
case ProofTypes.PersonalSignBIP137:
|
33
|
+
case ProofTypes.PersonalSignXPUB:
|
34
|
+
case ProofTypes.MicroTransfer:
|
35
|
+
}
|
36
|
+
return proof;
|
37
|
+
}
|
38
|
+
|
39
|
+
async function verifyPersonalSignEIP191(
|
40
|
+
proof: SignatureProof,
|
41
|
+
): Promise<SignatureProof> {
|
42
|
+
const [ns, chainId, address] = proof.address.split(/:/);
|
43
|
+
if (ns !== "eip155") return { ...proof, status: ProofStatus.FAILED };
|
44
|
+
|
45
|
+
const verified = await verifyMessage({
|
46
|
+
address: address as `0x${string}`,
|
47
|
+
message: proof.attestation,
|
48
|
+
signature: proof.proof as `0x${string}`,
|
49
|
+
});
|
50
|
+
return {
|
51
|
+
...proof,
|
52
|
+
status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,
|
53
|
+
};
|
54
|
+
}
|
package/tsconfig.json
ADDED
@@ -0,0 +1,32 @@
|
|
1
|
+
{
|
2
|
+
"compilerOptions": {
|
3
|
+
"target": "ES2020",
|
4
|
+
"useDefineForClassFields": true,
|
5
|
+
"module": "ESNext",
|
6
|
+
"lib": ["ES2020", "DOM", "DOM.Iterable"],
|
7
|
+
"skipLibCheck": true,
|
8
|
+
|
9
|
+
/* Bundler mode */
|
10
|
+
"moduleResolution": "bundler",
|
11
|
+
"resolveJsonModule": true,
|
12
|
+
"isolatedModules": true,
|
13
|
+
"noEmit": true,
|
14
|
+
|
15
|
+
/* Linting */
|
16
|
+
"strict": true,
|
17
|
+
"noUnusedLocals": true,
|
18
|
+
"noUnusedParameters": true,
|
19
|
+
"noFallthroughCasesInSwitch": true,
|
20
|
+
|
21
|
+
/* Path aliases */
|
22
|
+
"baseUrl": ".",
|
23
|
+
"paths": {
|
24
|
+
"@/*": ["src/*"]
|
25
|
+
},
|
26
|
+
|
27
|
+
/* Additional settings */
|
28
|
+
"esModuleInterop": true,
|
29
|
+
"forceConsistentCasingInFileNames": true
|
30
|
+
},
|
31
|
+
"include": ["src/**/*.ts", "src/**/*.d.ts", "src/**/*.tsx", "src/**/*.vue"]
|
32
|
+
}
|