@notabene/verify-proof 1.0.0-preview.4 → 1.0.0-preview.6

Sign up to get free protection for your applications and to get access to all the features.
package/README.md CHANGED
@@ -36,10 +36,10 @@ async function checkProof(proof: OwnershipProof) {
36
36
 
37
37
  - Checkbox Confirmation (`ProofTypes.CheckboxConfirmation`)
38
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`)
39
+ - Personal Sign EIP191 (`ProofTypes.EIP191`)
40
+ - Personal Sign EIP712 (`ProofTypes.EIP712`)
41
+ - Personal Sign BIP137 (`ProofTypes.BIP137`)
42
+ - Personal Sign XPUB (`ProofTypes.XPUB`)
43
43
  - Micro Transfer (`ProofTypes.MicroTransfer`)
44
44
 
45
45
  ## Development
@@ -0,0 +1,12 @@
1
+ import { SignatureProof } from "@notabene/javascript-sdk/src/types";
2
+ export declare enum DerivationMode {
3
+ LEGACY = "Legacy",
4
+ NATIVE = "Native SegWit",
5
+ SEGWIT = "SegWit",
6
+ P2SH_SEGWIT = "p2sh",
7
+ BCH = "Bitcoin Cash",
8
+ ETHEREUM = "Ethereum",
9
+ DOGECOIN = "Dogecoin",
10
+ UNKNOWN = "Unknown"
11
+ }
12
+ export declare function verifyBTCSignature(proof: SignatureProof): Promise<SignatureProof>;
package/dist/eth.d.ts ADDED
@@ -0,0 +1,2 @@
1
+ import { SignatureProof } from "@notabene/javascript-sdk/src/types";
2
+ export declare function verifyPersonalSignEIP191(proof: SignatureProof): Promise<SignatureProof>;
package/dist/index.cjs CHANGED
@@ -1,2 +1,2 @@
1
- var e,r,o=require("viem");function s(){return s=Object.assign?Object.assign.bind():function(e){for(var r=1;r<arguments.length;r++){var o=arguments[r];for(var s in o)({}).hasOwnProperty.call(o,s)&&(e[s]=o[s])}return e},s.apply(null,arguments)}exports.ProofStatus=void 0,(e=exports.ProofStatus||(exports.ProofStatus={})).PENDING="pending",e.FAILED="rejected",e.FLAGGED="flagged",e.VERIFIED="verified",exports.ProofTypes=void 0,(r=exports.ProofTypes||(exports.ProofTypes={})).SelfDeclaration="self-declaration",r.PersonalSignEIP191="eip-191",r.PersonalSignEIP712="eip-712",r.PersonalSignBIP137="bip-137",r.PersonalSignXPUB="xpub",r.MicroTransfer="microtransfer",r.Screenshot="screenshot",exports.verifyProof=function(e){try{switch(e.type){case exports.ProofTypes.SelfDeclaration:return Promise.resolve(s({},e,{status:e.confirmed?exports.ProofStatus.VERIFIED:exports.ProofStatus.FAILED}));case exports.ProofTypes.Screenshot:return Promise.resolve(s({},e,{status:e.url?exports.ProofStatus.FLAGGED:exports.ProofStatus.FAILED}));case exports.ProofTypes.PersonalSignEIP191:return function(e){try{var r=e.address.split(/:/),t=r[2];return"eip155"!==r[0]?Promise.resolve(s({},e,{status:exports.ProofStatus.FAILED})):Promise.resolve(o.verifyMessage({address:t,message:e.attestation,signature:e.proof})).then(function(r){return s({},e,{status:r?exports.ProofStatus.VERIFIED:exports.ProofStatus.FAILED})})}catch(e){return Promise.reject(e)}}(e);case exports.ProofTypes.PersonalSignEIP712:case exports.ProofTypes.PersonalSignBIP137:case exports.ProofTypes.PersonalSignXPUB:case exports.ProofTypes.MicroTransfer:}return Promise.resolve(e)}catch(e){return Promise.reject(e)}};
1
+ var e=require("@notabene/javascript-sdk/src/types"),r=require("bitcoinjs-message"),t=require("viem"),o=require("@solana/web3.js"),s=require("tweetnacl"),a=require("@stablelib/base64");function n(e){return e&&"object"==typeof e&&"default"in e?e:{default:e}}function u(e){if(e&&e.__esModule)return e;var r=Object.create(null);return e&&Object.keys(e).forEach(function(t){if("default"!==t){var o=Object.getOwnPropertyDescriptor(e,t);Object.defineProperty(r,t,o.get?o:{enumerable:!0,get:function(){return e[t]}})}}),r.default=e,r}var i,c=/*#__PURE__*/u(r),f=/*#__PURE__*/n(s);function P(){return P=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},P.apply(null,arguments)}!function(e){e.LEGACY="Legacy",e.NATIVE="Native SegWit",e.SEGWIT="SegWit",e.P2SH_SEGWIT="p2sh",e.BCH="Bitcoin Cash",e.ETHEREUM="Ethereum",e.DOGECOIN="Dogecoin",e.UNKNOWN="Unknown"}(i||(i={})),exports.verifyProof=function(r){try{switch(r.type){case e.ProofTypes.SelfDeclaration:return Promise.resolve(P({},r,{status:r.confirmed?e.ProofStatus.VERIFIED:e.ProofStatus.FAILED}));case e.ProofTypes.Screenshot:return Promise.resolve(P({},r,{status:r.url?e.ProofStatus.FLAGGED:e.ProofStatus.FAILED}));case e.ProofTypes.EIP191:return Promise.resolve(function(r){try{var o=r.address.split(/:/),s=o[2];return"eip155"!==o[0]?Promise.resolve(P({},r,{status:e.ProofStatus.FAILED})):Promise.resolve(t.verifyMessage({address:s,message:r.attestation,signature:r.proof})).then(function(t){return P({},r,{status:t?e.ProofStatus.VERIFIED:e.ProofStatus.FAILED})})}catch(e){return Promise.reject(e)}}(r));case e.ProofTypes.ED25519:return Promise.resolve(function(r){try{var t=r.address.split(/:/),s=t[2];if("solana"!==t[0])return Promise.resolve(P({},r,{status:e.ProofStatus.FAILED}));try{var n=new o.PublicKey(s),u=(new TextEncoder).encode(r.attestation),i=a.decode(r.proof),c=f.default.sign.detached.verify(u,i,n.toBytes());return Promise.resolve(P({},r,{status:c?e.ProofStatus.VERIFIED:e.ProofStatus.FAILED}))}catch(t){return Promise.resolve(P({},r,{status:e.ProofStatus.FAILED}))}}catch(e){return Promise.reject(e)}}(r));case e.ProofTypes.EIP712:case e.ProofTypes.BIP137:return Promise.resolve(function(r){try{var t=r.address.split(/:/),o=t[2];if("bip122"!==t[0])return Promise.resolve(P({},r,{status:e.ProofStatus.FAILED}));try{var s=[i.SEGWIT,i.NATIVE].includes(function(e){if(e.match("^(bc1|tb1|ltc1).*"))return i.NATIVE;if(e.match("^[32M].*"))return i.SEGWIT;if(e.match("^[1nmL].*"))return i.LEGACY;if(e.match("^(D).*"))return i.DOGECOIN;throw new Error("INVALID ADDRESS: ".concat(e).concat(" is not a valid or a supported address"))}(o)),a=c.verify(r.attestation,o,r.proof,void 0,s);return Promise.resolve(P({},r,{status:a?e.ProofStatus.VERIFIED:e.ProofStatus.FAILED}))}catch(t){return Promise.resolve(P({},r,{status:e.ProofStatus.FAILED}))}}catch(e){return Promise.reject(e)}}(r))}return Promise.resolve(r)}catch(e){return Promise.reject(e)}};
2
2
  //# sourceMappingURL=index.cjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.cjs","sources":["../src/index.ts"],"sourcesContent":["import { verifyMessage } from \"viem\";\n\nexport type CAIP2 = `${string}:${string}`;\nexport type CAIP10 = `${CAIP2}:${string}`;\nexport type CAIP19 = `${CAIP2}/${string}:${string}`;\nexport type CAIP220 = string;\n\nexport type DTI = string;\nexport type NotabeneAsset = string;\n\n/**\n * The asset of a transaction either a Notabene asset, a CAIP-19 asset, or a DTI.\n *\n * @public\n */\n\nexport type TransactionAsset = NotabeneAsset | CAIP19 | DTI;\n\nexport type BlockchainAddress = string;\nexport type TravelAddress = string;\n\n/**\n * The destination of a transaction either a blockchain address, a CAIP-19 address, or a travel address.\n * @public\n */\nexport type Destination = BlockchainAddress | CAIP10 | TravelAddress;\nexport type Source = BlockchainAddress | CAIP10;\nexport type URI = string;\nexport type DID = `did:${string}:${string}`;\n\n/**\n * Status of the proof\n * @public\n */\nexport enum ProofStatus {\n PENDING = \"pending\", // Verification is pending\n FAILED = \"rejected\", // Rejected\n FLAGGED = \"flagged\", // Flagged for manual review\n VERIFIED = \"verified\", // Verified\n}\n\n/**\n * The type of Proofs supported\n * @public\n **/\nexport enum ProofTypes {\n SelfDeclaration = \"self-declaration\",\n PersonalSignEIP191 = \"eip-191\",\n PersonalSignEIP712 = \"eip-712\",\n PersonalSignBIP137 = \"bip-137\",\n PersonalSignXPUB = \"xpub\",\n MicroTransfer = \"microtransfer\",\n Screenshot = \"screenshot\",\n}\n/**\n * Ownership Proof\n * @public\n */\nexport interface OwnershipProof {\n type: ProofTypes;\n status: ProofStatus;\n did: DID;\n address: CAIP10;\n}\n\n/**\n * Ownership Proof using Message Signature\n * @public\n */\nexport interface SignatureProof extends OwnershipProof {\n type:\n | ProofTypes.PersonalSignEIP191\n | ProofTypes.PersonalSignEIP712\n | ProofTypes.PersonalSignBIP137\n | ProofTypes.PersonalSignXPUB;\n proof: string;\n attestation: string;\n wallet_provider: string;\n}\n\n/**\n * Ownership Proof using Self Declaration\n * @public\n */\nexport interface DeclarationProof extends OwnershipProof {\n type: ProofTypes.SelfDeclaration;\n attestation: string;\n confirmed: boolean;\n}\n\n/**\n * Ownership Proof using Micro Transfer\n * @public\n */\nexport interface MicroTransferProof extends OwnershipProof {\n type: ProofTypes.MicroTransfer;\n txhash: string;\n chain: CAIP2;\n amount: number;\n}\n\n/**\n * Ownership Proof using Screenshot\n * @public\n */\nexport interface ScreenshotProof extends OwnershipProof {\n type: ProofTypes.Screenshot;\n url: string;\n}\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 [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"eip155\") return { ...proof, status: ProofStatus.FAILED };\n\n const verified = await verifyMessage({\n address: 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":["ProofStatus","ProofTypes","proof","type","SelfDeclaration","Promise","resolve","_extends","status","confirmed","VERIFIED","FAILED","Screenshot","url","FLAGGED","PersonalSignEIP191","_proof$address$split","address","split","_","verifyMessage","message","attestation","signature","then","verified","e","reject","verifyPersonalSignEIP191","PersonalSignEIP712","PersonalSignBIP137","PersonalSignXPUB","MicroTransfer"],"mappings":"IAkCYA,EAWAC,4OAXAD,QAAAA,iBAAAA,GAAAA,EAAAA,QAAWA,cAAXA,oBAKX,CAAA,IAJC,QAAA,UACAA,EAAA,OAAA,WACAA,EAAA,QAAA,UACAA,EAAA,SAAA,WAOUC,2BAAAA,EAAAA,QAAAA,aAAAA,QAAUA,WAQrB,CAAA,IAPC,gBAAA,mBACAA,EAAA,mBAAA,UACAA,EAAA,mBAAA,UACAA,EAAA,mBAAA,UACAA,EAAA,iBAAA,OACAA,EAAA,cAAA,gBACAA,EAAA,WAAA,iCA0DoB,SACpBC,OAEA,OAAQA,EAAMC,MACZ,KAAKF,mBAAWG,gBACd,OAAAC,QAAAC,QAAAC,EAAA,CAAA,EACKL,EACHM,CAAAA,OAASN,EAA2BO,UAChCT,QAAWA,YAACU,SACZV,QAAAA,YAAYW,UAEpB,KAAKV,mBAAWW,WACd,OAAAP,QAAAC,QAAAC,EAAA,CAAA,EACKL,EACHM,CAAAA,OAASN,EAA0BW,IAC/Bb,QAAWA,YAACc,QACZd,QAAAA,YAAYW,UAEpB,KAAKV,QAAUA,WAACc,mBACd,OASS,SACbb,GAAqB,IAErB,IAAAc,EAAyBd,EAAMe,QAAQC,MAAM,KAA/BD,EAAOD,KACrB,MAAW,WADFA,EAAEG,GACUd,QAAAC,QAAAC,EAAYL,GAAAA,GAAOM,OAAQR,QAAWA,YAACW,UAASN,QAAAC,QAE9Cc,EAAaA,cAAC,CACnCH,QAASA,EACTI,QAASnB,EAAMoB,YACfC,UAAWrB,EAAMA,SACjBsB,cAJIC,GAKN,OAAAlB,KACKL,EAAK,CACRM,OAAQiB,EAAWzB,QAAAA,YAAYU,SAAWV,oBAAYW,QACtD,EACJ,CAAC,MAAAe,GAAA,OAAArB,QAAAsB,OAAAD,IAxBYE,CAAyB1B,GAClC,KAAKD,mBAAW4B,mBAChB,KAAK5B,QAAAA,WAAW6B,mBAChB,KAAK7B,QAAUA,WAAC8B,iBAChB,KAAK9B,mBAAW+B,eAElB,OAAA3B,QAAAC,QAAOJ,EACT,CAAC,MAAAwB,GAAA,OAAArB,QAAAsB,OAAAD,EAAA,CAAA"}
1
+ {"version":3,"file":"index.cjs","sources":["../src/bitcoin.ts","../src/index.ts","../src/eth.ts","../src/solana.ts"],"sourcesContent":["import {\n ProofStatus,\n SignatureProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport * as bitcoinMessage from \"bitcoinjs-message\";\n\nexport enum DerivationMode {\n LEGACY = \"Legacy\",\n NATIVE = \"Native SegWit\",\n SEGWIT = \"SegWit\",\n P2SH_SEGWIT = \"p2sh\",\n BCH = \"Bitcoin Cash\",\n ETHEREUM = \"Ethereum\",\n DOGECOIN = \"Dogecoin\",\n UNKNOWN = \"Unknown\",\n}\n\nexport async function verifyBTCSignature(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"bip122\") return { ...proof, status: ProofStatus.FAILED };\n try {\n // const messageToBeSigned = message.replace(/\\s+/g, \" \").trim();\n const segwit = [DerivationMode.SEGWIT, DerivationMode.NATIVE].includes(\n getDerivationMode(address),\n );\n const verified = bitcoinMessage.verify(\n proof.attestation,\n address,\n proof.proof,\n undefined,\n segwit,\n );\n\n return {\n ...proof,\n status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,\n };\n } catch (error) {\n return { ...proof, status: ProofStatus.FAILED };\n }\n}\n\nfunction getDerivationMode(address: string) {\n if (address.match(\"^(bc1|tb1|ltc1).*\")) {\n return DerivationMode.NATIVE;\n } else if (address.match(\"^[32M].*\")) {\n return DerivationMode.SEGWIT;\n } else if (address.match(\"^[1nmL].*\")) {\n return DerivationMode.LEGACY;\n } else if (address.match(\"^(D).*\")) {\n return DerivationMode.DOGECOIN;\n } else {\n throw new Error(\n \"INVALID ADDRESS: \"\n .concat(address)\n .concat(\" is not a valid or a supported address\"),\n );\n }\n}\n","import {\n type OwnershipProof,\n SignatureProof,\n DeclarationProof,\n ScreenshotProof,\n ProofTypes,\n ProofStatus,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { verifyBTCSignature } from \"./bitcoin\";\nimport { verifyPersonalSignEIP191 } from \"./eth\";\nimport { verifySolanaSignature } from \"./solana\";\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.EIP191:\n return verifyPersonalSignEIP191(proof as SignatureProof);\n case ProofTypes.ED25519:\n return verifySolanaSignature(proof as SignatureProof);\n case ProofTypes.EIP712:\n case ProofTypes.BIP137:\n return verifyBTCSignature(proof as SignatureProof);\n case ProofTypes.BIP137_XPUB:\n case ProofTypes.MicroTransfer:\n }\n return proof;\n}\n","import {\n ProofStatus,\n SignatureProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { verifyMessage } from \"viem\";\n\nexport async function verifyPersonalSignEIP191(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"eip155\") return { ...proof, status: ProofStatus.FAILED };\n\n const verified = await verifyMessage({\n address: 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","import { PublicKey } from \"@solana/web3.js\";\nimport nacl from \"tweetnacl\";\nimport {\n ProofStatus,\n SignatureProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { decode as decodeBase64 } from \"@stablelib/base64\";\n\nexport async function verifySolanaSignature(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"solana\") return { ...proof, status: ProofStatus.FAILED };\n try {\n const publicKey = new PublicKey(address);\n const messageBytes = new TextEncoder().encode(proof.attestation);\n const signatureBytes = decodeBase64(proof.proof);\n const verified = nacl.sign.detached.verify(\n messageBytes,\n signatureBytes,\n publicKey.toBytes(),\n );\n\n return {\n ...proof,\n status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,\n };\n } catch (error) {\n return { ...proof, status: ProofStatus.FAILED };\n }\n}\n"],"names":["DerivationMode","proof","type","ProofTypes","SelfDeclaration","Promise","resolve","_extends","status","confirmed","ProofStatus","VERIFIED","FAILED","Screenshot","url","FLAGGED","EIP191","_proof$address$split","address","split","verifyMessage","message","attestation","signature","then","verified","e","reject","verifyPersonalSignEIP191","ED25519","publicKey","PublicKey","messageBytes","TextEncoder","encode","signatureBytes","decodeBase64","nacl","sign","detached","verify","toBytes","error","verifySolanaSignature","EIP712","BIP137","segwit","SEGWIT","NATIVE","includes","match","LEGACY","DOGECOIN","Error","concat","getDerivationMode","bitcoinMessage","undefined","verifyBTCSignature"],"mappings":"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"}
package/dist/index.d.ts CHANGED
@@ -1,93 +1,2 @@
1
- export type CAIP2 = `${string}:${string}`;
2
- export type CAIP10 = `${CAIP2}:${string}`;
3
- export type CAIP19 = `${CAIP2}/${string}:${string}`;
4
- export type CAIP220 = string;
5
- export type DTI = string;
6
- export type NotabeneAsset = string;
7
- /**
8
- * The asset of a transaction either a Notabene asset, a CAIP-19 asset, or a DTI.
9
- *
10
- * @public
11
- */
12
- export type TransactionAsset = NotabeneAsset | CAIP19 | DTI;
13
- export type BlockchainAddress = string;
14
- export type TravelAddress = string;
15
- /**
16
- * The destination of a transaction either a blockchain address, a CAIP-19 address, or a travel address.
17
- * @public
18
- */
19
- export type Destination = BlockchainAddress | CAIP10 | TravelAddress;
20
- export type Source = BlockchainAddress | CAIP10;
21
- export type URI = string;
22
- export type DID = `did:${string}:${string}`;
23
- /**
24
- * Status of the proof
25
- * @public
26
- */
27
- export declare enum ProofStatus {
28
- PENDING = "pending",// Verification is pending
29
- FAILED = "rejected",// Rejected
30
- FLAGGED = "flagged",// Flagged for manual review
31
- VERIFIED = "verified"
32
- }
33
- /**
34
- * The type of Proofs supported
35
- * @public
36
- **/
37
- export declare enum ProofTypes {
38
- SelfDeclaration = "self-declaration",
39
- PersonalSignEIP191 = "eip-191",
40
- PersonalSignEIP712 = "eip-712",
41
- PersonalSignBIP137 = "bip-137",
42
- PersonalSignXPUB = "xpub",
43
- MicroTransfer = "microtransfer",
44
- Screenshot = "screenshot"
45
- }
46
- /**
47
- * Ownership Proof
48
- * @public
49
- */
50
- export interface OwnershipProof {
51
- type: ProofTypes;
52
- status: ProofStatus;
53
- did: DID;
54
- address: CAIP10;
55
- }
56
- /**
57
- * Ownership Proof using Message Signature
58
- * @public
59
- */
60
- export interface SignatureProof extends OwnershipProof {
61
- type: ProofTypes.PersonalSignEIP191 | ProofTypes.PersonalSignEIP712 | ProofTypes.PersonalSignBIP137 | ProofTypes.PersonalSignXPUB;
62
- proof: string;
63
- attestation: string;
64
- wallet_provider: string;
65
- }
66
- /**
67
- * Ownership Proof using Self Declaration
68
- * @public
69
- */
70
- export interface DeclarationProof extends OwnershipProof {
71
- type: ProofTypes.SelfDeclaration;
72
- attestation: string;
73
- confirmed: boolean;
74
- }
75
- /**
76
- * Ownership Proof using Micro Transfer
77
- * @public
78
- */
79
- export interface MicroTransferProof extends OwnershipProof {
80
- type: ProofTypes.MicroTransfer;
81
- txhash: string;
82
- chain: CAIP2;
83
- amount: number;
84
- }
85
- /**
86
- * Ownership Proof using Screenshot
87
- * @public
88
- */
89
- export interface ScreenshotProof extends OwnershipProof {
90
- type: ProofTypes.Screenshot;
91
- url: string;
92
- }
1
+ import { type OwnershipProof } from "@notabene/javascript-sdk/src/types";
93
2
  export declare function verifyProof(proof: OwnershipProof): Promise<OwnershipProof>;
package/dist/index.js CHANGED
@@ -1,2 +1,2 @@
1
- import{verifyMessage as e}from"viem";function r(){return r=Object.assign?Object.assign.bind():function(e){for(var r=1;r<arguments.length;r++){var n=arguments[r];for(var t in n)({}).hasOwnProperty.call(n,t)&&(e[t]=n[t])}return e},r.apply(null,arguments)}var n,t,s=function(s){try{switch(s.type){case t.SelfDeclaration:return Promise.resolve(r({},s,{status:s.confirmed?n.VERIFIED:n.FAILED}));case t.Screenshot:return Promise.resolve(r({},s,{status:s.url?n.FLAGGED:n.FAILED}));case t.PersonalSignEIP191:return function(t){try{var s=t.address.split(/:/),i=s[2];return"eip155"!==s[0]?Promise.resolve(r({},t,{status:n.FAILED})):Promise.resolve(e({address:i,message:t.attestation,signature:t.proof})).then(function(e){return r({},t,{status:e?n.VERIFIED:n.FAILED})})}catch(e){return Promise.reject(e)}}(s)}return Promise.resolve(s)}catch(e){return Promise.reject(e)}};!function(e){e.PENDING="pending",e.FAILED="rejected",e.FLAGGED="flagged",e.VERIFIED="verified"}(n||(n={})),function(e){e.SelfDeclaration="self-declaration",e.PersonalSignEIP191="eip-191",e.PersonalSignEIP712="eip-712",e.PersonalSignBIP137="bip-137",e.PersonalSignXPUB="xpub",e.MicroTransfer="microtransfer",e.Screenshot="screenshot"}(t||(t={}));export{n as ProofStatus,t as ProofTypes,s as verifyProof};
1
+ import{ProofStatus as r,ProofTypes as e}from"@notabene/javascript-sdk/src/types";import*as t from"bitcoinjs-message";import{verifyMessage as s}from"viem";import{PublicKey as o}from"@solana/web3.js";import n from"tweetnacl";import{decode as a}from"@stablelib/base64";function i(){return i=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},i.apply(null,arguments)}var c;!function(r){r.LEGACY="Legacy",r.NATIVE="Native SegWit",r.SEGWIT="SegWit",r.P2SH_SEGWIT="p2sh",r.BCH="Bitcoin Cash",r.ETHEREUM="Ethereum",r.DOGECOIN="Dogecoin",r.UNKNOWN="Unknown"}(c||(c={}));var u=function(u){try{switch(u.type){case e.SelfDeclaration:return Promise.resolve(i({},u,{status:u.confirmed?r.VERIFIED:r.FAILED}));case e.Screenshot:return Promise.resolve(i({},u,{status:u.url?r.FLAGGED:r.FAILED}));case e.EIP191:return Promise.resolve(function(e){try{var t=e.address.split(/:/),o=t[2];return"eip155"!==t[0]?Promise.resolve(i({},e,{status:r.FAILED})):Promise.resolve(s({address:o,message:e.attestation,signature:e.proof})).then(function(t){return i({},e,{status:t?r.VERIFIED:r.FAILED})})}catch(r){return Promise.reject(r)}}(u));case e.ED25519:return Promise.resolve(function(e){try{var t=e.address.split(/:/),s=t[2];if("solana"!==t[0])return Promise.resolve(i({},e,{status:r.FAILED}));try{var c=new o(s),u=(new TextEncoder).encode(e.attestation),m=a(e.proof),E=n.sign.detached.verify(u,m,c.toBytes());return Promise.resolve(i({},e,{status:E?r.VERIFIED:r.FAILED}))}catch(t){return Promise.resolve(i({},e,{status:r.FAILED}))}}catch(r){return Promise.reject(r)}}(u));case e.EIP712:case e.BIP137:return Promise.resolve(function(e){try{var s=e.address.split(/:/),o=s[2];if("bip122"!==s[0])return Promise.resolve(i({},e,{status:r.FAILED}));try{var n=[c.SEGWIT,c.NATIVE].includes(function(r){if(r.match("^(bc1|tb1|ltc1).*"))return c.NATIVE;if(r.match("^[32M].*"))return c.SEGWIT;if(r.match("^[1nmL].*"))return c.LEGACY;if(r.match("^(D).*"))return c.DOGECOIN;throw new Error("INVALID ADDRESS: ".concat(r).concat(" is not a valid or a supported address"))}(o)),a=t.verify(e.attestation,o,e.proof,void 0,n);return Promise.resolve(i({},e,{status:a?r.VERIFIED:r.FAILED}))}catch(t){return Promise.resolve(i({},e,{status:r.FAILED}))}}catch(r){return Promise.reject(r)}}(u))}return Promise.resolve(u)}catch(r){return Promise.reject(r)}};export{u as verifyProof};
2
2
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sources":["../src/index.ts"],"sourcesContent":["import { verifyMessage } from \"viem\";\n\nexport type CAIP2 = `${string}:${string}`;\nexport type CAIP10 = `${CAIP2}:${string}`;\nexport type CAIP19 = `${CAIP2}/${string}:${string}`;\nexport type CAIP220 = string;\n\nexport type DTI = string;\nexport type NotabeneAsset = string;\n\n/**\n * The asset of a transaction either a Notabene asset, a CAIP-19 asset, or a DTI.\n *\n * @public\n */\n\nexport type TransactionAsset = NotabeneAsset | CAIP19 | DTI;\n\nexport type BlockchainAddress = string;\nexport type TravelAddress = string;\n\n/**\n * The destination of a transaction either a blockchain address, a CAIP-19 address, or a travel address.\n * @public\n */\nexport type Destination = BlockchainAddress | CAIP10 | TravelAddress;\nexport type Source = BlockchainAddress | CAIP10;\nexport type URI = string;\nexport type DID = `did:${string}:${string}`;\n\n/**\n * Status of the proof\n * @public\n */\nexport enum ProofStatus {\n PENDING = \"pending\", // Verification is pending\n FAILED = \"rejected\", // Rejected\n FLAGGED = \"flagged\", // Flagged for manual review\n VERIFIED = \"verified\", // Verified\n}\n\n/**\n * The type of Proofs supported\n * @public\n **/\nexport enum ProofTypes {\n SelfDeclaration = \"self-declaration\",\n PersonalSignEIP191 = \"eip-191\",\n PersonalSignEIP712 = \"eip-712\",\n PersonalSignBIP137 = \"bip-137\",\n PersonalSignXPUB = \"xpub\",\n MicroTransfer = \"microtransfer\",\n Screenshot = \"screenshot\",\n}\n/**\n * Ownership Proof\n * @public\n */\nexport interface OwnershipProof {\n type: ProofTypes;\n status: ProofStatus;\n did: DID;\n address: CAIP10;\n}\n\n/**\n * Ownership Proof using Message Signature\n * @public\n */\nexport interface SignatureProof extends OwnershipProof {\n type:\n | ProofTypes.PersonalSignEIP191\n | ProofTypes.PersonalSignEIP712\n | ProofTypes.PersonalSignBIP137\n | ProofTypes.PersonalSignXPUB;\n proof: string;\n attestation: string;\n wallet_provider: string;\n}\n\n/**\n * Ownership Proof using Self Declaration\n * @public\n */\nexport interface DeclarationProof extends OwnershipProof {\n type: ProofTypes.SelfDeclaration;\n attestation: string;\n confirmed: boolean;\n}\n\n/**\n * Ownership Proof using Micro Transfer\n * @public\n */\nexport interface MicroTransferProof extends OwnershipProof {\n type: ProofTypes.MicroTransfer;\n txhash: string;\n chain: CAIP2;\n amount: number;\n}\n\n/**\n * Ownership Proof using Screenshot\n * @public\n */\nexport interface ScreenshotProof extends OwnershipProof {\n type: ProofTypes.Screenshot;\n url: string;\n}\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 [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"eip155\") return { ...proof, status: ProofStatus.FAILED };\n\n const verified = await verifyMessage({\n address: 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":["ProofStatus","ProofTypes","verifyProof","proof","type","SelfDeclaration","Promise","resolve","_extends","status","confirmed","VERIFIED","FAILED","Screenshot","url","FLAGGED","PersonalSignEIP191","_proof$address$split","address","split","_","verifyMessage","message","attestation","signature","then","verified","e","reject","verifyPersonalSignEIP191"],"mappings":"6PAAqC,IAkCzBA,EAWAC,EAiEUC,EAAA,SACpBC,OAEA,OAAQA,EAAMC,MACZ,KAAKH,EAAWI,gBACd,OAAAC,QAAAC,QAAAC,EAAA,CAAA,EACKL,EACHM,CAAAA,OAASN,EAA2BO,UAChCV,EAAYW,SACZX,EAAYY,UAEpB,KAAKX,EAAWY,WACd,OAAAP,QAAAC,QAAAC,EAAA,CAAA,EACKL,EACHM,CAAAA,OAASN,EAA0BW,IAC/Bd,EAAYe,QACZf,EAAYY,UAEpB,KAAKX,EAAWe,mBACd,OASS,SACbb,GAAqB,IAErB,IAAAc,EAAyBd,EAAMe,QAAQC,MAAM,KAA/BD,EAAOD,KACrB,MAAW,WADFA,EAAEG,GACUd,QAAAC,QAAAC,EAAYL,GAAAA,GAAOM,OAAQT,EAAYY,UAASN,QAAAC,QAE9Cc,EAAc,CACnCH,QAASA,EACTI,QAASnB,EAAMoB,YACfC,UAAWrB,EAAMA,SACjBsB,cAJIC,GAKN,OAAAlB,KACKL,EAAK,CACRM,OAAQiB,EAAW1B,EAAYW,SAAWX,EAAYY,QACtD,EACJ,CAAC,MAAAe,GAAA,OAAArB,QAAAsB,OAAAD,IAxBYE,CAAyB1B,GAMpC,OAAAG,QAAAC,QAAOJ,EACT,CAAC,MAAAwB,GAAA,OAAArB,QAAAsB,OAAAD,EAAA,CAAA,GAtGD,SAAY3B,GACVA,EAAA,QAAA,UACAA,EAAA,OAAA,WACAA,EAAA,QAAA,UACAA,EAAA,SAAA,UACD,CALD,CAAYA,IAAAA,EAKX,CAAA,IAMD,SAAYC,GACVA,EAAA,gBAAA,mBACAA,EAAA,mBAAA,UACAA,EAAA,mBAAA,UACAA,EAAA,mBAAA,UACAA,EAAA,iBAAA,OACAA,EAAA,cAAA,gBACAA,EAAA,WAAA,YACD,CARD,CAAYA,IAAAA,EAQX,CAAA"}
1
+ {"version":3,"file":"index.js","sources":["../src/bitcoin.ts","../src/eth.ts","../src/index.ts","../src/solana.ts"],"sourcesContent":["import {\n ProofStatus,\n SignatureProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport * as bitcoinMessage from \"bitcoinjs-message\";\n\nexport enum DerivationMode {\n LEGACY = \"Legacy\",\n NATIVE = \"Native SegWit\",\n SEGWIT = \"SegWit\",\n P2SH_SEGWIT = \"p2sh\",\n BCH = \"Bitcoin Cash\",\n ETHEREUM = \"Ethereum\",\n DOGECOIN = \"Dogecoin\",\n UNKNOWN = \"Unknown\",\n}\n\nexport async function verifyBTCSignature(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"bip122\") return { ...proof, status: ProofStatus.FAILED };\n try {\n // const messageToBeSigned = message.replace(/\\s+/g, \" \").trim();\n const segwit = [DerivationMode.SEGWIT, DerivationMode.NATIVE].includes(\n getDerivationMode(address),\n );\n const verified = bitcoinMessage.verify(\n proof.attestation,\n address,\n proof.proof,\n undefined,\n segwit,\n );\n\n return {\n ...proof,\n status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,\n };\n } catch (error) {\n return { ...proof, status: ProofStatus.FAILED };\n }\n}\n\nfunction getDerivationMode(address: string) {\n if (address.match(\"^(bc1|tb1|ltc1).*\")) {\n return DerivationMode.NATIVE;\n } else if (address.match(\"^[32M].*\")) {\n return DerivationMode.SEGWIT;\n } else if (address.match(\"^[1nmL].*\")) {\n return DerivationMode.LEGACY;\n } else if (address.match(\"^(D).*\")) {\n return DerivationMode.DOGECOIN;\n } else {\n throw new Error(\n \"INVALID ADDRESS: \"\n .concat(address)\n .concat(\" is not a valid or a supported address\"),\n );\n }\n}\n","import {\n ProofStatus,\n SignatureProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { verifyMessage } from \"viem\";\n\nexport async function verifyPersonalSignEIP191(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"eip155\") return { ...proof, status: ProofStatus.FAILED };\n\n const verified = await verifyMessage({\n address: 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","import {\n type OwnershipProof,\n SignatureProof,\n DeclarationProof,\n ScreenshotProof,\n ProofTypes,\n ProofStatus,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { verifyBTCSignature } from \"./bitcoin\";\nimport { verifyPersonalSignEIP191 } from \"./eth\";\nimport { verifySolanaSignature } from \"./solana\";\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.EIP191:\n return verifyPersonalSignEIP191(proof as SignatureProof);\n case ProofTypes.ED25519:\n return verifySolanaSignature(proof as SignatureProof);\n case ProofTypes.EIP712:\n case ProofTypes.BIP137:\n return verifyBTCSignature(proof as SignatureProof);\n case ProofTypes.BIP137_XPUB:\n case ProofTypes.MicroTransfer:\n }\n return proof;\n}\n","import { PublicKey } from \"@solana/web3.js\";\nimport nacl from \"tweetnacl\";\nimport {\n ProofStatus,\n SignatureProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { decode as decodeBase64 } from \"@stablelib/base64\";\n\nexport async function verifySolanaSignature(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"solana\") return { ...proof, status: ProofStatus.FAILED };\n try {\n const publicKey = new PublicKey(address);\n const messageBytes = new TextEncoder().encode(proof.attestation);\n const signatureBytes = decodeBase64(proof.proof);\n const verified = nacl.sign.detached.verify(\n messageBytes,\n signatureBytes,\n publicKey.toBytes(),\n );\n\n return {\n ...proof,\n status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,\n };\n } catch (error) {\n return { ...proof, status: ProofStatus.FAILED };\n }\n}\n"],"names":["DerivationMode","verifyProof","proof","type","ProofTypes","SelfDeclaration","Promise","resolve","_extends","status","confirmed","ProofStatus","VERIFIED","FAILED","Screenshot","url","FLAGGED","EIP191","_proof$address$split","address","split","verifyMessage","message","attestation","signature","then","verified","e","reject","verifyPersonalSignEIP191","ED25519","publicKey","PublicKey","messageBytes","TextEncoder","encode","signatureBytes","decodeBase64","nacl","sign","detached","verify","toBytes","error","verifySolanaSignature","EIP712","BIP137","segwit","SEGWIT","NATIVE","includes","match","LEGACY","DOGECOIN","Error","concat","getDerivationMode","bitcoinMessage","undefined","verifyBTCSignature"],"mappings":"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"}
@@ -1,2 +1,2 @@
1
- import{verifyMessage as e}from"viem";function n(){return n=Object.assign?Object.assign.bind():function(e){for(var n=1;n<arguments.length;n++){var r=arguments[n];for(var t in r)({}).hasOwnProperty.call(r,t)&&(e[t]=r[t])}return e},n.apply(null,arguments)}var r,t;async function s(s){switch(s.type){case t.SelfDeclaration:return n({},s,{status:s.confirmed?r.VERIFIED:r.FAILED});case t.Screenshot:return n({},s,{status:s.url?r.FLAGGED:r.FAILED});case t.PersonalSignEIP191:return async function(t){const[s,a,i]=t.address.split(/:/);return n({},t,"eip155"!==s?{status:r.FAILED}:{status:await e({address:i,message:t.attestation,signature:t.proof})?r.VERIFIED:r.FAILED})}(s)}return s}!function(e){e.PENDING="pending",e.FAILED="rejected",e.FLAGGED="flagged",e.VERIFIED="verified"}(r||(r={})),function(e){e.SelfDeclaration="self-declaration",e.PersonalSignEIP191="eip-191",e.PersonalSignEIP712="eip-712",e.PersonalSignBIP137="bip-137",e.PersonalSignXPUB="xpub",e.MicroTransfer="microtransfer",e.Screenshot="screenshot"}(t||(t={}));export{r as ProofStatus,t as ProofTypes,s as verifyProof};
1
+ import{ProofStatus as t,ProofTypes as r}from"@notabene/javascript-sdk/src/types";import*as s from"bitcoinjs-message";import{verifyMessage as e}from"viem";import{PublicKey as n}from"@solana/web3.js";import a from"tweetnacl";import{decode as o}from"@stablelib/base64";function c(){return c=Object.assign?Object.assign.bind():function(t){for(var r=1;r<arguments.length;r++){var s=arguments[r];for(var e in s)({}).hasOwnProperty.call(s,e)&&(t[e]=s[e])}return t},c.apply(null,arguments)}var i;async function u(u){switch(u.type){case r.SelfDeclaration:return c({},u,{status:u.confirmed?t.VERIFIED:t.FAILED});case r.Screenshot:return c({},u,{status:u.url?t.FLAGGED:t.FAILED});case r.EIP191:return async function(r){const[s,n,a]=r.address.split(/:/);return c({},r,"eip155"!==s?{status:t.FAILED}:{status:await e({address:a,message:r.attestation,signature:r.proof})?t.VERIFIED:t.FAILED})}(u);case r.ED25519:return async function(r){const[s,e,i]=r.address.split(/:/);if("solana"!==s)return c({},r,{status:t.FAILED});try{const s=new n(i),e=(new TextEncoder).encode(r.attestation),u=o(r.proof);return c({},r,{status:a.sign.detached.verify(e,u,s.toBytes())?t.VERIFIED:t.FAILED})}catch(s){return c({},r,{status:t.FAILED})}}(u);case r.EIP712:case r.BIP137:return async function(r){const[e,n,a]=r.address.split(/:/);if("bip122"!==e)return c({},r,{status:t.FAILED});try{const e=[i.SEGWIT,i.NATIVE].includes(function(t){if(t.match("^(bc1|tb1|ltc1).*"))return i.NATIVE;if(t.match("^[32M].*"))return i.SEGWIT;if(t.match("^[1nmL].*"))return i.LEGACY;if(t.match("^(D).*"))return i.DOGECOIN;throw new Error("INVALID ADDRESS: ".concat(t).concat(" is not a valid or a supported address"))}(a));return c({},r,{status:s.verify(r.attestation,a,r.proof,void 0,e)?t.VERIFIED:t.FAILED})}catch(s){return c({},r,{status:t.FAILED})}}(u)}return u}!function(t){t.LEGACY="Legacy",t.NATIVE="Native SegWit",t.SEGWIT="SegWit",t.P2SH_SEGWIT="p2sh",t.BCH="Bitcoin Cash",t.ETHEREUM="Ethereum",t.DOGECOIN="Dogecoin",t.UNKNOWN="Unknown"}(i||(i={}));export{u as verifyProof};
2
2
  //# sourceMappingURL=index.modern.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.modern.js","sources":["../src/index.ts"],"sourcesContent":["import { verifyMessage } from \"viem\";\n\nexport type CAIP2 = `${string}:${string}`;\nexport type CAIP10 = `${CAIP2}:${string}`;\nexport type CAIP19 = `${CAIP2}/${string}:${string}`;\nexport type CAIP220 = string;\n\nexport type DTI = string;\nexport type NotabeneAsset = string;\n\n/**\n * The asset of a transaction either a Notabene asset, a CAIP-19 asset, or a DTI.\n *\n * @public\n */\n\nexport type TransactionAsset = NotabeneAsset | CAIP19 | DTI;\n\nexport type BlockchainAddress = string;\nexport type TravelAddress = string;\n\n/**\n * The destination of a transaction either a blockchain address, a CAIP-19 address, or a travel address.\n * @public\n */\nexport type Destination = BlockchainAddress | CAIP10 | TravelAddress;\nexport type Source = BlockchainAddress | CAIP10;\nexport type URI = string;\nexport type DID = `did:${string}:${string}`;\n\n/**\n * Status of the proof\n * @public\n */\nexport enum ProofStatus {\n PENDING = \"pending\", // Verification is pending\n FAILED = \"rejected\", // Rejected\n FLAGGED = \"flagged\", // Flagged for manual review\n VERIFIED = \"verified\", // Verified\n}\n\n/**\n * The type of Proofs supported\n * @public\n **/\nexport enum ProofTypes {\n SelfDeclaration = \"self-declaration\",\n PersonalSignEIP191 = \"eip-191\",\n PersonalSignEIP712 = \"eip-712\",\n PersonalSignBIP137 = \"bip-137\",\n PersonalSignXPUB = \"xpub\",\n MicroTransfer = \"microtransfer\",\n Screenshot = \"screenshot\",\n}\n/**\n * Ownership Proof\n * @public\n */\nexport interface OwnershipProof {\n type: ProofTypes;\n status: ProofStatus;\n did: DID;\n address: CAIP10;\n}\n\n/**\n * Ownership Proof using Message Signature\n * @public\n */\nexport interface SignatureProof extends OwnershipProof {\n type:\n | ProofTypes.PersonalSignEIP191\n | ProofTypes.PersonalSignEIP712\n | ProofTypes.PersonalSignBIP137\n | ProofTypes.PersonalSignXPUB;\n proof: string;\n attestation: string;\n wallet_provider: string;\n}\n\n/**\n * Ownership Proof using Self Declaration\n * @public\n */\nexport interface DeclarationProof extends OwnershipProof {\n type: ProofTypes.SelfDeclaration;\n attestation: string;\n confirmed: boolean;\n}\n\n/**\n * Ownership Proof using Micro Transfer\n * @public\n */\nexport interface MicroTransferProof extends OwnershipProof {\n type: ProofTypes.MicroTransfer;\n txhash: string;\n chain: CAIP2;\n amount: number;\n}\n\n/**\n * Ownership Proof using Screenshot\n * @public\n */\nexport interface ScreenshotProof extends OwnershipProof {\n type: ProofTypes.Screenshot;\n url: string;\n}\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 [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"eip155\") return { ...proof, status: ProofStatus.FAILED };\n\n const verified = await verifyMessage({\n address: 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":["ProofStatus","ProofTypes","verifyProof","proof","type","SelfDeclaration","_extends","status","confirmed","VERIFIED","FAILED","Screenshot","url","FLAGGED","PersonalSignEIP191","async","ns","_","address","split","verifyMessage","message","attestation","signature","verifyPersonalSignEIP191"],"mappings":"6PAkCY,IAAAA,EAWAC,iBAiEUC,EACpBC,GAEA,OAAQA,EAAMC,MACZ,KAAKH,EAAWI,gBACd,OAAAC,KACKH,EAAK,CACRI,OAASJ,EAA2BK,UAChCR,EAAYS,SACZT,EAAYU,SAEpB,KAAKT,EAAWU,WACd,OAAAL,EACKH,CAAAA,EAAAA,EACHI,CAAAA,OAASJ,EAA0BS,IAC/BZ,EAAYa,QACZb,EAAYU,SAEpB,KAAKT,EAAWa,mBACd,OASNC,eACEZ,GAEA,MAAOa,EAAIC,EAAGC,GAAWf,EAAMe,QAAQC,MAAM,KAC7C,OAAqBb,EAAA,CAAA,EAAYH,EAAtB,WAAPa,EAAoCT,CAAAA,OAAQP,EAAYU,QAQlD,CACRH,aAPqBa,EAAc,CACnCF,QAASA,EACTG,QAASlB,EAAMmB,YACfC,UAAWpB,EAAMA,QAIEH,EAAYS,SAAWT,EAAYU,QAE1D,CAxBac,CAAyBrB,GAMpC,OAAOA,CACT,EAtGA,SAAYH,GACVA,EAAA,QAAA,UACAA,EAAA,OAAA,WACAA,EAAA,QAAA,UACAA,EAAA,SAAA,UACD,CALD,CAAYA,IAAAA,EAKX,KAMD,SAAYC,GACVA,EAAA,gBAAA,mBACAA,EAAA,mBAAA,UACAA,EAAA,mBAAA,UACAA,EAAA,mBAAA,UACAA,EAAA,iBAAA,OACAA,EAAA,cAAA,gBACAA,EAAA,WAAA,YACD,CARD,CAAYA,IAAAA,EAQX,CAAA"}
1
+ {"version":3,"file":"index.modern.js","sources":["../src/bitcoin.ts","../src/index.ts","../src/eth.ts","../src/solana.ts"],"sourcesContent":["import {\n ProofStatus,\n SignatureProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport * as bitcoinMessage from \"bitcoinjs-message\";\n\nexport enum DerivationMode {\n LEGACY = \"Legacy\",\n NATIVE = \"Native SegWit\",\n SEGWIT = \"SegWit\",\n P2SH_SEGWIT = \"p2sh\",\n BCH = \"Bitcoin Cash\",\n ETHEREUM = \"Ethereum\",\n DOGECOIN = \"Dogecoin\",\n UNKNOWN = \"Unknown\",\n}\n\nexport async function verifyBTCSignature(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"bip122\") return { ...proof, status: ProofStatus.FAILED };\n try {\n // const messageToBeSigned = message.replace(/\\s+/g, \" \").trim();\n const segwit = [DerivationMode.SEGWIT, DerivationMode.NATIVE].includes(\n getDerivationMode(address),\n );\n const verified = bitcoinMessage.verify(\n proof.attestation,\n address,\n proof.proof,\n undefined,\n segwit,\n );\n\n return {\n ...proof,\n status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,\n };\n } catch (error) {\n return { ...proof, status: ProofStatus.FAILED };\n }\n}\n\nfunction getDerivationMode(address: string) {\n if (address.match(\"^(bc1|tb1|ltc1).*\")) {\n return DerivationMode.NATIVE;\n } else if (address.match(\"^[32M].*\")) {\n return DerivationMode.SEGWIT;\n } else if (address.match(\"^[1nmL].*\")) {\n return DerivationMode.LEGACY;\n } else if (address.match(\"^(D).*\")) {\n return DerivationMode.DOGECOIN;\n } else {\n throw new Error(\n \"INVALID ADDRESS: \"\n .concat(address)\n .concat(\" is not a valid or a supported address\"),\n );\n }\n}\n","import {\n type OwnershipProof,\n SignatureProof,\n DeclarationProof,\n ScreenshotProof,\n ProofTypes,\n ProofStatus,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { verifyBTCSignature } from \"./bitcoin\";\nimport { verifyPersonalSignEIP191 } from \"./eth\";\nimport { verifySolanaSignature } from \"./solana\";\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.EIP191:\n return verifyPersonalSignEIP191(proof as SignatureProof);\n case ProofTypes.ED25519:\n return verifySolanaSignature(proof as SignatureProof);\n case ProofTypes.EIP712:\n case ProofTypes.BIP137:\n return verifyBTCSignature(proof as SignatureProof);\n case ProofTypes.BIP137_XPUB:\n case ProofTypes.MicroTransfer:\n }\n return proof;\n}\n","import {\n ProofStatus,\n SignatureProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { verifyMessage } from \"viem\";\n\nexport async function verifyPersonalSignEIP191(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"eip155\") return { ...proof, status: ProofStatus.FAILED };\n\n const verified = await verifyMessage({\n address: 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","import { PublicKey } from \"@solana/web3.js\";\nimport nacl from \"tweetnacl\";\nimport {\n ProofStatus,\n SignatureProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { decode as decodeBase64 } from \"@stablelib/base64\";\n\nexport async function verifySolanaSignature(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"solana\") return { ...proof, status: ProofStatus.FAILED };\n try {\n const publicKey = new PublicKey(address);\n const messageBytes = new TextEncoder().encode(proof.attestation);\n const signatureBytes = decodeBase64(proof.proof);\n const verified = nacl.sign.detached.verify(\n messageBytes,\n signatureBytes,\n publicKey.toBytes(),\n );\n\n return {\n ...proof,\n status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,\n };\n } catch (error) {\n return { ...proof, status: ProofStatus.FAILED };\n }\n}\n"],"names":["DerivationMode","verifyProof","proof","type","ProofTypes","SelfDeclaration","_extends","status","confirmed","ProofStatus","VERIFIED","FAILED","Screenshot","url","FLAGGED","EIP191","ns","_","address","split","verifyMessage","message","attestation","signature","verifyPersonalSignEIP191","ED25519","async","publicKey","PublicKey","messageBytes","TextEncoder","encode","signatureBytes","decodeBase64","nacl","sign","detached","verify","toBytes","error","verifySolanaSignature","EIP712","BIP137","segwit","SEGWIT","NATIVE","includes","match","LEGACY","DOGECOIN","Error","concat","getDerivationMode","bitcoinMessage","undefined","verifyBTCSignature"],"mappings":"keAMY,IAAAA,iBCMUC,EACpBC,GAEA,OAAQA,EAAMC,MACZ,KAAKC,EAAWC,gBACd,OAAAC,EACKJ,CAAAA,EAAAA,EACHK,CAAAA,OAASL,EAA2BM,UAChCC,EAAYC,SACZD,EAAYE,SAEpB,KAAKP,EAAWQ,WACd,OAAAN,EACKJ,GAAAA,GACHK,OAASL,EAA0BW,IAC/BJ,EAAYK,QACZL,EAAYE,SAEpB,KAAKP,EAAWW,OACd,sBCxBJb,GAEA,MAAOc,EAAIC,EAAGC,GAAWhB,EAAMgB,QAAQC,MAAM,KAC7C,OAAqBb,EAAA,CAAA,EAAYJ,EAAtB,WAAPc,EAAkC,CAAET,OAAQE,EAAYE,QAQlD,CACRJ,aAPqBa,EAAc,CACnCF,QAASA,EACTG,QAASnB,EAAMoB,YACfC,UAAWrB,EAAMA,QAIEO,EAAYC,SAAWD,EAAYE,QAE1D,CDUaa,CAAyBtB,GAClC,KAAKE,EAAWqB,QACd,OEzBCC,eACLxB,GAEA,MAAOc,EAAIC,EAAGC,GAAWhB,EAAMgB,QAAQC,MAAM,KAC7C,GAAW,WAAPH,EAAiB,OAAAV,EAAA,GAAYJ,EAAOK,CAAAA,OAAQE,EAAYE,SAC5D,IACE,MAAMgB,EAAY,IAAIC,EAAUV,GAC1BW,GAAe,IAAIC,aAAcC,OAAO7B,EAAMoB,aAC9CU,EAAiBC,EAAa/B,EAAMA,OAO1C,OAAAI,EAAA,GACKJ,EAAK,CACRK,OARe2B,EAAKC,KAAKC,SAASC,OAClCR,EACAG,EACAL,EAAUW,WAKS7B,EAAYC,SAAWD,EAAYE,QAE1D,CAAE,MAAO4B,GACP,OAAAjC,EAAYJ,CAAAA,EAAAA,GAAOK,OAAQE,EAAYE,QACzC,CACF,CFGa6B,CAAsBtC,GAC/B,KAAKE,EAAWqC,OAChB,KAAKrC,EAAWsC,OACd,ODnBgBhB,eACpBxB,GAEA,MAAOc,EAAIC,EAAGC,GAAWhB,EAAMgB,QAAQC,MAAM,KAC7C,GAAW,WAAPH,EAAiB,OAAAV,EAAA,GAAYJ,EAAK,CAAEK,OAAQE,EAAYE,SAC5D,IAEE,MAAMgC,EAAS,CAAC3C,EAAe4C,OAAQ5C,EAAe6C,QAAQC,SAoBlE,SAA2B5B,GACzB,GAAIA,EAAQ6B,MAAM,qBAChB,OAAO/C,EAAe6C,OACjB,GAAI3B,EAAQ6B,MAAM,YACvB,OAAO/C,EAAe4C,OACjB,GAAI1B,EAAQ6B,MAAM,aACvB,OAAO/C,EAAegD,OACb9B,GAAAA,EAAQ6B,MAAM,UACvB,OAAO/C,EAAeiD,SAEtB,MAAM,IAAIC,MACR,oBACGC,OAAOjC,GACPiC,OAAO,0CAGhB,CAnCMC,CAAkBlC,IAUpB,OAAAZ,EACKJ,CAAAA,EAAAA,GACHK,OAVe8C,EAAehB,OAC9BnC,EAAMoB,YACNJ,EACAhB,EAAMA,WACNoD,EACAX,GAKmBlC,EAAYC,SAAWD,EAAYE,QAE1D,CAAE,MAAO4B,GACP,OAAAjC,EAAYJ,CAAAA,EAAAA,EAAOK,CAAAA,OAAQE,EAAYE,QACzC,CACF,CCNa4C,CAAmBrD,GAI9B,OAAOA,CACT,EDnCA,SAAYF,GACVA,EAAA,OAAA,SACAA,EAAA,OAAA,gBACAA,EAAA,OAAA,SACAA,EAAA,YAAA,OACAA,EAAA,IAAA,eACAA,EAAA,SAAA,WACAA,EAAA,SAAA,WACAA,EAAA,QAAA,SACD,CATD,CAAYA,IAAAA,EASX"}
package/dist/index.umd.js CHANGED
@@ -1,2 +1,2 @@
1
- !function(e,r){"object"==typeof exports&&"undefined"!=typeof module?r(exports,require("viem")):"function"==typeof define&&define.amd?define(["exports","viem"],r):r((e||self).verifyProof={},e.viem)}(this,function(e,r){function o(){return o=Object.assign?Object.assign.bind():function(e){for(var r=1;r<arguments.length;r++){var o=arguments[r];for(var t in o)({}).hasOwnProperty.call(o,t)&&(e[t]=o[t])}return e},o.apply(null,arguments)}var t,s;e.ProofStatus=void 0,(t=e.ProofStatus||(e.ProofStatus={})).PENDING="pending",t.FAILED="rejected",t.FLAGGED="flagged",t.VERIFIED="verified",e.ProofTypes=void 0,(s=e.ProofTypes||(e.ProofTypes={})).SelfDeclaration="self-declaration",s.PersonalSignEIP191="eip-191",s.PersonalSignEIP712="eip-712",s.PersonalSignBIP137="bip-137",s.PersonalSignXPUB="xpub",s.MicroTransfer="microtransfer",s.Screenshot="screenshot",e.verifyProof=function(t){try{switch(t.type){case e.ProofTypes.SelfDeclaration:return Promise.resolve(o({},t,{status:t.confirmed?e.ProofStatus.VERIFIED:e.ProofStatus.FAILED}));case e.ProofTypes.Screenshot:return Promise.resolve(o({},t,{status:t.url?e.ProofStatus.FLAGGED:e.ProofStatus.FAILED}));case e.ProofTypes.PersonalSignEIP191:return function(t){try{var s=t.address.split(/:/),n=s[2];return"eip155"!==s[0]?Promise.resolve(o({},t,{status:e.ProofStatus.FAILED})):Promise.resolve(r.verifyMessage({address:n,message:t.attestation,signature:t.proof})).then(function(r){return o({},t,{status:r?e.ProofStatus.VERIFIED:e.ProofStatus.FAILED})})}catch(e){return Promise.reject(e)}}(t)}return Promise.resolve(t)}catch(e){return Promise.reject(e)}}});
1
+ !function(e,t){"object"==typeof exports&&"undefined"!=typeof module?t(exports,require("@notabene/javascript-sdk/src/types"),require("bitcoinjs-message"),require("viem"),require("@solana/web3.js"),require("tweetnacl"),require("@stablelib/base64")):"function"==typeof define&&define.amd?define(["exports","@notabene/javascript-sdk/src/types","bitcoinjs-message","viem","@solana/web3.js","tweetnacl","@stablelib/base64"],t):t((e||self).verifyProof={},e.types,e.bitcoinjsMessage,e.viem,e.web3_js,e.tweetnacl,e.base64)}(this,function(e,t,r,s,o,a,n){function i(e){return e&&"object"==typeof e&&"default"in e?e:{default:e}}function u(e){if(e&&e.__esModule)return e;var t=Object.create(null);return e&&Object.keys(e).forEach(function(r){if("default"!==r){var s=Object.getOwnPropertyDescriptor(e,r);Object.defineProperty(t,r,s.get?s:{enumerable:!0,get:function(){return e[r]}})}}),t.default=e,t}var c,f=/*#__PURE__*/u(r),l=/*#__PURE__*/i(a);function P(){return P=Object.assign?Object.assign.bind():function(e){for(var t=1;t<arguments.length;t++){var r=arguments[t];for(var s in r)({}).hasOwnProperty.call(r,s)&&(e[s]=r[s])}return e},P.apply(null,arguments)}!function(e){e.LEGACY="Legacy",e.NATIVE="Native SegWit",e.SEGWIT="SegWit",e.P2SH_SEGWIT="p2sh",e.BCH="Bitcoin Cash",e.ETHEREUM="Ethereum",e.DOGECOIN="Dogecoin",e.UNKNOWN="Unknown"}(c||(c={})),e.verifyProof=function(e){try{switch(e.type){case t.ProofTypes.SelfDeclaration:return Promise.resolve(P({},e,{status:e.confirmed?t.ProofStatus.VERIFIED:t.ProofStatus.FAILED}));case t.ProofTypes.Screenshot:return Promise.resolve(P({},e,{status:e.url?t.ProofStatus.FLAGGED:t.ProofStatus.FAILED}));case t.ProofTypes.EIP191:return Promise.resolve(function(e){try{var r=e.address.split(/:/),o=r[2];return"eip155"!==r[0]?Promise.resolve(P({},e,{status:t.ProofStatus.FAILED})):Promise.resolve(s.verifyMessage({address:o,message:e.attestation,signature:e.proof})).then(function(r){return P({},e,{status:r?t.ProofStatus.VERIFIED:t.ProofStatus.FAILED})})}catch(e){return Promise.reject(e)}}(e));case t.ProofTypes.ED25519:return Promise.resolve(function(e){try{var r=e.address.split(/:/),s=r[2];if("solana"!==r[0])return Promise.resolve(P({},e,{status:t.ProofStatus.FAILED}));try{var a=new o.PublicKey(s),i=(new TextEncoder).encode(e.attestation),u=n.decode(e.proof),c=l.default.sign.detached.verify(i,u,a.toBytes());return Promise.resolve(P({},e,{status:c?t.ProofStatus.VERIFIED:t.ProofStatus.FAILED}))}catch(r){return Promise.resolve(P({},e,{status:t.ProofStatus.FAILED}))}}catch(e){return Promise.reject(e)}}(e));case t.ProofTypes.EIP712:case t.ProofTypes.BIP137:return Promise.resolve(function(e){try{var r=e.address.split(/:/),s=r[2];if("bip122"!==r[0])return Promise.resolve(P({},e,{status:t.ProofStatus.FAILED}));try{var o=[c.SEGWIT,c.NATIVE].includes(function(e){if(e.match("^(bc1|tb1|ltc1).*"))return c.NATIVE;if(e.match("^[32M].*"))return c.SEGWIT;if(e.match("^[1nmL].*"))return c.LEGACY;if(e.match("^(D).*"))return c.DOGECOIN;throw new Error("INVALID ADDRESS: ".concat(e).concat(" is not a valid or a supported address"))}(s)),a=f.verify(e.attestation,s,e.proof,void 0,o);return Promise.resolve(P({},e,{status:a?t.ProofStatus.VERIFIED:t.ProofStatus.FAILED}))}catch(r){return Promise.resolve(P({},e,{status:t.ProofStatus.FAILED}))}}catch(e){return Promise.reject(e)}}(e))}return Promise.resolve(e)}catch(e){return Promise.reject(e)}}});
2
2
  //# sourceMappingURL=index.umd.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.umd.js","sources":["../src/index.ts"],"sourcesContent":["import { verifyMessage } from \"viem\";\n\nexport type CAIP2 = `${string}:${string}`;\nexport type CAIP10 = `${CAIP2}:${string}`;\nexport type CAIP19 = `${CAIP2}/${string}:${string}`;\nexport type CAIP220 = string;\n\nexport type DTI = string;\nexport type NotabeneAsset = string;\n\n/**\n * The asset of a transaction either a Notabene asset, a CAIP-19 asset, or a DTI.\n *\n * @public\n */\n\nexport type TransactionAsset = NotabeneAsset | CAIP19 | DTI;\n\nexport type BlockchainAddress = string;\nexport type TravelAddress = string;\n\n/**\n * The destination of a transaction either a blockchain address, a CAIP-19 address, or a travel address.\n * @public\n */\nexport type Destination = BlockchainAddress | CAIP10 | TravelAddress;\nexport type Source = BlockchainAddress | CAIP10;\nexport type URI = string;\nexport type DID = `did:${string}:${string}`;\n\n/**\n * Status of the proof\n * @public\n */\nexport enum ProofStatus {\n PENDING = \"pending\", // Verification is pending\n FAILED = \"rejected\", // Rejected\n FLAGGED = \"flagged\", // Flagged for manual review\n VERIFIED = \"verified\", // Verified\n}\n\n/**\n * The type of Proofs supported\n * @public\n **/\nexport enum ProofTypes {\n SelfDeclaration = \"self-declaration\",\n PersonalSignEIP191 = \"eip-191\",\n PersonalSignEIP712 = \"eip-712\",\n PersonalSignBIP137 = \"bip-137\",\n PersonalSignXPUB = \"xpub\",\n MicroTransfer = \"microtransfer\",\n Screenshot = \"screenshot\",\n}\n/**\n * Ownership Proof\n * @public\n */\nexport interface OwnershipProof {\n type: ProofTypes;\n status: ProofStatus;\n did: DID;\n address: CAIP10;\n}\n\n/**\n * Ownership Proof using Message Signature\n * @public\n */\nexport interface SignatureProof extends OwnershipProof {\n type:\n | ProofTypes.PersonalSignEIP191\n | ProofTypes.PersonalSignEIP712\n | ProofTypes.PersonalSignBIP137\n | ProofTypes.PersonalSignXPUB;\n proof: string;\n attestation: string;\n wallet_provider: string;\n}\n\n/**\n * Ownership Proof using Self Declaration\n * @public\n */\nexport interface DeclarationProof extends OwnershipProof {\n type: ProofTypes.SelfDeclaration;\n attestation: string;\n confirmed: boolean;\n}\n\n/**\n * Ownership Proof using Micro Transfer\n * @public\n */\nexport interface MicroTransferProof extends OwnershipProof {\n type: ProofTypes.MicroTransfer;\n txhash: string;\n chain: CAIP2;\n amount: number;\n}\n\n/**\n * Ownership Proof using Screenshot\n * @public\n */\nexport interface ScreenshotProof extends OwnershipProof {\n type: ProofTypes.Screenshot;\n url: string;\n}\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 [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"eip155\") return { ...proof, status: ProofStatus.FAILED };\n\n const verified = await verifyMessage({\n address: 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":["ProofStatus","ProofTypes","proof","type","SelfDeclaration","Promise","resolve","_extends","status","confirmed","VERIFIED","FAILED","Screenshot","url","FLAGGED","PersonalSignEIP191","_proof$address$split","address","split","_","verifyMessage","message","attestation","signature","then","verified","e","reject","verifyPersonalSignEIP191"],"mappings":"6dAAqC,IAkCzBA,EAWAC,EAXAD,EAAAA,iBAAAA,GAAAA,EAAAA,EAAWA,cAAXA,cAKX,CAAA,IAJC,QAAA,UACAA,EAAA,OAAA,WACAA,EAAA,QAAA,UACAA,EAAA,SAAA,WAOUC,qBAAAA,EAAAA,EAAAA,aAAAA,EAAUA,WAQrB,CAAA,IAPC,gBAAA,mBACAA,EAAA,mBAAA,UACAA,EAAA,mBAAA,UACAA,EAAA,mBAAA,UACAA,EAAA,iBAAA,OACAA,EAAA,cAAA,gBACAA,EAAA,WAAA,2BA0DoB,SACpBC,OAEA,OAAQA,EAAMC,MACZ,KAAKF,aAAWG,gBACd,OAAAC,QAAAC,QAAAC,EAAA,CAAA,EACKL,EACHM,CAAAA,OAASN,EAA2BO,UAChCT,EAAWA,YAACU,SACZV,EAAAA,YAAYW,UAEpB,KAAKV,aAAWW,WACd,OAAAP,QAAAC,QAAAC,EAAA,CAAA,EACKL,EACHM,CAAAA,OAASN,EAA0BW,IAC/Bb,EAAWA,YAACc,QACZd,EAAAA,YAAYW,UAEpB,KAAKV,EAAUA,WAACc,mBACd,OASS,SACbb,GAAqB,IAErB,IAAAc,EAAyBd,EAAMe,QAAQC,MAAM,KAA/BD,EAAOD,KACrB,MAAW,WADFA,EAAEG,GACUd,QAAAC,QAAAC,EAAYL,GAAAA,GAAOM,OAAQR,EAAWA,YAACW,UAASN,QAAAC,QAE9Cc,EAAaA,cAAC,CACnCH,QAASA,EACTI,QAASnB,EAAMoB,YACfC,UAAWrB,EAAMA,SACjBsB,cAJIC,GAKN,OAAAlB,KACKL,EAAK,CACRM,OAAQiB,EAAWzB,EAAAA,YAAYU,SAAWV,cAAYW,QACtD,EACJ,CAAC,MAAAe,GAAA,OAAArB,QAAAsB,OAAAD,IAxBYE,CAAyB1B,GAMpC,OAAAG,QAAAC,QAAOJ,EACT,CAAC,MAAAwB,GAAA,OAAArB,QAAAsB,OAAAD,EAAA,CAAA"}
1
+ {"version":3,"file":"index.umd.js","sources":["../src/bitcoin.ts","../src/index.ts","../src/eth.ts","../src/solana.ts"],"sourcesContent":["import {\n ProofStatus,\n SignatureProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport * as bitcoinMessage from \"bitcoinjs-message\";\n\nexport enum DerivationMode {\n LEGACY = \"Legacy\",\n NATIVE = \"Native SegWit\",\n SEGWIT = \"SegWit\",\n P2SH_SEGWIT = \"p2sh\",\n BCH = \"Bitcoin Cash\",\n ETHEREUM = \"Ethereum\",\n DOGECOIN = \"Dogecoin\",\n UNKNOWN = \"Unknown\",\n}\n\nexport async function verifyBTCSignature(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"bip122\") return { ...proof, status: ProofStatus.FAILED };\n try {\n // const messageToBeSigned = message.replace(/\\s+/g, \" \").trim();\n const segwit = [DerivationMode.SEGWIT, DerivationMode.NATIVE].includes(\n getDerivationMode(address),\n );\n const verified = bitcoinMessage.verify(\n proof.attestation,\n address,\n proof.proof,\n undefined,\n segwit,\n );\n\n return {\n ...proof,\n status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,\n };\n } catch (error) {\n return { ...proof, status: ProofStatus.FAILED };\n }\n}\n\nfunction getDerivationMode(address: string) {\n if (address.match(\"^(bc1|tb1|ltc1).*\")) {\n return DerivationMode.NATIVE;\n } else if (address.match(\"^[32M].*\")) {\n return DerivationMode.SEGWIT;\n } else if (address.match(\"^[1nmL].*\")) {\n return DerivationMode.LEGACY;\n } else if (address.match(\"^(D).*\")) {\n return DerivationMode.DOGECOIN;\n } else {\n throw new Error(\n \"INVALID ADDRESS: \"\n .concat(address)\n .concat(\" is not a valid or a supported address\"),\n );\n }\n}\n","import {\n type OwnershipProof,\n SignatureProof,\n DeclarationProof,\n ScreenshotProof,\n ProofTypes,\n ProofStatus,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { verifyBTCSignature } from \"./bitcoin\";\nimport { verifyPersonalSignEIP191 } from \"./eth\";\nimport { verifySolanaSignature } from \"./solana\";\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.EIP191:\n return verifyPersonalSignEIP191(proof as SignatureProof);\n case ProofTypes.ED25519:\n return verifySolanaSignature(proof as SignatureProof);\n case ProofTypes.EIP712:\n case ProofTypes.BIP137:\n return verifyBTCSignature(proof as SignatureProof);\n case ProofTypes.BIP137_XPUB:\n case ProofTypes.MicroTransfer:\n }\n return proof;\n}\n","import {\n ProofStatus,\n SignatureProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { verifyMessage } from \"viem\";\n\nexport async function verifyPersonalSignEIP191(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"eip155\") return { ...proof, status: ProofStatus.FAILED };\n\n const verified = await verifyMessage({\n address: 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","import { PublicKey } from \"@solana/web3.js\";\nimport nacl from \"tweetnacl\";\nimport {\n ProofStatus,\n SignatureProof,\n} from \"@notabene/javascript-sdk/src/types\";\nimport { decode as decodeBase64 } from \"@stablelib/base64\";\n\nexport async function verifySolanaSignature(\n proof: SignatureProof,\n): Promise<SignatureProof> {\n const [ns, _, address] = proof.address.split(/:/);\n if (ns !== \"solana\") return { ...proof, status: ProofStatus.FAILED };\n try {\n const publicKey = new PublicKey(address);\n const messageBytes = new TextEncoder().encode(proof.attestation);\n const signatureBytes = decodeBase64(proof.proof);\n const verified = nacl.sign.detached.verify(\n messageBytes,\n signatureBytes,\n publicKey.toBytes(),\n );\n\n return {\n ...proof,\n status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,\n };\n } catch (error) {\n return { ...proof, status: ProofStatus.FAILED };\n }\n}\n"],"names":["DerivationMode","proof","type","ProofTypes","SelfDeclaration","Promise","resolve","_extends","status","confirmed","ProofStatus","VERIFIED","FAILED","Screenshot","url","FLAGGED","EIP191","_proof$address$split","address","split","verifyMessage","message","attestation","signature","then","verified","e","reject","verifyPersonalSignEIP191","ED25519","publicKey","PublicKey","messageBytes","TextEncoder","encode","signatureBytes","decodeBase64","nacl","sign","detached","verify","toBytes","error","verifySolanaSignature","EIP712","BIP137","segwit","SEGWIT","NATIVE","includes","match","LEGACY","DOGECOIN","Error","concat","getDerivationMode","bitcoinMessage","undefined","verifyBTCSignature"],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ import { SignatureProof } from "@notabene/javascript-sdk/src/types";
2
+ export declare function verifySolanaSignature(proof: SignatureProof): Promise<SignatureProof>;
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1 @@
1
+ export {};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@notabene/verify-proof",
3
- "version": "1.0.0-preview.4",
3
+ "version": "1.0.0-preview.6",
4
4
  "description": "Verify ownership proofs",
5
5
  "source": "src/index.ts",
6
6
  "type": "module",
@@ -22,13 +22,25 @@
22
22
  "test": "vitest"
23
23
  },
24
24
  "devDependencies": {
25
+ "@types/bitcoinjs-lib": "3.4.0",
26
+ "@types/node": "^22.9.0",
27
+ "bitcoinjs-lib": "^3.2.0",
28
+ "buffer": "^6.0.3",
29
+ "ecpair": "^3.0.0-rc.0",
25
30
  "eslint": "^9.9.0",
26
31
  "microbundle": "^0.15.1",
32
+ "tiny-secp256k1": "^2.2.3",
27
33
  "typescript": "^5.5.4",
28
34
  "vitest": "^2.0.5"
29
35
  },
30
36
  "dependencies": {
37
+ "@notabene/javascript-sdk": "^2.0.2",
38
+ "@solana/web3.js": "^1.95.4",
39
+ "@stablelib/base64": "^2.0.0",
40
+ "bigi": "^1.4.2",
31
41
  "bitcoinjs-message": "^2.2.0",
32
- "viem": "^2.19.8"
42
+ "ox": "^0.1.4",
43
+ "tweetnacl": "^1.0.3",
44
+ "viem": "^2.21.44"
33
45
  }
34
46
  }
package/src/bitcoin.ts ADDED
@@ -0,0 +1,61 @@
1
+ import {
2
+ ProofStatus,
3
+ SignatureProof,
4
+ } from "@notabene/javascript-sdk/src/types";
5
+ import * as bitcoinMessage from "bitcoinjs-message";
6
+
7
+ export enum DerivationMode {
8
+ LEGACY = "Legacy",
9
+ NATIVE = "Native SegWit",
10
+ SEGWIT = "SegWit",
11
+ P2SH_SEGWIT = "p2sh",
12
+ BCH = "Bitcoin Cash",
13
+ ETHEREUM = "Ethereum",
14
+ DOGECOIN = "Dogecoin",
15
+ UNKNOWN = "Unknown",
16
+ }
17
+
18
+ export async function verifyBTCSignature(
19
+ proof: SignatureProof,
20
+ ): Promise<SignatureProof> {
21
+ const [ns, _, address] = proof.address.split(/:/);
22
+ if (ns !== "bip122") return { ...proof, status: ProofStatus.FAILED };
23
+ try {
24
+ // const messageToBeSigned = message.replace(/\s+/g, " ").trim();
25
+ const segwit = [DerivationMode.SEGWIT, DerivationMode.NATIVE].includes(
26
+ getDerivationMode(address),
27
+ );
28
+ const verified = bitcoinMessage.verify(
29
+ proof.attestation,
30
+ address,
31
+ proof.proof,
32
+ undefined,
33
+ segwit,
34
+ );
35
+
36
+ return {
37
+ ...proof,
38
+ status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,
39
+ };
40
+ } catch (error) {
41
+ return { ...proof, status: ProofStatus.FAILED };
42
+ }
43
+ }
44
+
45
+ function getDerivationMode(address: string) {
46
+ if (address.match("^(bc1|tb1|ltc1).*")) {
47
+ return DerivationMode.NATIVE;
48
+ } else if (address.match("^[32M].*")) {
49
+ return DerivationMode.SEGWIT;
50
+ } else if (address.match("^[1nmL].*")) {
51
+ return DerivationMode.LEGACY;
52
+ } else if (address.match("^(D).*")) {
53
+ return DerivationMode.DOGECOIN;
54
+ } else {
55
+ throw new Error(
56
+ "INVALID ADDRESS: "
57
+ .concat(address)
58
+ .concat(" is not a valid or a supported address"),
59
+ );
60
+ }
61
+ }
package/src/eth.ts ADDED
@@ -0,0 +1,22 @@
1
+ import {
2
+ ProofStatus,
3
+ SignatureProof,
4
+ } from "@notabene/javascript-sdk/src/types";
5
+ import { verifyMessage } from "viem";
6
+
7
+ export async function verifyPersonalSignEIP191(
8
+ proof: SignatureProof,
9
+ ): Promise<SignatureProof> {
10
+ const [ns, _, address] = proof.address.split(/:/);
11
+ if (ns !== "eip155") return { ...proof, status: ProofStatus.FAILED };
12
+
13
+ const verified = await verifyMessage({
14
+ address: address as `0x${string}`,
15
+ message: proof.attestation,
16
+ signature: proof.proof as `0x${string}`,
17
+ });
18
+ return {
19
+ ...proof,
20
+ status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,
21
+ };
22
+ }
package/src/index.ts CHANGED
@@ -1,112 +1,14 @@
1
- import { verifyMessage } from "viem";
2
-
3
- export type CAIP2 = `${string}:${string}`;
4
- export type CAIP10 = `${CAIP2}:${string}`;
5
- export type CAIP19 = `${CAIP2}/${string}:${string}`;
6
- export type CAIP220 = string;
7
-
8
- export type DTI = string;
9
- export type NotabeneAsset = string;
10
-
11
- /**
12
- * The asset of a transaction either a Notabene asset, a CAIP-19 asset, or a DTI.
13
- *
14
- * @public
15
- */
16
-
17
- export type TransactionAsset = NotabeneAsset | CAIP19 | DTI;
18
-
19
- export type BlockchainAddress = string;
20
- export type TravelAddress = string;
21
-
22
- /**
23
- * The destination of a transaction either a blockchain address, a CAIP-19 address, or a travel address.
24
- * @public
25
- */
26
- export type Destination = BlockchainAddress | CAIP10 | TravelAddress;
27
- export type Source = BlockchainAddress | CAIP10;
28
- export type URI = string;
29
- export type DID = `did:${string}:${string}`;
30
-
31
- /**
32
- * Status of the proof
33
- * @public
34
- */
35
- export enum ProofStatus {
36
- PENDING = "pending", // Verification is pending
37
- FAILED = "rejected", // Rejected
38
- FLAGGED = "flagged", // Flagged for manual review
39
- VERIFIED = "verified", // Verified
40
- }
41
-
42
- /**
43
- * The type of Proofs supported
44
- * @public
45
- **/
46
- export enum ProofTypes {
47
- SelfDeclaration = "self-declaration",
48
- PersonalSignEIP191 = "eip-191",
49
- PersonalSignEIP712 = "eip-712",
50
- PersonalSignBIP137 = "bip-137",
51
- PersonalSignXPUB = "xpub",
52
- MicroTransfer = "microtransfer",
53
- Screenshot = "screenshot",
54
- }
55
- /**
56
- * Ownership Proof
57
- * @public
58
- */
59
- export interface OwnershipProof {
60
- type: ProofTypes;
61
- status: ProofStatus;
62
- did: DID;
63
- address: CAIP10;
64
- }
65
-
66
- /**
67
- * Ownership Proof using Message Signature
68
- * @public
69
- */
70
- export interface SignatureProof extends OwnershipProof {
71
- type:
72
- | ProofTypes.PersonalSignEIP191
73
- | ProofTypes.PersonalSignEIP712
74
- | ProofTypes.PersonalSignBIP137
75
- | ProofTypes.PersonalSignXPUB;
76
- proof: string;
77
- attestation: string;
78
- wallet_provider: string;
79
- }
80
-
81
- /**
82
- * Ownership Proof using Self Declaration
83
- * @public
84
- */
85
- export interface DeclarationProof extends OwnershipProof {
86
- type: ProofTypes.SelfDeclaration;
87
- attestation: string;
88
- confirmed: boolean;
89
- }
90
-
91
- /**
92
- * Ownership Proof using Micro Transfer
93
- * @public
94
- */
95
- export interface MicroTransferProof extends OwnershipProof {
96
- type: ProofTypes.MicroTransfer;
97
- txhash: string;
98
- chain: CAIP2;
99
- amount: number;
100
- }
101
-
102
- /**
103
- * Ownership Proof using Screenshot
104
- * @public
105
- */
106
- export interface ScreenshotProof extends OwnershipProof {
107
- type: ProofTypes.Screenshot;
108
- url: string;
109
- }
1
+ import {
2
+ type OwnershipProof,
3
+ SignatureProof,
4
+ DeclarationProof,
5
+ ScreenshotProof,
6
+ ProofTypes,
7
+ ProofStatus,
8
+ } from "@notabene/javascript-sdk/src/types";
9
+ import { verifyBTCSignature } from "./bitcoin";
10
+ import { verifyPersonalSignEIP191 } from "./eth";
11
+ import { verifySolanaSignature } from "./solana";
110
12
 
111
13
  export async function verifyProof(
112
14
  proof: OwnershipProof,
@@ -126,29 +28,15 @@ export async function verifyProof(
126
28
  ? ProofStatus.FLAGGED
127
29
  : ProofStatus.FAILED,
128
30
  };
129
- case ProofTypes.PersonalSignEIP191:
31
+ case ProofTypes.EIP191:
130
32
  return verifyPersonalSignEIP191(proof as SignatureProof);
131
- case ProofTypes.PersonalSignEIP712:
132
- case ProofTypes.PersonalSignBIP137:
133
- case ProofTypes.PersonalSignXPUB:
33
+ case ProofTypes.ED25519:
34
+ return verifySolanaSignature(proof as SignatureProof);
35
+ case ProofTypes.EIP712:
36
+ case ProofTypes.BIP137:
37
+ return verifyBTCSignature(proof as SignatureProof);
38
+ case ProofTypes.BIP137_XPUB:
134
39
  case ProofTypes.MicroTransfer:
135
40
  }
136
41
  return proof;
137
42
  }
138
-
139
- async function verifyPersonalSignEIP191(
140
- proof: SignatureProof,
141
- ): Promise<SignatureProof> {
142
- const [ns, _, address] = proof.address.split(/:/);
143
- if (ns !== "eip155") return { ...proof, status: ProofStatus.FAILED };
144
-
145
- const verified = await verifyMessage({
146
- address: address as `0x${string}`,
147
- message: proof.attestation,
148
- signature: proof.proof as `0x${string}`,
149
- });
150
- return {
151
- ...proof,
152
- status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,
153
- };
154
- }
package/src/solana.ts ADDED
@@ -0,0 +1,31 @@
1
+ import { PublicKey } from "@solana/web3.js";
2
+ import nacl from "tweetnacl";
3
+ import {
4
+ ProofStatus,
5
+ SignatureProof,
6
+ } from "@notabene/javascript-sdk/src/types";
7
+ import { decode as decodeBase64 } from "@stablelib/base64";
8
+
9
+ export async function verifySolanaSignature(
10
+ proof: SignatureProof,
11
+ ): Promise<SignatureProof> {
12
+ const [ns, _, address] = proof.address.split(/:/);
13
+ if (ns !== "solana") return { ...proof, status: ProofStatus.FAILED };
14
+ try {
15
+ const publicKey = new PublicKey(address);
16
+ const messageBytes = new TextEncoder().encode(proof.attestation);
17
+ const signatureBytes = decodeBase64(proof.proof);
18
+ const verified = nacl.sign.detached.verify(
19
+ messageBytes,
20
+ signatureBytes,
21
+ publicKey.toBytes(),
22
+ );
23
+
24
+ return {
25
+ ...proof,
26
+ status: verified ? ProofStatus.VERIFIED : ProofStatus.FAILED,
27
+ };
28
+ } catch (error) {
29
+ return { ...proof, status: ProofStatus.FAILED };
30
+ }
31
+ }
@@ -0,0 +1,95 @@
1
+ import { describe, it, expect, vi } from "vitest";
2
+ import * as bitcoin from "bitcoinjs-lib";
3
+ import * as bitcoinMessage from "bitcoinjs-message";
4
+ import { Buffer } from "node:buffer";
5
+
6
+ import { verifyBTCSignature } from "../bitcoin";
7
+ import {
8
+ type SignatureProof,
9
+ ProofStatus,
10
+ ProofTypes,
11
+ } from "@notabene/javascript-sdk/src/types";
12
+
13
+ function rng() {
14
+ return Buffer.from("zzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzz");
15
+ }
16
+
17
+ function signMessage(
18
+ toAddress: (kp: bitcoin.ECPair) => string,
19
+ ): SignatureProof {
20
+ const keyPair = bitcoin.ECPair.makeRandom({ rng: rng });
21
+ const address = toAddress(keyPair);
22
+ const privateKey = keyPair.d.toBuffer(32);
23
+ var attestation = "This is an example of a signed message.";
24
+ var proof = bitcoinMessage
25
+ .sign(attestation, privateKey, keyPair.compressed)
26
+ .toString("base64");
27
+ // console.log("signMessage", { proof, address });
28
+ return {
29
+ type: ProofTypes.BIP137,
30
+ address: `bip122:000000000019d6689c085ae165831e93:${address}`,
31
+ did: `did:pkh:bip122:000000000019d6689c085ae165831e93:${address}`,
32
+ attestation,
33
+ proof,
34
+ status: ProofStatus.PENDING,
35
+ wallet_provider: "MetaMask",
36
+ };
37
+ }
38
+
39
+ function signP2PKHMessage(): SignatureProof {
40
+ return signMessage((kp) => kp.getAddress());
41
+ }
42
+
43
+ function signSegWitMessage(): SignatureProof {
44
+ return signMessage((kp) =>
45
+ bitcoin.address.toBech32(
46
+ bitcoin.crypto.hash160(kp.getPublicKeyBuffer()),
47
+ 0,
48
+ kp.network.bech32 || "bc",
49
+ ),
50
+ );
51
+ }
52
+
53
+ describe("verifyBTCSignature", () => {
54
+ it("handles native segwit addresses", async () => {
55
+ const proof: SignatureProof = signSegWitMessage();
56
+ const result = await verifyBTCSignature(proof);
57
+ expect(result.status).toBe(ProofStatus.VERIFIED);
58
+ });
59
+
60
+ it("verifies legacy bitcoin address signature", async () => {
61
+ const proof: SignatureProof = signP2PKHMessage();
62
+ const result = await verifyBTCSignature(proof);
63
+ expect(result.status).toBe(ProofStatus.VERIFIED);
64
+ });
65
+
66
+ it("fails for invalid bitcoin signature", async () => {
67
+ const proof: SignatureProof = {
68
+ type: ProofTypes.BIP137,
69
+ did: "did:pkh:bip122:000000000019d6689c085ae165831e93:1A1zP1eP5QGefi2DMPTfTL5SLmv7DivfNa",
70
+ address:
71
+ "bip122:000000000019d6689c085ae165831e93:1A1zP1eP5QGefi2DMPTfTL5SLmv7DivfNa",
72
+ attestation: "test message",
73
+ proof: "invalid_signature",
74
+ status: ProofStatus.PENDING,
75
+ };
76
+
77
+ const result = await verifyBTCSignature(proof);
78
+ expect(result.status).toBe(ProofStatus.FAILED);
79
+ });
80
+
81
+ it("returns failed proof for non-BIP122 address", async () => {
82
+ const proof: SignatureProof = {
83
+ type: ProofTypes.EIP191,
84
+ status: ProofStatus.PENDING,
85
+ did: "did:example:123",
86
+ address: "eip155:1:0x1234567890123456789012345678901234567890",
87
+ proof: "0x1234567890",
88
+ attestation: "I own this address",
89
+ wallet_provider: "MetaMask",
90
+ };
91
+
92
+ const result = await verifyBTCSignature(proof);
93
+ expect(result.status).toBe(ProofStatus.FAILED);
94
+ });
95
+ });
@@ -0,0 +1,59 @@
1
+ import { describe, it, expect, vi } from "vitest";
2
+ import { verifyPersonalSignEIP191 } from "../eth";
3
+ import {
4
+ type SignatureProof,
5
+ ProofStatus,
6
+ ProofTypes,
7
+ } from "@notabene/javascript-sdk/src/types";
8
+
9
+ import { Hex, Address, PersonalMessage, Secp256k1, Signature } from "ox";
10
+
11
+ const privateKey = Secp256k1.randomPrivateKey();
12
+ const address = Address.fromPublicKey(Secp256k1.getPublicKey({ privateKey }));
13
+
14
+ function personalSign(): SignatureProof {
15
+ const attestation = "I agree";
16
+ const payload = PersonalMessage.getSignPayload(Hex.fromString(attestation));
17
+ const proof = Signature.toHex(Secp256k1.sign({ payload, privateKey }));
18
+ return {
19
+ type: ProofTypes.EIP191,
20
+ address: `eip155:1:${address}`,
21
+ did: `did:pkh:eip155:1:${address}`,
22
+ attestation,
23
+ proof,
24
+ status: ProofStatus.PENDING,
25
+ wallet_provider: "MetaMask",
26
+ };
27
+ }
28
+
29
+ describe("verifyPersonalSignEIP191", () => {
30
+ it("returns verified proof when valid message and address", async () => {
31
+ const proof = personalSign();
32
+ const result = await verifyPersonalSignEIP191(proof);
33
+
34
+ expect(result.status).toBe(ProofStatus.VERIFIED);
35
+ });
36
+
37
+ it("returns failed proof when invalid message or address", async () => {
38
+ const proof = { ...personalSign(), attestation: "evil text" };
39
+ const result = await verifyPersonalSignEIP191(proof);
40
+
41
+ expect(result.status).toBe(ProofStatus.FAILED);
42
+ });
43
+
44
+ it("returns failed proof for non-EIP155 address", async () => {
45
+ const proof: SignatureProof = {
46
+ type: ProofTypes.EIP191,
47
+ did: `did:pkh:bip122:000000000019d6689c085ae165831e93:128Lkh3S7CkDTBZ8W7BbpsN3YYizJMp8p6`,
48
+ address:
49
+ "bip122:000000000019d6689c085ae165831e93:128Lkh3S7CkDTBZ8W7BbpsN3YYizJMp8p6",
50
+ attestation: "test message",
51
+ proof: "0xabcd",
52
+ status: ProofStatus.PENDING,
53
+ };
54
+
55
+ const result = await verifyPersonalSignEIP191(proof);
56
+
57
+ expect(result.status).toBe(ProofStatus.FAILED);
58
+ });
59
+ });
@@ -1,5 +1,5 @@
1
1
  import { describe, it, expect, vi } from "vitest";
2
- import { verifyProof } from "./index";
2
+ import { verifyProof } from "../index";
3
3
  import {
4
4
  type DeclarationProof,
5
5
  type ScreenshotProof,
@@ -89,7 +89,7 @@ describe("verifyProof", () => {
89
89
 
90
90
  it("should verify a valid PersonalSignEIP191 proof", async () => {
91
91
  const proof: SignatureProof = {
92
- type: ProofTypes.PersonalSignEIP191,
92
+ type: ProofTypes.EIP191,
93
93
  status: ProofStatus.PENDING,
94
94
  did: "did:example:123",
95
95
  address: "eip155:1:0x1234567890123456789012345678901234567890",
@@ -113,7 +113,7 @@ describe("verifyProof", () => {
113
113
 
114
114
  it("should fail an invalid PersonalSignEIP191 proof", async () => {
115
115
  const proof: SignatureProof = {
116
- type: ProofTypes.PersonalSignEIP191,
116
+ type: ProofTypes.EIP191,
117
117
  status: ProofStatus.PENDING,
118
118
  did: "did:example:123",
119
119
  address: "eip155:1:0x1234567890123456789012345678901234567890",
@@ -137,7 +137,7 @@ describe("verifyProof", () => {
137
137
 
138
138
  it("should fail if not eip155 proof", async () => {
139
139
  const proof: SignatureProof = {
140
- type: ProofTypes.PersonalSignEIP191,
140
+ type: ProofTypes.EIP191,
141
141
  status: ProofStatus.PENDING,
142
142
  did: "did:example:123",
143
143
  address:
@@ -0,0 +1,61 @@
1
+ import { describe, it, expect } from "vitest";
2
+ import { Keypair } from "@solana/web3.js";
3
+ import nacl from "tweetnacl";
4
+ import {
5
+ ProofStatus,
6
+ ProofTypes,
7
+ SignatureProof,
8
+ } from "@notabene/javascript-sdk/src/types";
9
+ import { verifySolanaSignature } from "../solana";
10
+
11
+ describe("verifySolanaSignature", () => {
12
+ it("verifies valid Solana signature", async () => {
13
+ // Generate a test keypair
14
+ const keypair = Keypair.generate();
15
+ const message = "Test message";
16
+ const messageBytes = new TextEncoder().encode(message);
17
+ const signature = nacl.sign.detached(messageBytes, keypair.secretKey);
18
+ const proof: SignatureProof = {
19
+ type: ProofTypes.ED25519,
20
+ status: ProofStatus.PENDING,
21
+ did: `did:pkh:solana:5eykt4UsFv8P8NJdTREpY1vzqKqZKvdp:${keypair.publicKey.toString()}`,
22
+ address: `solana:5eykt4UsFv8P8NJdTREpY1vzqKqZKvdp:${keypair.publicKey.toString()}`,
23
+ attestation: message,
24
+ proof: Buffer.from(signature).toString("base64"),
25
+ wallet_provider: "Phantom",
26
+ };
27
+ const result = await verifySolanaSignature(proof);
28
+ expect(result.status).toBe(ProofStatus.VERIFIED);
29
+ });
30
+
31
+ it("fails for invalid signature", async () => {
32
+ const keypair = Keypair.generate();
33
+ const proof: SignatureProof = {
34
+ type: ProofTypes.ED25519,
35
+ status: ProofStatus.PENDING,
36
+ did: `did:pkh:solana:5eykt4UsFv8P8NJdTREpY1vzqKqZKvdp:${keypair.publicKey.toString()}`,
37
+ address: `solana:5eykt4UsFv8P8NJdTREpY1vzqKqZKvdp:${keypair.publicKey.toString()}`,
38
+ attestation: "Test message",
39
+ proof: "invalid_signature",
40
+ wallet_provider: "Phantom",
41
+ };
42
+
43
+ const result = await verifySolanaSignature(proof);
44
+ expect(result.status).toBe(ProofStatus.FAILED);
45
+ });
46
+
47
+ it("fails for non-Solana address", async () => {
48
+ const proof: SignatureProof = {
49
+ type: ProofTypes.ED25519,
50
+ status: ProofStatus.PENDING,
51
+ did: "did:pkh:eth:0x1234567890123456789012345678901234567890",
52
+ address: "eth:1:0x1234567890123456789012345678901234567890",
53
+ attestation: "Test message",
54
+ proof: "some_signature",
55
+ wallet_provider: "MetaMask",
56
+ };
57
+
58
+ const result = await verifySolanaSignature(proof);
59
+ expect(result.status).toBe(ProofStatus.FAILED);
60
+ });
61
+ });