@cofhe/sdk 0.2.0 → 0.3.0
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/CHANGELOG.md +36 -0
- package/chains/defineChain.ts +2 -2
- package/chains/types.ts +3 -3
- package/core/baseBuilder.ts +18 -18
- package/core/client.test.ts +155 -41
- package/core/client.ts +72 -32
- package/core/clientTypes.ts +28 -18
- package/core/config.test.ts +40 -33
- package/core/config.ts +56 -51
- package/core/consts.ts +22 -0
- package/core/decrypt/{MockQueryDecrypterAbi.ts → MockThresholdNetworkAbi.ts} +71 -21
- package/core/decrypt/cofheMocksDecryptForTx.ts +142 -0
- package/core/decrypt/{cofheMocksSealOutput.ts → cofheMocksDecryptForView.ts} +12 -14
- package/core/decrypt/decryptForTxBuilder.ts +340 -0
- package/core/decrypt/{decryptHandleBuilder.ts → decryptForViewBuilder.ts} +75 -42
- package/core/decrypt/tnDecrypt.ts +232 -0
- package/core/decrypt/tnSealOutputV1.ts +5 -5
- package/core/decrypt/tnSealOutputV2.ts +27 -27
- package/core/encrypt/cofheMocksZkVerifySign.ts +19 -26
- package/core/encrypt/encryptInputsBuilder.test.ts +57 -61
- package/core/encrypt/encryptInputsBuilder.ts +65 -42
- package/core/encrypt/zkPackProveVerify.ts +11 -11
- package/core/error.ts +18 -18
- package/core/fetchKeys.test.ts +3 -3
- package/core/fetchKeys.ts +3 -3
- package/core/index.ts +22 -11
- package/core/permits.test.ts +5 -6
- package/core/permits.ts +5 -4
- package/core/utils.ts +10 -10
- package/dist/chains.cjs +4 -7
- package/dist/chains.d.cts +12 -12
- package/dist/chains.d.ts +12 -12
- package/dist/chains.js +1 -1
- package/dist/{chunk-WGCRJCBR.js → chunk-2TPSCOW3.js} +820 -224
- package/dist/{chunk-UGBVZNRT.js → chunk-NWDKXBIP.js} +309 -189
- package/dist/{chunk-WEAZ25JO.js → chunk-TBLR7NNE.js} +4 -7
- package/dist/{clientTypes-5_1nwtUe.d.cts → clientTypes-6aTZPQ_4.d.ts} +233 -173
- package/dist/{clientTypes-Es7fyi65.d.ts → clientTypes-Bhq7pCSA.d.cts} +233 -173
- package/dist/core.cjs +1138 -418
- package/dist/core.d.cts +37 -24
- package/dist/core.d.ts +37 -24
- package/dist/core.js +3 -3
- package/dist/node.cjs +1082 -370
- package/dist/node.d.cts +12 -12
- package/dist/node.d.ts +12 -12
- package/dist/node.js +8 -8
- package/dist/{permit-fUSe6KKq.d.cts → permit-MZ502UBl.d.cts} +30 -33
- package/dist/{permit-fUSe6KKq.d.ts → permit-MZ502UBl.d.ts} +30 -33
- package/dist/permits.cjs +305 -187
- package/dist/permits.d.cts +111 -812
- package/dist/permits.d.ts +111 -812
- package/dist/permits.js +1 -1
- package/dist/types-YiAC4gig.d.cts +33 -0
- package/dist/types-YiAC4gig.d.ts +33 -0
- package/dist/web.cjs +1085 -373
- package/dist/web.d.cts +13 -13
- package/dist/web.d.ts +13 -13
- package/dist/web.js +10 -10
- package/node/client.test.ts +34 -34
- package/node/config.test.ts +11 -11
- package/node/encryptInputs.test.ts +29 -29
- package/node/index.ts +15 -15
- package/package.json +3 -3
- package/permits/localstorage.test.ts +9 -13
- package/permits/onchain-utils.ts +221 -0
- package/permits/permit.test.ts +51 -5
- package/permits/permit.ts +28 -74
- package/permits/store.test.ts +10 -50
- package/permits/store.ts +4 -14
- package/permits/test-utils.ts +10 -2
- package/permits/types.ts +22 -9
- package/permits/utils.ts +0 -4
- package/permits/validation.test.ts +29 -32
- package/permits/validation.ts +112 -194
- package/web/client.web.test.ts +34 -34
- package/web/config.web.test.ts +11 -11
- package/web/encryptInputs.web.test.ts +29 -29
- package/web/index.ts +19 -19
- package/web/worker.builder.web.test.ts +28 -28
- package/web/worker.config.web.test.ts +47 -47
- package/web/worker.output.web.test.ts +10 -10
- package/dist/types-KImPrEIe.d.cts +0 -48
- package/dist/types-KImPrEIe.d.ts +0 -48
package/dist/core.cjs
CHANGED
|
@@ -32,53 +32,53 @@ var nacl__namespace = /*#__PURE__*/_interopNamespace(nacl);
|
|
|
32
32
|
// core/client.ts
|
|
33
33
|
|
|
34
34
|
// core/error.ts
|
|
35
|
-
var
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
return
|
|
80
|
-
})(
|
|
81
|
-
var
|
|
35
|
+
var CofheErrorCode = /* @__PURE__ */ ((CofheErrorCode2) => {
|
|
36
|
+
CofheErrorCode2["InternalError"] = "INTERNAL_ERROR";
|
|
37
|
+
CofheErrorCode2["UnknownEnvironment"] = "UNKNOWN_ENVIRONMENT";
|
|
38
|
+
CofheErrorCode2["InitTfheFailed"] = "INIT_TFHE_FAILED";
|
|
39
|
+
CofheErrorCode2["InitViemFailed"] = "INIT_VIEM_FAILED";
|
|
40
|
+
CofheErrorCode2["InitEthersFailed"] = "INIT_ETHERS_FAILED";
|
|
41
|
+
CofheErrorCode2["NotConnected"] = "NOT_CONNECTED";
|
|
42
|
+
CofheErrorCode2["MissingPublicClient"] = "MISSING_PUBLIC_CLIENT";
|
|
43
|
+
CofheErrorCode2["MissingWalletClient"] = "MISSING_WALLET_CLIENT";
|
|
44
|
+
CofheErrorCode2["MissingProviderParam"] = "MISSING_PROVIDER_PARAM";
|
|
45
|
+
CofheErrorCode2["EmptySecurityZonesParam"] = "EMPTY_SECURITY_ZONES_PARAM";
|
|
46
|
+
CofheErrorCode2["InvalidPermitData"] = "INVALID_PERMIT_DATA";
|
|
47
|
+
CofheErrorCode2["InvalidPermitDomain"] = "INVALID_PERMIT_DOMAIN";
|
|
48
|
+
CofheErrorCode2["PermitNotFound"] = "PERMIT_NOT_FOUND";
|
|
49
|
+
CofheErrorCode2["CannotRemoveLastPermit"] = "CANNOT_REMOVE_LAST_PERMIT";
|
|
50
|
+
CofheErrorCode2["AccountUninitialized"] = "ACCOUNT_UNINITIALIZED";
|
|
51
|
+
CofheErrorCode2["ChainIdUninitialized"] = "CHAIN_ID_UNINITIALIZED";
|
|
52
|
+
CofheErrorCode2["SealOutputFailed"] = "SEAL_OUTPUT_FAILED";
|
|
53
|
+
CofheErrorCode2["SealOutputReturnedNull"] = "SEAL_OUTPUT_RETURNED_NULL";
|
|
54
|
+
CofheErrorCode2["InvalidUtype"] = "INVALID_UTYPE";
|
|
55
|
+
CofheErrorCode2["DecryptFailed"] = "DECRYPT_FAILED";
|
|
56
|
+
CofheErrorCode2["DecryptReturnedNull"] = "DECRYPT_RETURNED_NULL";
|
|
57
|
+
CofheErrorCode2["ZkMocksInsertCtHashesFailed"] = "ZK_MOCKS_INSERT_CT_HASHES_FAILED";
|
|
58
|
+
CofheErrorCode2["ZkMocksCalcCtHashesFailed"] = "ZK_MOCKS_CALC_CT_HASHES_FAILED";
|
|
59
|
+
CofheErrorCode2["ZkMocksVerifySignFailed"] = "ZK_MOCKS_VERIFY_SIGN_FAILED";
|
|
60
|
+
CofheErrorCode2["ZkMocksCreateProofSignatureFailed"] = "ZK_MOCKS_CREATE_PROOF_SIGNATURE_FAILED";
|
|
61
|
+
CofheErrorCode2["ZkVerifyFailed"] = "ZK_VERIFY_FAILED";
|
|
62
|
+
CofheErrorCode2["ZkPackFailed"] = "ZK_PACK_FAILED";
|
|
63
|
+
CofheErrorCode2["ZkProveFailed"] = "ZK_PROVE_FAILED";
|
|
64
|
+
CofheErrorCode2["EncryptRemainingInItems"] = "ENCRYPT_REMAINING_IN_ITEMS";
|
|
65
|
+
CofheErrorCode2["ZkUninitialized"] = "ZK_UNINITIALIZED";
|
|
66
|
+
CofheErrorCode2["ZkVerifierUrlUninitialized"] = "ZK_VERIFIER_URL_UNINITIALIZED";
|
|
67
|
+
CofheErrorCode2["ThresholdNetworkUrlUninitialized"] = "THRESHOLD_NETWORK_URL_UNINITIALIZED";
|
|
68
|
+
CofheErrorCode2["MissingConfig"] = "MISSING_CONFIG";
|
|
69
|
+
CofheErrorCode2["UnsupportedChain"] = "UNSUPPORTED_CHAIN";
|
|
70
|
+
CofheErrorCode2["MissingZkBuilderAndCrsGenerator"] = "MISSING_ZK_BUILDER_AND_CRS_GENERATOR";
|
|
71
|
+
CofheErrorCode2["MissingTfhePublicKeyDeserializer"] = "MISSING_TFHE_PUBLIC_KEY_DESERIALIZER";
|
|
72
|
+
CofheErrorCode2["MissingCompactPkeCrsDeserializer"] = "MISSING_COMPACT_PKE_CRS_DESERIALIZER";
|
|
73
|
+
CofheErrorCode2["MissingFheKey"] = "MISSING_FHE_KEY";
|
|
74
|
+
CofheErrorCode2["MissingCrs"] = "MISSING_CRS";
|
|
75
|
+
CofheErrorCode2["FetchKeysFailed"] = "FETCH_KEYS_FAILED";
|
|
76
|
+
CofheErrorCode2["PublicWalletGetChainIdFailed"] = "PUBLIC_WALLET_GET_CHAIN_ID_FAILED";
|
|
77
|
+
CofheErrorCode2["PublicWalletGetAddressesFailed"] = "PUBLIC_WALLET_GET_ADDRESSES_FAILED";
|
|
78
|
+
CofheErrorCode2["RehydrateKeysStoreFailed"] = "REHYDRATE_KEYS_STORE_FAILED";
|
|
79
|
+
return CofheErrorCode2;
|
|
80
|
+
})(CofheErrorCode || {});
|
|
81
|
+
var CofheError = class _CofheError extends Error {
|
|
82
82
|
code;
|
|
83
83
|
cause;
|
|
84
84
|
hint;
|
|
@@ -86,25 +86,25 @@ var CofhesdkError = class _CofhesdkError extends Error {
|
|
|
86
86
|
constructor({ code, message, cause, hint, context }) {
|
|
87
87
|
const fullMessage = cause ? `${message} | Caused by: ${cause.message}` : message;
|
|
88
88
|
super(fullMessage);
|
|
89
|
-
this.name = "
|
|
89
|
+
this.name = "CofheError";
|
|
90
90
|
this.code = code;
|
|
91
91
|
this.cause = cause;
|
|
92
92
|
this.hint = hint;
|
|
93
93
|
this.context = context;
|
|
94
94
|
if (Error.captureStackTrace) {
|
|
95
|
-
Error.captureStackTrace(this,
|
|
95
|
+
Error.captureStackTrace(this, _CofheError);
|
|
96
96
|
}
|
|
97
97
|
}
|
|
98
98
|
/**
|
|
99
|
-
* Creates a
|
|
100
|
-
* If the error is a
|
|
101
|
-
* If a wrapperError is provided, it is used to create the new
|
|
99
|
+
* Creates a CofheError from an unknown error
|
|
100
|
+
* If the error is a CofheError, it is returned unchanged, else a new CofheError is created
|
|
101
|
+
* If a wrapperError is provided, it is used to create the new CofheError, else a default is used
|
|
102
102
|
*/
|
|
103
103
|
static fromError(error, wrapperError) {
|
|
104
|
-
if (
|
|
104
|
+
if (isCofheError(error))
|
|
105
105
|
return error;
|
|
106
106
|
const cause = error instanceof Error ? error : new Error(`${error}`);
|
|
107
|
-
return new
|
|
107
|
+
return new _CofheError({
|
|
108
108
|
code: wrapperError?.code ?? "INTERNAL_ERROR" /* InternalError */,
|
|
109
109
|
message: wrapperError?.message ?? "An internal error occurred",
|
|
110
110
|
hint: wrapperError?.hint,
|
|
@@ -164,7 +164,7 @@ var bigintSafeJsonStringify = (value) => {
|
|
|
164
164
|
return value2;
|
|
165
165
|
});
|
|
166
166
|
};
|
|
167
|
-
var
|
|
167
|
+
var isCofheError = (error) => error instanceof CofheError;
|
|
168
168
|
|
|
169
169
|
// core/types.ts
|
|
170
170
|
var FheTypes = /* @__PURE__ */ ((FheTypes2) => {
|
|
@@ -315,14 +315,14 @@ async function getPublicClientChainID(publicClient) {
|
|
|
315
315
|
try {
|
|
316
316
|
chainId = publicClient.chain?.id ?? await publicClient.getChainId();
|
|
317
317
|
} catch (e) {
|
|
318
|
-
throw new
|
|
318
|
+
throw new CofheError({
|
|
319
319
|
code: "PUBLIC_WALLET_GET_CHAIN_ID_FAILED" /* PublicWalletGetChainIdFailed */,
|
|
320
320
|
message: "getting chain ID from public client failed",
|
|
321
321
|
cause: e instanceof Error ? e : void 0
|
|
322
322
|
});
|
|
323
323
|
}
|
|
324
324
|
if (chainId === null) {
|
|
325
|
-
throw new
|
|
325
|
+
throw new CofheError({
|
|
326
326
|
code: "PUBLIC_WALLET_GET_CHAIN_ID_FAILED" /* PublicWalletGetChainIdFailed */,
|
|
327
327
|
message: "chain ID from public client is null"
|
|
328
328
|
});
|
|
@@ -337,14 +337,14 @@ async function getWalletClientAccount(walletClient) {
|
|
|
337
337
|
address = (await walletClient.getAddresses())?.[0];
|
|
338
338
|
}
|
|
339
339
|
} catch (e) {
|
|
340
|
-
throw new
|
|
340
|
+
throw new CofheError({
|
|
341
341
|
code: "PUBLIC_WALLET_GET_ADDRESSES_FAILED" /* PublicWalletGetAddressesFailed */,
|
|
342
342
|
message: "getting address from wallet client failed",
|
|
343
343
|
cause: e instanceof Error ? e : void 0
|
|
344
344
|
});
|
|
345
345
|
}
|
|
346
346
|
if (!address) {
|
|
347
|
-
throw new
|
|
347
|
+
throw new CofheError({
|
|
348
348
|
code: "PUBLIC_WALLET_GET_ADDRESSES_FAILED" /* PublicWalletGetAddressesFailed */,
|
|
349
349
|
message: "address from wallet client is null"
|
|
350
350
|
});
|
|
@@ -448,7 +448,7 @@ var zkPack = (items, builder) => {
|
|
|
448
448
|
break;
|
|
449
449
|
}
|
|
450
450
|
default: {
|
|
451
|
-
throw new
|
|
451
|
+
throw new CofheError({
|
|
452
452
|
code: "ZK_PACK_FAILED" /* ZkPackFailed */,
|
|
453
453
|
message: `Invalid utype: ${item.utype}`,
|
|
454
454
|
hint: `Ensure that the utype is valid, using the Encryptable type, for example: Encryptable.uint128(100n)`,
|
|
@@ -460,7 +460,7 @@ var zkPack = (items, builder) => {
|
|
|
460
460
|
}
|
|
461
461
|
}
|
|
462
462
|
if (totalBits > MAX_ENCRYPTABLE_BITS) {
|
|
463
|
-
throw new
|
|
463
|
+
throw new CofheError({
|
|
464
464
|
code: "ZK_PACK_FAILED" /* ZkPackFailed */,
|
|
465
465
|
message: `Total bits ${totalBits} exceeds ${MAX_ENCRYPTABLE_BITS}`,
|
|
466
466
|
hint: `Ensure that the total bits of the items to encrypt does not exceed ${MAX_ENCRYPTABLE_BITS}`,
|
|
@@ -524,14 +524,14 @@ var zkVerify = async (verifierUrl, serializedBytes, address, securityZone, chain
|
|
|
524
524
|
});
|
|
525
525
|
if (!response.ok) {
|
|
526
526
|
const errorBody = await response.text();
|
|
527
|
-
throw new
|
|
527
|
+
throw new CofheError({
|
|
528
528
|
code: "ZK_VERIFY_FAILED" /* ZkVerifyFailed */,
|
|
529
529
|
message: `HTTP error! ZK proof verification failed - ${errorBody}`
|
|
530
530
|
});
|
|
531
531
|
}
|
|
532
532
|
const json = await response.json();
|
|
533
533
|
if (json.status !== "success") {
|
|
534
|
-
throw new
|
|
534
|
+
throw new CofheError({
|
|
535
535
|
code: "ZK_VERIFY_FAILED" /* ZkVerifyFailed */,
|
|
536
536
|
message: `ZK proof verification response malformed - ${json.error}`
|
|
537
537
|
});
|
|
@@ -543,7 +543,7 @@ var zkVerify = async (verifierUrl, serializedBytes, address, securityZone, chain
|
|
|
543
543
|
};
|
|
544
544
|
});
|
|
545
545
|
} catch (e) {
|
|
546
|
-
throw new
|
|
546
|
+
throw new CofheError({
|
|
547
547
|
code: "ZK_VERIFY_FAILED" /* ZkVerifyFailed */,
|
|
548
548
|
message: `ZK proof verification failed`,
|
|
549
549
|
cause: e instanceof Error ? e : void 0
|
|
@@ -661,9 +661,17 @@ var MockZkVerifierAbi = [
|
|
|
661
661
|
},
|
|
662
662
|
{ type: "error", name: "InvalidInputs", inputs: [] }
|
|
663
663
|
];
|
|
664
|
-
|
|
664
|
+
|
|
665
|
+
// core/consts.ts
|
|
666
|
+
var TASK_MANAGER_ADDRESS = "0xeA30c4B8b44078Bbf8a6ef5b9f1eC1626C7848D9";
|
|
667
|
+
var MOCKS_ZK_VERIFIER_ADDRESS = "0x0000000000000000000000000000000000005001";
|
|
668
|
+
var MOCKS_THRESHOLD_NETWORK_ADDRESS = "0x0000000000000000000000000000000000005002";
|
|
669
|
+
var TEST_BED_ADDRESS = "0x0000000000000000000000000000000000005003";
|
|
665
670
|
var MOCKS_ZK_VERIFIER_SIGNER_PRIVATE_KEY = "0x6C8D7F768A6BB4AAFE85E8A2F5A9680355239C7E14646ED62B044E39DE154512";
|
|
666
671
|
var MOCKS_ZK_VERIFIER_SIGNER_ADDRESS = "0x6E12D8C87503D4287c294f2Fdef96ACd9DFf6bd2";
|
|
672
|
+
var MOCKS_DECRYPT_RESULT_SIGNER_PRIVATE_KEY = "0x59c6995e998f97a5a0044966f0945389dc9e86dae88c7a8412f4603b6b78690d";
|
|
673
|
+
|
|
674
|
+
// core/encrypt/cofheMocksZkVerifySign.ts
|
|
667
675
|
function createMockZkVerifierSigner() {
|
|
668
676
|
return viem.createWalletClient({
|
|
669
677
|
chain: chains.hardhat,
|
|
@@ -706,7 +714,7 @@ async function cofheMocksCheckEncryptableBits(items) {
|
|
|
706
714
|
}
|
|
707
715
|
}
|
|
708
716
|
if (totalBits > MAX_ENCRYPTABLE_BITS) {
|
|
709
|
-
throw new
|
|
717
|
+
throw new CofheError({
|
|
710
718
|
code: "ZK_PACK_FAILED" /* ZkPackFailed */,
|
|
711
719
|
message: `Total bits ${totalBits} exceeds ${MAX_ENCRYPTABLE_BITS}`,
|
|
712
720
|
hint: `Ensure that the total bits of the items to encrypt does not exceed ${MAX_ENCRYPTABLE_BITS}`,
|
|
@@ -729,18 +737,18 @@ async function calcCtHashes(items, account, securityZone, publicClient) {
|
|
|
729
737
|
let ctHashes;
|
|
730
738
|
try {
|
|
731
739
|
ctHashes = await publicClient.readContract({
|
|
732
|
-
address:
|
|
740
|
+
address: MOCKS_ZK_VERIFIER_ADDRESS,
|
|
733
741
|
abi: MockZkVerifierAbi,
|
|
734
742
|
functionName: "zkVerifyCalcCtHashesPacked",
|
|
735
743
|
args: calcCtHashesArgs
|
|
736
744
|
});
|
|
737
745
|
} catch (err) {
|
|
738
|
-
throw new
|
|
746
|
+
throw new CofheError({
|
|
739
747
|
code: "ZK_MOCKS_CALC_CT_HASHES_FAILED" /* ZkMocksCalcCtHashesFailed */,
|
|
740
748
|
message: `mockZkVerifySign calcCtHashes failed while calling zkVerifyCalcCtHashesPacked`,
|
|
741
749
|
cause: err instanceof Error ? err : void 0,
|
|
742
750
|
context: {
|
|
743
|
-
address:
|
|
751
|
+
address: MOCKS_ZK_VERIFIER_ADDRESS,
|
|
744
752
|
items,
|
|
745
753
|
account,
|
|
746
754
|
securityZone,
|
|
@@ -750,7 +758,7 @@ async function calcCtHashes(items, account, securityZone, publicClient) {
|
|
|
750
758
|
});
|
|
751
759
|
}
|
|
752
760
|
if (ctHashes.length !== items.length) {
|
|
753
|
-
throw new
|
|
761
|
+
throw new CofheError({
|
|
754
762
|
code: "ZK_MOCKS_CALC_CT_HASHES_FAILED" /* ZkMocksCalcCtHashesFailed */,
|
|
755
763
|
message: `mockZkVerifySign calcCtHashes returned incorrect number of ctHashes`,
|
|
756
764
|
context: {
|
|
@@ -773,7 +781,7 @@ async function insertCtHashes(items, walletClient) {
|
|
|
773
781
|
try {
|
|
774
782
|
const account = walletClient.account;
|
|
775
783
|
await walletClient.writeContract({
|
|
776
|
-
address:
|
|
784
|
+
address: MOCKS_ZK_VERIFIER_ADDRESS,
|
|
777
785
|
abi: MockZkVerifierAbi,
|
|
778
786
|
functionName: "insertPackedCtHashes",
|
|
779
787
|
args: insertPackedCtHashesArgs,
|
|
@@ -781,7 +789,7 @@ async function insertCtHashes(items, walletClient) {
|
|
|
781
789
|
account
|
|
782
790
|
});
|
|
783
791
|
} catch (err) {
|
|
784
|
-
throw new
|
|
792
|
+
throw new CofheError({
|
|
785
793
|
code: "ZK_MOCKS_INSERT_CT_HASHES_FAILED" /* ZkMocksInsertCtHashesFailed */,
|
|
786
794
|
message: `mockZkVerifySign insertPackedCtHashes failed while calling insertPackedCtHashes`,
|
|
787
795
|
cause: err instanceof Error ? err : void 0,
|
|
@@ -799,7 +807,7 @@ async function createProofSignatures(items, securityZone) {
|
|
|
799
807
|
try {
|
|
800
808
|
encInputSignerClient = createMockZkVerifierSigner();
|
|
801
809
|
} catch (err) {
|
|
802
|
-
throw new
|
|
810
|
+
throw new CofheError({
|
|
803
811
|
code: "ZK_MOCKS_CREATE_PROOF_SIGNATURE_FAILED" /* ZkMocksCreateProofSignatureFailed */,
|
|
804
812
|
message: `mockZkVerifySign createProofSignatures failed while creating wallet client`,
|
|
805
813
|
cause: err instanceof Error ? err : void 0,
|
|
@@ -820,7 +828,7 @@ async function createProofSignatures(items, securityZone) {
|
|
|
820
828
|
signatures.push(signature);
|
|
821
829
|
}
|
|
822
830
|
} catch (err) {
|
|
823
|
-
throw new
|
|
831
|
+
throw new CofheError({
|
|
824
832
|
code: "ZK_MOCKS_CREATE_PROOF_SIGNATURE_FAILED" /* ZkMocksCreateProofSignatureFailed */,
|
|
825
833
|
message: `mockZkVerifySign createProofSignatures failed while calling signMessage`,
|
|
826
834
|
cause: err instanceof Error ? err : void 0,
|
|
@@ -831,7 +839,7 @@ async function createProofSignatures(items, securityZone) {
|
|
|
831
839
|
});
|
|
832
840
|
}
|
|
833
841
|
if (signatures.length !== items.length) {
|
|
834
|
-
throw new
|
|
842
|
+
throw new CofheError({
|
|
835
843
|
code: "ZK_MOCKS_CREATE_PROOF_SIGNATURE_FAILED" /* ZkMocksCreateProofSignatureFailed */,
|
|
836
844
|
message: `mockZkVerifySign createProofSignatures returned incorrect number of signatures`,
|
|
837
845
|
context: {
|
|
@@ -861,21 +869,18 @@ var CofheChainSchema = zod.z.object({
|
|
|
861
869
|
/** Network identifier */
|
|
862
870
|
network: zod.z.string().min(1),
|
|
863
871
|
/** coFhe service URL */
|
|
864
|
-
coFheUrl: zod.z.
|
|
872
|
+
coFheUrl: zod.z.url(),
|
|
865
873
|
/** Verifier service URL */
|
|
866
|
-
verifierUrl: zod.z.
|
|
874
|
+
verifierUrl: zod.z.url(),
|
|
867
875
|
/** Threshold network service URL */
|
|
868
|
-
thresholdNetworkUrl: zod.z.
|
|
876
|
+
thresholdNetworkUrl: zod.z.url(),
|
|
869
877
|
/** Environment type */
|
|
870
878
|
environment: EnvironmentSchema
|
|
871
879
|
});
|
|
872
|
-
|
|
873
|
-
// chains/defineChain.ts
|
|
874
880
|
function defineChain(chainConfig) {
|
|
875
881
|
const result = CofheChainSchema.safeParse(chainConfig);
|
|
876
882
|
if (!result.success) {
|
|
877
|
-
|
|
878
|
-
throw new Error(`Invalid chain configuration: ${errorMessages.join(", ")}`);
|
|
883
|
+
throw new Error(`Invalid chain configuration: ${zod.z.prettifyError(result.error)}`, { cause: result.error });
|
|
879
884
|
}
|
|
880
885
|
return result.data;
|
|
881
886
|
}
|
|
@@ -891,46 +896,51 @@ var hardhat2 = defineChain({
|
|
|
891
896
|
thresholdNetworkUrl: "http://127.0.0.1:3000",
|
|
892
897
|
environment: "MOCK"
|
|
893
898
|
});
|
|
894
|
-
var
|
|
899
|
+
var CofheConfigSchema = zod.z.object({
|
|
895
900
|
/** Environment that the SDK is running in */
|
|
896
901
|
environment: zod.z.enum(["node", "hardhat", "web", "react"]).optional().default("node"),
|
|
897
902
|
/** List of supported chain configurations */
|
|
898
903
|
supportedChains: zod.z.array(zod.z.custom()),
|
|
899
|
-
/** How permits are generated */
|
|
900
|
-
permitGeneration: zod.z.enum(["ON_CONNECT", "ON_DECRYPT_HANDLES", "MANUAL"]).optional().default("ON_CONNECT"),
|
|
901
904
|
/** Default permit expiration in seconds, default is 30 days */
|
|
902
905
|
defaultPermitExpiration: zod.z.number().optional().default(60 * 60 * 24 * 30),
|
|
903
906
|
/** Storage method for fhe keys (defaults to indexedDB on web, filesystem on node) */
|
|
904
907
|
fheKeyStorage: zod.z.object({
|
|
905
|
-
getItem: zod.z.
|
|
906
|
-
|
|
907
|
-
|
|
908
|
+
getItem: zod.z.custom((val) => typeof val === "function", {
|
|
909
|
+
message: "getItem must be a function"
|
|
910
|
+
}),
|
|
911
|
+
setItem: zod.z.custom((val) => typeof val === "function", {
|
|
912
|
+
message: "setItem must be a function"
|
|
913
|
+
}),
|
|
914
|
+
removeItem: zod.z.custom((val) => typeof val === "function", {
|
|
915
|
+
message: "removeItem must be a function"
|
|
916
|
+
})
|
|
908
917
|
}).or(zod.z.null()).default(null),
|
|
909
918
|
/** Whether to use Web Workers for ZK proof generation (web platform only) */
|
|
910
919
|
useWorkers: zod.z.boolean().optional().default(true),
|
|
911
920
|
/** Mocks configs */
|
|
912
921
|
mocks: zod.z.object({
|
|
913
|
-
|
|
914
|
-
|
|
922
|
+
decryptDelay: zod.z.number().optional().default(0),
|
|
923
|
+
encryptDelay: zod.z.union([zod.z.number(), zod.z.tuple([zod.z.number(), zod.z.number(), zod.z.number(), zod.z.number(), zod.z.number()])]).optional().default([100, 100, 100, 500, 500])
|
|
924
|
+
}).optional().default({ decryptDelay: 0, encryptDelay: [100, 100, 100, 500, 500] }),
|
|
915
925
|
/** Internal configuration */
|
|
916
926
|
_internal: zod.z.object({
|
|
917
927
|
zkvWalletClient: zod.z.any().optional()
|
|
918
928
|
}).optional()
|
|
919
929
|
});
|
|
920
|
-
function
|
|
921
|
-
const result =
|
|
930
|
+
function createCofheConfigBase(config) {
|
|
931
|
+
const result = CofheConfigSchema.safeParse(config);
|
|
922
932
|
if (!result.success) {
|
|
923
|
-
throw new Error(`Invalid
|
|
933
|
+
throw new Error(`Invalid cofhe configuration: ${zod.z.prettifyError(result.error)}`, { cause: result.error });
|
|
924
934
|
}
|
|
925
935
|
return result.data;
|
|
926
936
|
}
|
|
927
|
-
var
|
|
937
|
+
var getCofheConfigItem = (config, key) => {
|
|
928
938
|
return config[key];
|
|
929
939
|
};
|
|
930
940
|
function getSupportedChainOrThrow(config, chainId) {
|
|
931
941
|
const supportedChain = config.supportedChains.find((chain) => chain.id === chainId);
|
|
932
942
|
if (!supportedChain) {
|
|
933
|
-
throw new
|
|
943
|
+
throw new CofheError({
|
|
934
944
|
code: "UNSUPPORTED_CHAIN" /* UnsupportedChain */,
|
|
935
945
|
message: `Config does not support chain <${chainId}>`,
|
|
936
946
|
hint: "Ensure config passed to client has been created with this chain in the config.supportedChains array.",
|
|
@@ -946,7 +956,7 @@ function getCoFheUrlOrThrow(config, chainId) {
|
|
|
946
956
|
const supportedChain = getSupportedChainOrThrow(config, chainId);
|
|
947
957
|
const url = supportedChain.coFheUrl;
|
|
948
958
|
if (!url) {
|
|
949
|
-
throw new
|
|
959
|
+
throw new CofheError({
|
|
950
960
|
code: "MISSING_CONFIG" /* MissingConfig */,
|
|
951
961
|
message: `CoFHE URL is not configured for chain <${chainId}>`,
|
|
952
962
|
hint: "Ensure this chain config includes a coFheUrl property.",
|
|
@@ -959,7 +969,7 @@ function getZkVerifierUrlOrThrow(config, chainId) {
|
|
|
959
969
|
const supportedChain = getSupportedChainOrThrow(config, chainId);
|
|
960
970
|
const url = supportedChain.verifierUrl;
|
|
961
971
|
if (!url) {
|
|
962
|
-
throw new
|
|
972
|
+
throw new CofheError({
|
|
963
973
|
code: "ZK_VERIFIER_URL_UNINITIALIZED" /* ZkVerifierUrlUninitialized */,
|
|
964
974
|
message: `ZK verifier URL is not configured for chain <${chainId}>`,
|
|
965
975
|
hint: "Ensure this chain config includes a verifierUrl property.",
|
|
@@ -972,7 +982,7 @@ function getThresholdNetworkUrlOrThrow(config, chainId) {
|
|
|
972
982
|
const supportedChain = getSupportedChainOrThrow(config, chainId);
|
|
973
983
|
const url = supportedChain.thresholdNetworkUrl;
|
|
974
984
|
if (!url) {
|
|
975
|
-
throw new
|
|
985
|
+
throw new CofheError({
|
|
976
986
|
code: "THRESHOLD_NETWORK_URL_UNINITIALIZED" /* ThresholdNetworkUrlUninitialized */,
|
|
977
987
|
message: `Threshold network URL is not configured for chain <${chainId}>`,
|
|
978
988
|
hint: "Ensure this chain config includes a thresholdNetworkUrl property.",
|
|
@@ -1184,7 +1194,7 @@ var BaseBuilder = class {
|
|
|
1184
1194
|
account;
|
|
1185
1195
|
constructor(params) {
|
|
1186
1196
|
if (!params.config) {
|
|
1187
|
-
throw new
|
|
1197
|
+
throw new CofheError({
|
|
1188
1198
|
code: "MISSING_CONFIG" /* MissingConfig */,
|
|
1189
1199
|
message: "Builder config is undefined",
|
|
1190
1200
|
hint: "Ensure client has been created with a config.",
|
|
@@ -1202,12 +1212,12 @@ var BaseBuilder = class {
|
|
|
1202
1212
|
}
|
|
1203
1213
|
/**
|
|
1204
1214
|
* Asserts that this.chainId is populated
|
|
1205
|
-
* @throws {
|
|
1215
|
+
* @throws {CofheError} If chainId is not set
|
|
1206
1216
|
*/
|
|
1207
1217
|
assertChainId() {
|
|
1208
1218
|
if (this.chainId)
|
|
1209
1219
|
return;
|
|
1210
|
-
throw new
|
|
1220
|
+
throw new CofheError({
|
|
1211
1221
|
code: "CHAIN_ID_UNINITIALIZED" /* ChainIdUninitialized */,
|
|
1212
1222
|
message: "Chain ID is not set",
|
|
1213
1223
|
hint: "Ensure client.connect() has been called and awaited, or use setChainId(...) to set the chainId explicitly.",
|
|
@@ -1218,12 +1228,12 @@ var BaseBuilder = class {
|
|
|
1218
1228
|
}
|
|
1219
1229
|
/**
|
|
1220
1230
|
* Asserts that this.account is populated
|
|
1221
|
-
* @throws {
|
|
1231
|
+
* @throws {CofheError} If account is not set
|
|
1222
1232
|
*/
|
|
1223
1233
|
assertAccount() {
|
|
1224
1234
|
if (this.account)
|
|
1225
1235
|
return;
|
|
1226
|
-
throw new
|
|
1236
|
+
throw new CofheError({
|
|
1227
1237
|
code: "ACCOUNT_UNINITIALIZED" /* AccountUninitialized */,
|
|
1228
1238
|
message: "Account is not set",
|
|
1229
1239
|
hint: "Ensure client.connect() has been called and awaited, or use setAccount(...) to set the account explicitly.",
|
|
@@ -1234,12 +1244,12 @@ var BaseBuilder = class {
|
|
|
1234
1244
|
}
|
|
1235
1245
|
/**
|
|
1236
1246
|
* Asserts that this.publicClient is populated
|
|
1237
|
-
* @throws {
|
|
1247
|
+
* @throws {CofheError} If publicClient is not set
|
|
1238
1248
|
*/
|
|
1239
1249
|
assertPublicClient() {
|
|
1240
1250
|
if (this.publicClient)
|
|
1241
1251
|
return;
|
|
1242
|
-
throw new
|
|
1252
|
+
throw new CofheError({
|
|
1243
1253
|
code: "MISSING_PUBLIC_CLIENT" /* MissingPublicClient */,
|
|
1244
1254
|
message: "Public client not found",
|
|
1245
1255
|
hint: "Ensure client.connect() has been called with a publicClient.",
|
|
@@ -1250,12 +1260,12 @@ var BaseBuilder = class {
|
|
|
1250
1260
|
}
|
|
1251
1261
|
/**
|
|
1252
1262
|
* Asserts that this.walletClient is populated
|
|
1253
|
-
* @throws {
|
|
1263
|
+
* @throws {CofheError} If walletClient is not set
|
|
1254
1264
|
*/
|
|
1255
1265
|
assertWalletClient() {
|
|
1256
1266
|
if (this.walletClient)
|
|
1257
1267
|
return;
|
|
1258
|
-
throw new
|
|
1268
|
+
throw new CofheError({
|
|
1259
1269
|
code: "MISSING_WALLET_CLIENT" /* MissingWalletClient */,
|
|
1260
1270
|
message: "Wallet client not found",
|
|
1261
1271
|
hint: "Ensure client.connect() has been called with a walletClient.",
|
|
@@ -1300,7 +1310,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1300
1310
|
this.securityZone = params.securityZone ?? 0;
|
|
1301
1311
|
this.zkvWalletClient = params.zkvWalletClient;
|
|
1302
1312
|
if (!params.tfhePublicKeyDeserializer) {
|
|
1303
|
-
throw new
|
|
1313
|
+
throw new CofheError({
|
|
1304
1314
|
code: "MISSING_TFHE_PUBLIC_KEY_DESERIALIZER" /* MissingTfhePublicKeyDeserializer */,
|
|
1305
1315
|
message: "EncryptInputsBuilder tfhePublicKeyDeserializer is undefined",
|
|
1306
1316
|
hint: "Ensure client has been created with a tfhePublicKeyDeserializer.",
|
|
@@ -1311,7 +1321,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1311
1321
|
}
|
|
1312
1322
|
this.tfhePublicKeyDeserializer = params.tfhePublicKeyDeserializer;
|
|
1313
1323
|
if (!params.compactPkeCrsDeserializer) {
|
|
1314
|
-
throw new
|
|
1324
|
+
throw new CofheError({
|
|
1315
1325
|
code: "MISSING_COMPACT_PKE_CRS_DESERIALIZER" /* MissingCompactPkeCrsDeserializer */,
|
|
1316
1326
|
message: "EncryptInputsBuilder compactPkeCrsDeserializer is undefined",
|
|
1317
1327
|
hint: "Ensure client has been created with a compactPkeCrsDeserializer.",
|
|
@@ -1322,7 +1332,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1322
1332
|
}
|
|
1323
1333
|
this.compactPkeCrsDeserializer = params.compactPkeCrsDeserializer;
|
|
1324
1334
|
if (!params.zkBuilderAndCrsGenerator) {
|
|
1325
|
-
throw new
|
|
1335
|
+
throw new CofheError({
|
|
1326
1336
|
code: "MISSING_ZK_BUILDER_AND_CRS_GENERATOR" /* MissingZkBuilderAndCrsGenerator */,
|
|
1327
1337
|
message: "EncryptInputsBuilder zkBuilderAndCrsGenerator is undefined",
|
|
1328
1338
|
hint: "Ensure client has been created with a zkBuilderAndCrsGenerator.",
|
|
@@ -1346,7 +1356,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1346
1356
|
* ```typescript
|
|
1347
1357
|
* const encrypted = await encryptInputs([Encryptable.uint128(10n)])
|
|
1348
1358
|
* .setAccount("0x123")
|
|
1349
|
-
* .
|
|
1359
|
+
* .execute();
|
|
1350
1360
|
* ```
|
|
1351
1361
|
*
|
|
1352
1362
|
* @returns The chainable EncryptInputsBuilder instance.
|
|
@@ -1367,7 +1377,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1367
1377
|
* ```typescript
|
|
1368
1378
|
* const encrypted = await encryptInputs([Encryptable.uint128(10n)])
|
|
1369
1379
|
* .setChainId(11155111)
|
|
1370
|
-
* .
|
|
1380
|
+
* .execute();
|
|
1371
1381
|
* ```
|
|
1372
1382
|
*
|
|
1373
1383
|
* @returns The chainable EncryptInputsBuilder instance.
|
|
@@ -1388,7 +1398,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1388
1398
|
* ```typescript
|
|
1389
1399
|
* const encrypted = await encryptInputs([Encryptable.uint128(10n)])
|
|
1390
1400
|
* .setSecurityZone(1)
|
|
1391
|
-
* .
|
|
1401
|
+
* .execute();
|
|
1392
1402
|
* ```
|
|
1393
1403
|
*
|
|
1394
1404
|
* @returns The chainable EncryptInputsBuilder instance.
|
|
@@ -1409,7 +1419,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1409
1419
|
* ```typescript
|
|
1410
1420
|
* const encrypted = await encryptInputs([Encryptable.uint128(10n)])
|
|
1411
1421
|
* .setUseWorker(false)
|
|
1412
|
-
* .
|
|
1422
|
+
* .execute();
|
|
1413
1423
|
* ```
|
|
1414
1424
|
*
|
|
1415
1425
|
* @returns The chainable EncryptInputsBuilder instance.
|
|
@@ -1443,13 +1453,13 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1443
1453
|
* Example:
|
|
1444
1454
|
* ```typescript
|
|
1445
1455
|
* const encrypted = await encryptInputs([Encryptable.uint128(10n)])
|
|
1446
|
-
* .
|
|
1447
|
-
* .
|
|
1456
|
+
* .onStep((step: EncryptStep) => console.log(step))
|
|
1457
|
+
* .execute();
|
|
1448
1458
|
* ```
|
|
1449
1459
|
*
|
|
1450
1460
|
* @returns The EncryptInputsBuilder instance.
|
|
1451
1461
|
*/
|
|
1452
|
-
|
|
1462
|
+
onStep(callback) {
|
|
1453
1463
|
this.stepCallback = callback;
|
|
1454
1464
|
return this;
|
|
1455
1465
|
}
|
|
@@ -1472,7 +1482,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1472
1482
|
this.stepCallback(step, { ...context, isStart: false, isEnd: true, duration });
|
|
1473
1483
|
}
|
|
1474
1484
|
/**
|
|
1475
|
-
* zkVerifierUrl is included in the chains exported from
|
|
1485
|
+
* zkVerifierUrl is included in the chains exported from @cofhe/sdk/chains for use in CofheConfig.supportedChains
|
|
1476
1486
|
* Users should generally not set this manually.
|
|
1477
1487
|
*/
|
|
1478
1488
|
async getZkVerifierUrl() {
|
|
@@ -1480,7 +1490,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1480
1490
|
return getZkVerifierUrlOrThrow(this.config, this.chainId);
|
|
1481
1491
|
}
|
|
1482
1492
|
/**
|
|
1483
|
-
* initTfhe is a platform-specific dependency injected into core/
|
|
1493
|
+
* initTfhe is a platform-specific dependency injected into core/createCofheClientBase by web/createCofheClient and node/createCofheClient
|
|
1484
1494
|
* web/ uses zama "tfhe"
|
|
1485
1495
|
* node/ uses zama "node-tfhe"
|
|
1486
1496
|
* Users should not set this manually.
|
|
@@ -1491,7 +1501,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1491
1501
|
try {
|
|
1492
1502
|
return await this.initTfhe();
|
|
1493
1503
|
} catch (error) {
|
|
1494
|
-
throw
|
|
1504
|
+
throw CofheError.fromError(error, {
|
|
1495
1505
|
code: "INIT_TFHE_FAILED" /* InitTfheFailed */,
|
|
1496
1506
|
message: `Failed to initialize TFHE`,
|
|
1497
1507
|
context: {
|
|
@@ -1510,7 +1520,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1510
1520
|
try {
|
|
1511
1521
|
await this.keysStorage?.rehydrateKeysStore();
|
|
1512
1522
|
} catch (error) {
|
|
1513
|
-
throw
|
|
1523
|
+
throw CofheError.fromError(error, {
|
|
1514
1524
|
code: "REHYDRATE_KEYS_STORE_FAILED" /* RehydrateKeysStoreFailed */,
|
|
1515
1525
|
message: `Failed to rehydrate keys store`,
|
|
1516
1526
|
context: {
|
|
@@ -1532,7 +1542,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1532
1542
|
this.keysStorage
|
|
1533
1543
|
);
|
|
1534
1544
|
} catch (error) {
|
|
1535
|
-
throw
|
|
1545
|
+
throw CofheError.fromError(error, {
|
|
1536
1546
|
code: "FETCH_KEYS_FAILED" /* FetchKeysFailed */,
|
|
1537
1547
|
message: `Failed to fetch FHE key and CRS`,
|
|
1538
1548
|
context: {
|
|
@@ -1545,7 +1555,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1545
1555
|
});
|
|
1546
1556
|
}
|
|
1547
1557
|
if (!fheKey) {
|
|
1548
|
-
throw new
|
|
1558
|
+
throw new CofheError({
|
|
1549
1559
|
code: "MISSING_FHE_KEY" /* MissingFheKey */,
|
|
1550
1560
|
message: `FHE key not found`,
|
|
1551
1561
|
context: {
|
|
@@ -1555,7 +1565,7 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1555
1565
|
});
|
|
1556
1566
|
}
|
|
1557
1567
|
if (!crs) {
|
|
1558
|
-
throw new
|
|
1568
|
+
throw new CofheError({
|
|
1559
1569
|
code: "MISSING_CRS" /* MissingCrs */,
|
|
1560
1570
|
message: `CRS not found for chainId <${this.chainId}>`,
|
|
1561
1571
|
context: {
|
|
@@ -1565,6 +1575,17 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1565
1575
|
}
|
|
1566
1576
|
return { fheKey, fheKeyFetchedFromCoFHE, crs, crsFetchedFromCoFHE };
|
|
1567
1577
|
}
|
|
1578
|
+
/**
|
|
1579
|
+
* Resolves the encryptDelay config into an array of 5 per-step delays.
|
|
1580
|
+
* A single number is broadcast to all steps; a tuple is used as-is.
|
|
1581
|
+
*/
|
|
1582
|
+
resolveEncryptDelays() {
|
|
1583
|
+
const encryptDelay = this.config?.mocks?.encryptDelay ?? [100, 100, 100, 500, 500];
|
|
1584
|
+
if (typeof encryptDelay === "number") {
|
|
1585
|
+
return [encryptDelay, encryptDelay, encryptDelay, encryptDelay, encryptDelay];
|
|
1586
|
+
}
|
|
1587
|
+
return encryptDelay;
|
|
1588
|
+
}
|
|
1568
1589
|
/**
|
|
1569
1590
|
* @dev Encrypt against the cofheMocks instead of CoFHE
|
|
1570
1591
|
*
|
|
@@ -1572,25 +1593,35 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1572
1593
|
* cofheMocksInsertPackedHashes - stores the ctHashes and their plaintext values for on-chain mocking of FHE operations.
|
|
1573
1594
|
* cofheMocksZkCreateProofSignatures - creates signatures to be included in the encrypted inputs. The signers address is known and verified in the mock contracts.
|
|
1574
1595
|
*/
|
|
1575
|
-
async
|
|
1596
|
+
async mocksExecute() {
|
|
1576
1597
|
this.assertAccount();
|
|
1577
1598
|
this.assertPublicClient();
|
|
1578
1599
|
this.assertWalletClient();
|
|
1600
|
+
const [initTfheDelay, fetchKeysDelay, packDelay, proveDelay, verifyDelay] = this.resolveEncryptDelays();
|
|
1579
1601
|
this.fireStepStart("initTfhe" /* InitTfhe */);
|
|
1580
|
-
await sleep(
|
|
1581
|
-
this.fireStepEnd("initTfhe" /* InitTfhe */, {
|
|
1602
|
+
await sleep(initTfheDelay);
|
|
1603
|
+
this.fireStepEnd("initTfhe" /* InitTfhe */, {
|
|
1604
|
+
tfheInitializationExecuted: false,
|
|
1605
|
+
isMocks: true,
|
|
1606
|
+
mockSleep: initTfheDelay
|
|
1607
|
+
});
|
|
1582
1608
|
this.fireStepStart("fetchKeys" /* FetchKeys */);
|
|
1583
|
-
await sleep(
|
|
1584
|
-
this.fireStepEnd("fetchKeys" /* FetchKeys */, {
|
|
1609
|
+
await sleep(fetchKeysDelay);
|
|
1610
|
+
this.fireStepEnd("fetchKeys" /* FetchKeys */, {
|
|
1611
|
+
fheKeyFetchedFromCoFHE: false,
|
|
1612
|
+
crsFetchedFromCoFHE: false,
|
|
1613
|
+
isMocks: true,
|
|
1614
|
+
mockSleep: fetchKeysDelay
|
|
1615
|
+
});
|
|
1585
1616
|
this.fireStepStart("pack" /* Pack */);
|
|
1586
1617
|
await cofheMocksCheckEncryptableBits(this.inputItems);
|
|
1587
|
-
await sleep(
|
|
1588
|
-
this.fireStepEnd("pack" /* Pack
|
|
1618
|
+
await sleep(packDelay);
|
|
1619
|
+
this.fireStepEnd("pack" /* Pack */, { isMocks: true, mockSleep: packDelay });
|
|
1589
1620
|
this.fireStepStart("prove" /* Prove */);
|
|
1590
|
-
await sleep(
|
|
1591
|
-
this.fireStepEnd("prove" /* Prove
|
|
1621
|
+
await sleep(proveDelay);
|
|
1622
|
+
this.fireStepEnd("prove" /* Prove */, { isMocks: true, mockSleep: proveDelay });
|
|
1592
1623
|
this.fireStepStart("verify" /* Verify */);
|
|
1593
|
-
await sleep(
|
|
1624
|
+
await sleep(verifyDelay);
|
|
1594
1625
|
const signedResults = await cofheMocksZkVerifySign(
|
|
1595
1626
|
this.inputItems,
|
|
1596
1627
|
this.account,
|
|
@@ -1605,13 +1636,13 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1605
1636
|
utype: this.inputItems[index].utype,
|
|
1606
1637
|
signature
|
|
1607
1638
|
}));
|
|
1608
|
-
this.fireStepEnd("verify" /* Verify
|
|
1639
|
+
this.fireStepEnd("verify" /* Verify */, { isMocks: true, mockSleep: verifyDelay });
|
|
1609
1640
|
return encryptedInputs;
|
|
1610
1641
|
}
|
|
1611
1642
|
/**
|
|
1612
1643
|
* In the production context, perform a true encryption with the CoFHE coprocessor.
|
|
1613
1644
|
*/
|
|
1614
|
-
async
|
|
1645
|
+
async productionExecute() {
|
|
1615
1646
|
this.assertAccount();
|
|
1616
1647
|
this.assertChainId();
|
|
1617
1648
|
this.fireStepStart("initTfhe" /* InitTfhe */);
|
|
@@ -1674,15 +1705,15 @@ var EncryptInputsBuilder = class extends BaseBuilder {
|
|
|
1674
1705
|
* const encrypted = await encryptInputs([Encryptable.uint128(10n)])
|
|
1675
1706
|
* .setAccount('0x123...890') // optional
|
|
1676
1707
|
* .setChainId(11155111) // optional
|
|
1677
|
-
* .
|
|
1708
|
+
* .execute(); // execute
|
|
1678
1709
|
* ```
|
|
1679
1710
|
*
|
|
1680
1711
|
* @returns The encrypted inputs.
|
|
1681
1712
|
*/
|
|
1682
|
-
async
|
|
1713
|
+
async execute() {
|
|
1683
1714
|
if (this.chainId === chains.hardhat.id)
|
|
1684
|
-
return this.
|
|
1685
|
-
return this.
|
|
1715
|
+
return this.mocksExecute();
|
|
1716
|
+
return this.productionExecute();
|
|
1686
1717
|
}
|
|
1687
1718
|
};
|
|
1688
1719
|
|
|
@@ -1733,9 +1764,6 @@ function isBigIntOrNumber(value) {
|
|
|
1733
1764
|
}
|
|
1734
1765
|
}
|
|
1735
1766
|
}
|
|
1736
|
-
function is0xPrefixed(value) {
|
|
1737
|
-
return value.startsWith("0x");
|
|
1738
|
-
}
|
|
1739
1767
|
|
|
1740
1768
|
// permits/sealing.ts
|
|
1741
1769
|
var PRIVATE_KEY_LENGTH = 64;
|
|
@@ -1823,158 +1851,137 @@ var SerializedSealingPair = zod.z.object({
|
|
|
1823
1851
|
privateKey: zod.z.string(),
|
|
1824
1852
|
publicKey: zod.z.string()
|
|
1825
1853
|
});
|
|
1854
|
+
var addressSchema = zod.z.string().refine((val) => viem.isAddress(val), {
|
|
1855
|
+
error: "Invalid address"
|
|
1856
|
+
}).transform((val) => viem.getAddress(val));
|
|
1857
|
+
var addressNotZeroSchema = addressSchema.refine((val) => val !== viem.zeroAddress, {
|
|
1858
|
+
error: "Must not be zeroAddress"
|
|
1859
|
+
});
|
|
1860
|
+
var bytesSchema = zod.z.custom(
|
|
1861
|
+
(val) => {
|
|
1862
|
+
return typeof val === "string" && viem.isHex(val);
|
|
1863
|
+
},
|
|
1864
|
+
{
|
|
1865
|
+
message: "Invalid hex value"
|
|
1866
|
+
}
|
|
1867
|
+
);
|
|
1868
|
+
var bytesNotEmptySchema = bytesSchema.refine((val) => val !== "0x", {
|
|
1869
|
+
error: "Must not be empty"
|
|
1870
|
+
});
|
|
1826
1871
|
var DEFAULT_EXPIRATION_FN = () => Math.round(Date.now() / 1e3) + 7 * 24 * 60 * 60;
|
|
1827
1872
|
var zPermitWithDefaults = zod.z.object({
|
|
1828
1873
|
name: zod.z.string().optional().default("Unnamed Permit"),
|
|
1829
1874
|
type: zod.z.enum(["self", "sharing", "recipient"]),
|
|
1830
|
-
issuer:
|
|
1831
|
-
|
|
1832
|
-
|
|
1833
|
-
|
|
1834
|
-
|
|
1835
|
-
|
|
1836
|
-
|
|
1837
|
-
message: "Permit recipient :: invalid address"
|
|
1838
|
-
}),
|
|
1839
|
-
validatorId: zod.z.number().optional().default(0),
|
|
1840
|
-
validatorContract: zod.z.string().optional().default(viem.zeroAddress).refine((val) => viem.isAddress(val), {
|
|
1841
|
-
message: "Permit validatorContract :: invalid address"
|
|
1842
|
-
}),
|
|
1843
|
-
issuerSignature: zod.z.string().optional().default("0x"),
|
|
1844
|
-
recipientSignature: zod.z.string().optional().default("0x")
|
|
1875
|
+
issuer: addressNotZeroSchema,
|
|
1876
|
+
expiration: zod.z.int().optional().default(DEFAULT_EXPIRATION_FN),
|
|
1877
|
+
recipient: addressSchema.optional().default(viem.zeroAddress),
|
|
1878
|
+
validatorId: zod.z.int().optional().default(0),
|
|
1879
|
+
validatorContract: addressSchema.optional().default(viem.zeroAddress),
|
|
1880
|
+
issuerSignature: bytesSchema.optional().default("0x"),
|
|
1881
|
+
recipientSignature: bytesSchema.optional().default("0x")
|
|
1845
1882
|
});
|
|
1846
1883
|
var zPermitWithSealingPair = zPermitWithDefaults.extend({
|
|
1847
1884
|
sealingPair: SerializedSealingPair.optional()
|
|
1848
1885
|
});
|
|
1849
|
-
var
|
|
1886
|
+
var ExternalValidatorRefinement = [
|
|
1850
1887
|
(data) => data.validatorId !== 0 && data.validatorContract !== viem.zeroAddress || data.validatorId === 0 && data.validatorContract === viem.zeroAddress,
|
|
1851
1888
|
{
|
|
1852
|
-
|
|
1889
|
+
error: "Permit external validator :: validatorId and validatorContract must either both be set or both be unset.",
|
|
1853
1890
|
path: ["validatorId", "validatorContract"]
|
|
1854
1891
|
}
|
|
1855
1892
|
];
|
|
1893
|
+
var RecipientRefinement = [
|
|
1894
|
+
(data) => data.issuer !== data.recipient,
|
|
1895
|
+
{
|
|
1896
|
+
error: "Sharing permit :: issuer and recipient must not be the same",
|
|
1897
|
+
path: ["issuer", "recipient"]
|
|
1898
|
+
}
|
|
1899
|
+
];
|
|
1856
1900
|
var SelfPermitOptionsValidator = zod.z.object({
|
|
1857
1901
|
type: zod.z.literal("self").optional().default("self"),
|
|
1858
|
-
issuer:
|
|
1859
|
-
message: "Self permit issuer :: invalid address"
|
|
1860
|
-
}).refine((val) => is0xPrefixed(val), {
|
|
1861
|
-
message: "Self permit issuer :: must be 0x prefixed"
|
|
1862
|
-
}).refine((val) => val !== viem.zeroAddress, {
|
|
1863
|
-
message: "Self permit issuer :: must not be zeroAddress"
|
|
1864
|
-
}),
|
|
1902
|
+
issuer: addressNotZeroSchema,
|
|
1865
1903
|
name: zod.z.string().optional().default("Unnamed Permit"),
|
|
1866
|
-
expiration: zod.z.
|
|
1867
|
-
recipient:
|
|
1868
|
-
|
|
1869
|
-
|
|
1870
|
-
|
|
1871
|
-
|
|
1872
|
-
|
|
1873
|
-
}),
|
|
1874
|
-
validatorId: zod.z.number().optional().default(0),
|
|
1875
|
-
validatorContract: zod.z.string().optional().default(viem.zeroAddress).refine((val) => viem.isAddress(val), {
|
|
1876
|
-
message: "Self permit validatorContract :: invalid address"
|
|
1877
|
-
}),
|
|
1878
|
-
issuerSignature: zod.z.string().optional().default("0x").refine((val) => is0xPrefixed(val), {
|
|
1879
|
-
message: "Self permit issuerSignature :: must be 0x prefixed"
|
|
1880
|
-
}),
|
|
1881
|
-
recipientSignature: zod.z.string().optional().default("0x").refine((val) => is0xPrefixed(val), {
|
|
1882
|
-
message: "Self permit recipientSignature :: must be 0x prefixed"
|
|
1883
|
-
})
|
|
1884
|
-
}).refine(...ValidatorContractRefinement);
|
|
1904
|
+
expiration: zod.z.int().optional().default(DEFAULT_EXPIRATION_FN),
|
|
1905
|
+
recipient: addressSchema.optional().default(viem.zeroAddress),
|
|
1906
|
+
validatorId: zod.z.int().optional().default(0),
|
|
1907
|
+
validatorContract: addressSchema.optional().default(viem.zeroAddress),
|
|
1908
|
+
issuerSignature: bytesSchema.optional().default("0x"),
|
|
1909
|
+
recipientSignature: bytesSchema.optional().default("0x")
|
|
1910
|
+
}).refine(...ExternalValidatorRefinement);
|
|
1885
1911
|
var SelfPermitValidator = zPermitWithSealingPair.refine((data) => data.type === "self", {
|
|
1886
|
-
|
|
1912
|
+
error: "Type must be 'self'"
|
|
1887
1913
|
}).refine((data) => data.recipient === viem.zeroAddress, {
|
|
1888
|
-
|
|
1914
|
+
error: "Recipient must be zeroAddress"
|
|
1889
1915
|
}).refine((data) => data.issuerSignature !== "0x", {
|
|
1890
|
-
|
|
1916
|
+
error: "IssuerSignature must be populated"
|
|
1891
1917
|
}).refine((data) => data.recipientSignature === "0x", {
|
|
1892
|
-
|
|
1893
|
-
}).refine(...
|
|
1918
|
+
error: "RecipientSignature must be empty"
|
|
1919
|
+
}).refine(...ExternalValidatorRefinement);
|
|
1894
1920
|
var SharingPermitOptionsValidator = zod.z.object({
|
|
1895
1921
|
type: zod.z.literal("sharing").optional().default("sharing"),
|
|
1896
|
-
issuer:
|
|
1897
|
-
|
|
1898
|
-
}).refine((val) => is0xPrefixed(val), {
|
|
1899
|
-
message: "Sharing permit issuer :: must be 0x prefixed"
|
|
1900
|
-
}).refine((val) => val !== viem.zeroAddress, {
|
|
1901
|
-
message: "Sharing permit issuer :: must not be zeroAddress"
|
|
1902
|
-
}),
|
|
1903
|
-
recipient: zod.z.string().refine((val) => viem.isAddress(val), {
|
|
1904
|
-
message: "Sharing permit recipient :: invalid address"
|
|
1905
|
-
}).refine((val) => is0xPrefixed(val), {
|
|
1906
|
-
message: "Sharing permit recipient :: must be 0x prefixed"
|
|
1907
|
-
}).refine((val) => val !== viem.zeroAddress, {
|
|
1908
|
-
message: "Sharing permit recipient :: must not be zeroAddress"
|
|
1909
|
-
}),
|
|
1922
|
+
issuer: addressNotZeroSchema,
|
|
1923
|
+
recipient: addressNotZeroSchema,
|
|
1910
1924
|
name: zod.z.string().optional().default("Unnamed Permit"),
|
|
1911
|
-
expiration: zod.z.
|
|
1912
|
-
validatorId: zod.z.
|
|
1913
|
-
validatorContract:
|
|
1914
|
-
|
|
1915
|
-
|
|
1916
|
-
|
|
1917
|
-
message: "Sharing permit issuerSignature :: must be 0x prefixed"
|
|
1918
|
-
}),
|
|
1919
|
-
recipientSignature: zod.z.string().optional().default("0x").refine((val) => is0xPrefixed(val), {
|
|
1920
|
-
message: "Sharing permit recipientSignature :: must be 0x prefixed"
|
|
1921
|
-
})
|
|
1922
|
-
}).refine(...ValidatorContractRefinement);
|
|
1925
|
+
expiration: zod.z.int().optional().default(DEFAULT_EXPIRATION_FN),
|
|
1926
|
+
validatorId: zod.z.int().optional().default(0),
|
|
1927
|
+
validatorContract: addressSchema.optional().default(viem.zeroAddress),
|
|
1928
|
+
issuerSignature: bytesSchema.optional().default("0x"),
|
|
1929
|
+
recipientSignature: bytesSchema.optional().default("0x")
|
|
1930
|
+
}).refine(...RecipientRefinement).refine(...ExternalValidatorRefinement);
|
|
1923
1931
|
var SharingPermitValidator = zPermitWithSealingPair.refine((data) => data.type === "sharing", {
|
|
1924
|
-
|
|
1932
|
+
error: "Type must be 'sharing'"
|
|
1925
1933
|
}).refine((data) => data.recipient !== viem.zeroAddress, {
|
|
1926
|
-
|
|
1934
|
+
error: "Recipient must not be zeroAddress"
|
|
1927
1935
|
}).refine((data) => data.issuerSignature !== "0x", {
|
|
1928
|
-
|
|
1936
|
+
error: "IssuerSignature must be populated"
|
|
1929
1937
|
}).refine((data) => data.recipientSignature === "0x", {
|
|
1930
|
-
|
|
1931
|
-
}).refine(...
|
|
1938
|
+
error: "RecipientSignature must be empty"
|
|
1939
|
+
}).refine(...ExternalValidatorRefinement);
|
|
1932
1940
|
var ImportPermitOptionsValidator = zod.z.object({
|
|
1933
1941
|
type: zod.z.literal("recipient").optional().default("recipient"),
|
|
1934
|
-
issuer:
|
|
1935
|
-
|
|
1936
|
-
}).refine((val) => is0xPrefixed(val), {
|
|
1937
|
-
message: "Import permit issuer :: must be 0x prefixed"
|
|
1938
|
-
}).refine((val) => val !== viem.zeroAddress, {
|
|
1939
|
-
message: "Import permit issuer :: must not be zeroAddress"
|
|
1940
|
-
}),
|
|
1941
|
-
recipient: zod.z.string().refine((val) => viem.isAddress(val), {
|
|
1942
|
-
message: "Import permit recipient :: invalid address"
|
|
1943
|
-
}).refine((val) => is0xPrefixed(val), {
|
|
1944
|
-
message: "Import permit recipient :: must be 0x prefixed"
|
|
1945
|
-
}).refine((val) => val !== viem.zeroAddress, {
|
|
1946
|
-
message: "Import permit recipient :: must not be zeroAddress"
|
|
1947
|
-
}),
|
|
1948
|
-
issuerSignature: zod.z.string().refine((val) => is0xPrefixed(val), {
|
|
1949
|
-
message: "Import permit issuerSignature :: must be 0x prefixed"
|
|
1950
|
-
}).refine((val) => val !== "0x", {
|
|
1951
|
-
message: "Import permit :: issuerSignature must be provided"
|
|
1952
|
-
}),
|
|
1942
|
+
issuer: addressNotZeroSchema,
|
|
1943
|
+
recipient: addressNotZeroSchema,
|
|
1953
1944
|
name: zod.z.string().optional().default("Unnamed Permit"),
|
|
1954
|
-
expiration: zod.z.
|
|
1955
|
-
validatorId: zod.z.
|
|
1956
|
-
validatorContract:
|
|
1957
|
-
|
|
1958
|
-
|
|
1959
|
-
|
|
1960
|
-
message: "Import permit recipientSignature :: must be 0x prefixed"
|
|
1961
|
-
})
|
|
1962
|
-
}).refine(...ValidatorContractRefinement);
|
|
1945
|
+
expiration: zod.z.int(),
|
|
1946
|
+
validatorId: zod.z.int().optional().default(0),
|
|
1947
|
+
validatorContract: addressSchema.optional().default(viem.zeroAddress),
|
|
1948
|
+
issuerSignature: bytesNotEmptySchema,
|
|
1949
|
+
recipientSignature: bytesSchema.optional().default("0x")
|
|
1950
|
+
}).refine(...ExternalValidatorRefinement);
|
|
1963
1951
|
var ImportPermitValidator = zPermitWithSealingPair.refine((data) => data.type === "recipient", {
|
|
1964
|
-
|
|
1952
|
+
error: "Type must be 'recipient'"
|
|
1965
1953
|
}).refine((data) => data.recipient !== viem.zeroAddress, {
|
|
1966
|
-
|
|
1954
|
+
error: "Recipient must not be zeroAddress"
|
|
1967
1955
|
}).refine((data) => data.issuerSignature !== "0x", {
|
|
1968
|
-
|
|
1956
|
+
error: "IssuerSignature must be populated"
|
|
1969
1957
|
}).refine((data) => data.recipientSignature !== "0x", {
|
|
1970
|
-
|
|
1971
|
-
}).refine(...
|
|
1972
|
-
var
|
|
1973
|
-
|
|
1974
|
-
|
|
1975
|
-
|
|
1976
|
-
|
|
1977
|
-
|
|
1958
|
+
error: "RecipientSignature must be populated"
|
|
1959
|
+
}).refine(...ExternalValidatorRefinement);
|
|
1960
|
+
var safeParseAndThrowFormatted = (schema, data, message) => {
|
|
1961
|
+
const result = schema.safeParse(data);
|
|
1962
|
+
if (!result.success) {
|
|
1963
|
+
throw new Error(`${message}: ${zod.z.prettifyError(result.error)}`, { cause: result.error });
|
|
1964
|
+
}
|
|
1965
|
+
return result.data;
|
|
1966
|
+
};
|
|
1967
|
+
var validateSelfPermitOptions = (options) => {
|
|
1968
|
+
return safeParseAndThrowFormatted(SelfPermitOptionsValidator, options, "Invalid self permit options");
|
|
1969
|
+
};
|
|
1970
|
+
var validateSharingPermitOptions = (options) => {
|
|
1971
|
+
return safeParseAndThrowFormatted(SharingPermitOptionsValidator, options, "Invalid sharing permit options");
|
|
1972
|
+
};
|
|
1973
|
+
var validateImportPermitOptions = (options) => {
|
|
1974
|
+
return safeParseAndThrowFormatted(ImportPermitOptionsValidator, options, "Invalid import permit options");
|
|
1975
|
+
};
|
|
1976
|
+
var validateSelfPermit = (permit) => {
|
|
1977
|
+
return safeParseAndThrowFormatted(SelfPermitValidator, permit, "Invalid self permit");
|
|
1978
|
+
};
|
|
1979
|
+
var validateSharingPermit = (permit) => {
|
|
1980
|
+
return safeParseAndThrowFormatted(SharingPermitValidator, permit, "Invalid sharing permit");
|
|
1981
|
+
};
|
|
1982
|
+
var validateImportPermit = (permit) => {
|
|
1983
|
+
return safeParseAndThrowFormatted(ImportPermitValidator, permit, "Invalid import permit");
|
|
1984
|
+
};
|
|
1978
1985
|
var ValidationUtils = {
|
|
1979
1986
|
/**
|
|
1980
1987
|
* Check if permit is expired
|
|
@@ -2068,6 +2075,179 @@ var SignatureUtils = {
|
|
|
2068
2075
|
throw new Error(`Unknown permit type: ${permitType}`);
|
|
2069
2076
|
}
|
|
2070
2077
|
};
|
|
2078
|
+
var getAclAddress = async (publicClient) => {
|
|
2079
|
+
const ACL_IFACE = "function acl() view returns (address)";
|
|
2080
|
+
const aclAbi = viem.parseAbi([ACL_IFACE]);
|
|
2081
|
+
return await publicClient.readContract({
|
|
2082
|
+
address: TASK_MANAGER_ADDRESS,
|
|
2083
|
+
abi: aclAbi,
|
|
2084
|
+
functionName: "acl"
|
|
2085
|
+
});
|
|
2086
|
+
};
|
|
2087
|
+
var getAclEIP712Domain = async (publicClient) => {
|
|
2088
|
+
const aclAddress = await getAclAddress(publicClient);
|
|
2089
|
+
const EIP712_DOMAIN_IFACE = "function eip712Domain() public view returns (bytes1 fields, string name, string version, uint256 chainId, address verifyingContract, bytes32 salt, uint256[] extensions)";
|
|
2090
|
+
const domainAbi = viem.parseAbi([EIP712_DOMAIN_IFACE]);
|
|
2091
|
+
const domain = await publicClient.readContract({
|
|
2092
|
+
address: aclAddress,
|
|
2093
|
+
abi: domainAbi,
|
|
2094
|
+
functionName: "eip712Domain"
|
|
2095
|
+
});
|
|
2096
|
+
const [_fields, name, version, chainId, verifyingContract, _salt, _extensions] = domain;
|
|
2097
|
+
return {
|
|
2098
|
+
name,
|
|
2099
|
+
version,
|
|
2100
|
+
chainId: Number(chainId),
|
|
2101
|
+
verifyingContract
|
|
2102
|
+
};
|
|
2103
|
+
};
|
|
2104
|
+
var checkPermitValidityOnChain = async (permission, publicClient) => {
|
|
2105
|
+
const aclAddress = await getAclAddress(publicClient);
|
|
2106
|
+
try {
|
|
2107
|
+
await publicClient.simulateContract({
|
|
2108
|
+
address: aclAddress,
|
|
2109
|
+
abi: checkPermitValidityAbi,
|
|
2110
|
+
functionName: "checkPermitValidity",
|
|
2111
|
+
args: [
|
|
2112
|
+
{
|
|
2113
|
+
issuer: permission.issuer,
|
|
2114
|
+
expiration: BigInt(permission.expiration),
|
|
2115
|
+
recipient: permission.recipient,
|
|
2116
|
+
validatorId: BigInt(permission.validatorId),
|
|
2117
|
+
validatorContract: permission.validatorContract,
|
|
2118
|
+
sealingKey: permission.sealingKey,
|
|
2119
|
+
issuerSignature: permission.issuerSignature,
|
|
2120
|
+
recipientSignature: permission.recipientSignature
|
|
2121
|
+
}
|
|
2122
|
+
]
|
|
2123
|
+
});
|
|
2124
|
+
return true;
|
|
2125
|
+
} catch (err) {
|
|
2126
|
+
if (err instanceof viem.BaseError) {
|
|
2127
|
+
const revertError = err.walk((err2) => err2 instanceof viem.ContractFunctionRevertedError);
|
|
2128
|
+
if (revertError instanceof viem.ContractFunctionRevertedError) {
|
|
2129
|
+
const errorName = revertError.data?.errorName ?? "";
|
|
2130
|
+
throw new Error(errorName);
|
|
2131
|
+
}
|
|
2132
|
+
}
|
|
2133
|
+
const customErrorName = extractCustomErrorFromDetails(err, checkPermitValidityAbi);
|
|
2134
|
+
if (customErrorName) {
|
|
2135
|
+
throw new Error(customErrorName);
|
|
2136
|
+
}
|
|
2137
|
+
const hhDetailsData = extractReturnData(err);
|
|
2138
|
+
if (hhDetailsData != null) {
|
|
2139
|
+
const decoded = viem.decodeErrorResult({
|
|
2140
|
+
abi: checkPermitValidityAbi,
|
|
2141
|
+
data: hhDetailsData
|
|
2142
|
+
});
|
|
2143
|
+
throw new Error(decoded.errorName);
|
|
2144
|
+
}
|
|
2145
|
+
throw err;
|
|
2146
|
+
}
|
|
2147
|
+
};
|
|
2148
|
+
function extractCustomErrorFromDetails(err, abi) {
|
|
2149
|
+
const anyErr = err;
|
|
2150
|
+
const details = anyErr?.details ?? anyErr?.cause?.details;
|
|
2151
|
+
if (typeof details === "string") {
|
|
2152
|
+
const customErrorMatch = details.match(/reverted with custom error '(\w+)\(\)'/);
|
|
2153
|
+
if (customErrorMatch) {
|
|
2154
|
+
const errorName = customErrorMatch[1];
|
|
2155
|
+
const errorExists = abi.some((item) => item.type === "error" && item.name === errorName);
|
|
2156
|
+
if (errorExists) {
|
|
2157
|
+
return errorName;
|
|
2158
|
+
}
|
|
2159
|
+
}
|
|
2160
|
+
}
|
|
2161
|
+
return void 0;
|
|
2162
|
+
}
|
|
2163
|
+
function extractReturnData(err) {
|
|
2164
|
+
const anyErr = err;
|
|
2165
|
+
const s = anyErr?.details ?? anyErr?.cause?.details ?? anyErr?.shortMessage ?? anyErr?.message ?? String(err);
|
|
2166
|
+
return s.match(/return data:\s*(0x[a-fA-F0-9]+)/)?.[1];
|
|
2167
|
+
}
|
|
2168
|
+
var checkPermitValidityAbi = [
|
|
2169
|
+
{
|
|
2170
|
+
type: "function",
|
|
2171
|
+
name: "checkPermitValidity",
|
|
2172
|
+
inputs: [
|
|
2173
|
+
{
|
|
2174
|
+
name: "permission",
|
|
2175
|
+
type: "tuple",
|
|
2176
|
+
internalType: "struct Permission",
|
|
2177
|
+
components: [
|
|
2178
|
+
{
|
|
2179
|
+
name: "issuer",
|
|
2180
|
+
type: "address",
|
|
2181
|
+
internalType: "address"
|
|
2182
|
+
},
|
|
2183
|
+
{
|
|
2184
|
+
name: "expiration",
|
|
2185
|
+
type: "uint64",
|
|
2186
|
+
internalType: "uint64"
|
|
2187
|
+
},
|
|
2188
|
+
{
|
|
2189
|
+
name: "recipient",
|
|
2190
|
+
type: "address",
|
|
2191
|
+
internalType: "address"
|
|
2192
|
+
},
|
|
2193
|
+
{
|
|
2194
|
+
name: "validatorId",
|
|
2195
|
+
type: "uint256",
|
|
2196
|
+
internalType: "uint256"
|
|
2197
|
+
},
|
|
2198
|
+
{
|
|
2199
|
+
name: "validatorContract",
|
|
2200
|
+
type: "address",
|
|
2201
|
+
internalType: "address"
|
|
2202
|
+
},
|
|
2203
|
+
{
|
|
2204
|
+
name: "sealingKey",
|
|
2205
|
+
type: "bytes32",
|
|
2206
|
+
internalType: "bytes32"
|
|
2207
|
+
},
|
|
2208
|
+
{
|
|
2209
|
+
name: "issuerSignature",
|
|
2210
|
+
type: "bytes",
|
|
2211
|
+
internalType: "bytes"
|
|
2212
|
+
},
|
|
2213
|
+
{
|
|
2214
|
+
name: "recipientSignature",
|
|
2215
|
+
type: "bytes",
|
|
2216
|
+
internalType: "bytes"
|
|
2217
|
+
}
|
|
2218
|
+
]
|
|
2219
|
+
}
|
|
2220
|
+
],
|
|
2221
|
+
outputs: [
|
|
2222
|
+
{
|
|
2223
|
+
name: "",
|
|
2224
|
+
type: "bool",
|
|
2225
|
+
internalType: "bool"
|
|
2226
|
+
}
|
|
2227
|
+
],
|
|
2228
|
+
stateMutability: "view"
|
|
2229
|
+
},
|
|
2230
|
+
{
|
|
2231
|
+
type: "error",
|
|
2232
|
+
name: "PermissionInvalid_Disabled",
|
|
2233
|
+
inputs: []
|
|
2234
|
+
},
|
|
2235
|
+
{
|
|
2236
|
+
type: "error",
|
|
2237
|
+
name: "PermissionInvalid_Expired",
|
|
2238
|
+
inputs: []
|
|
2239
|
+
},
|
|
2240
|
+
{
|
|
2241
|
+
type: "error",
|
|
2242
|
+
name: "PermissionInvalid_IssuerSignature",
|
|
2243
|
+
inputs: []
|
|
2244
|
+
},
|
|
2245
|
+
{
|
|
2246
|
+
type: "error",
|
|
2247
|
+
name: "PermissionInvalid_RecipientSignature",
|
|
2248
|
+
inputs: []
|
|
2249
|
+
}
|
|
2250
|
+
];
|
|
2071
2251
|
|
|
2072
2252
|
// permits/permit.ts
|
|
2073
2253
|
var PermitUtils = {
|
|
@@ -2076,14 +2256,10 @@ var PermitUtils = {
|
|
|
2076
2256
|
*/
|
|
2077
2257
|
createSelf: (options) => {
|
|
2078
2258
|
const validation = validateSelfPermitOptions(options);
|
|
2079
|
-
if (!validation.success) {
|
|
2080
|
-
throw new Error(
|
|
2081
|
-
"PermitUtils :: createSelf :: Parsing SelfPermitOptions failed " + JSON.stringify(validation.error, null, 2)
|
|
2082
|
-
);
|
|
2083
|
-
}
|
|
2084
2259
|
const sealingPair = GenerateSealingKey();
|
|
2085
2260
|
const permit = {
|
|
2086
|
-
|
|
2261
|
+
hash: PermitUtils.getHash(validation),
|
|
2262
|
+
...validation,
|
|
2087
2263
|
sealingPair,
|
|
2088
2264
|
_signedDomain: void 0
|
|
2089
2265
|
};
|
|
@@ -2094,14 +2270,10 @@ var PermitUtils = {
|
|
|
2094
2270
|
*/
|
|
2095
2271
|
createSharing: (options) => {
|
|
2096
2272
|
const validation = validateSharingPermitOptions(options);
|
|
2097
|
-
if (!validation.success) {
|
|
2098
|
-
throw new Error(
|
|
2099
|
-
"PermitUtils :: createSharing :: Parsing SharingPermitOptions failed " + JSON.stringify(validation.error, null, 2)
|
|
2100
|
-
);
|
|
2101
|
-
}
|
|
2102
2273
|
const sealingPair = GenerateSealingKey();
|
|
2103
2274
|
const permit = {
|
|
2104
|
-
|
|
2275
|
+
hash: PermitUtils.getHash(validation),
|
|
2276
|
+
...validation,
|
|
2105
2277
|
sealingPair,
|
|
2106
2278
|
_signedDomain: void 0
|
|
2107
2279
|
};
|
|
@@ -2116,27 +2288,21 @@ var PermitUtils = {
|
|
|
2116
2288
|
try {
|
|
2117
2289
|
parsedOptions = JSON.parse(options);
|
|
2118
2290
|
} catch (error) {
|
|
2119
|
-
throw new Error(`
|
|
2291
|
+
throw new Error(`Failed to parse JSON string: ${error}`);
|
|
2120
2292
|
}
|
|
2121
2293
|
} else if (typeof options === "object" && options !== null) {
|
|
2122
2294
|
parsedOptions = options;
|
|
2123
2295
|
} else {
|
|
2124
|
-
throw new Error(
|
|
2125
|
-
"PermitUtils :: importShared :: Invalid input type, expected ImportSharedPermitOptions, object, or string"
|
|
2126
|
-
);
|
|
2296
|
+
throw new Error("Invalid input type, expected ImportSharedPermitOptions, object, or string");
|
|
2127
2297
|
}
|
|
2128
2298
|
if (parsedOptions.type != null && parsedOptions.type !== "sharing") {
|
|
2129
|
-
throw new Error(`
|
|
2299
|
+
throw new Error(`Invalid permit type <${parsedOptions.type}>, must be "sharing"`);
|
|
2130
2300
|
}
|
|
2131
2301
|
const validation = validateImportPermitOptions({ ...parsedOptions, type: "recipient" });
|
|
2132
|
-
if (!validation.success) {
|
|
2133
|
-
throw new Error(
|
|
2134
|
-
"PermitUtils :: importShared :: Parsing ImportPermitOptions failed " + JSON.stringify(validation.error, null, 2)
|
|
2135
|
-
);
|
|
2136
|
-
}
|
|
2137
2302
|
const sealingPair = GenerateSealingKey();
|
|
2138
2303
|
const permit = {
|
|
2139
|
-
|
|
2304
|
+
hash: PermitUtils.getHash(validation),
|
|
2305
|
+
...validation,
|
|
2140
2306
|
sealingPair,
|
|
2141
2307
|
_signedDomain: void 0
|
|
2142
2308
|
};
|
|
@@ -2148,11 +2314,11 @@ var PermitUtils = {
|
|
|
2148
2314
|
sign: async (permit, publicClient, walletClient) => {
|
|
2149
2315
|
if (walletClient == null || walletClient.account == null) {
|
|
2150
2316
|
throw new Error(
|
|
2151
|
-
"
|
|
2317
|
+
"Missing walletClient, you must pass in a `walletClient` for the connected user to create a permit signature"
|
|
2152
2318
|
);
|
|
2153
2319
|
}
|
|
2154
2320
|
const primaryType = SignatureUtils.getPrimaryType(permit.type);
|
|
2155
|
-
const domain = await
|
|
2321
|
+
const domain = await getAclEIP712Domain(publicClient);
|
|
2156
2322
|
const { types, message } = SignatureUtils.getSignatureParams(PermitUtils.getPermission(permit, true), primaryType);
|
|
2157
2323
|
const signature = await walletClient.signTypedData({
|
|
2158
2324
|
domain,
|
|
@@ -2212,6 +2378,7 @@ var PermitUtils = {
|
|
|
2212
2378
|
*/
|
|
2213
2379
|
serialize: (permit) => {
|
|
2214
2380
|
return {
|
|
2381
|
+
hash: permit.hash,
|
|
2215
2382
|
name: permit.name,
|
|
2216
2383
|
type: permit.type,
|
|
2217
2384
|
issuer: permit.issuer,
|
|
@@ -2236,7 +2403,7 @@ var PermitUtils = {
|
|
|
2236
2403
|
} else if (permit.type === "recipient") {
|
|
2237
2404
|
return validateImportPermit(permit);
|
|
2238
2405
|
} else {
|
|
2239
|
-
throw new Error("
|
|
2406
|
+
throw new Error("Invalid permit type");
|
|
2240
2407
|
}
|
|
2241
2408
|
},
|
|
2242
2409
|
/**
|
|
@@ -2244,12 +2411,7 @@ var PermitUtils = {
|
|
|
2244
2411
|
*/
|
|
2245
2412
|
getPermission: (permit, skipValidation = false) => {
|
|
2246
2413
|
if (!skipValidation) {
|
|
2247
|
-
|
|
2248
|
-
if (!validationResult.success) {
|
|
2249
|
-
throw new Error(
|
|
2250
|
-
`PermitUtils :: getPermission :: permit validation failed - ${JSON.stringify(validationResult.error, null, 2)} ${JSON.stringify(permit, null, 2)}`
|
|
2251
|
-
);
|
|
2252
|
-
}
|
|
2414
|
+
PermitUtils.validate(permit);
|
|
2253
2415
|
}
|
|
2254
2416
|
return {
|
|
2255
2417
|
issuer: permit.issuer,
|
|
@@ -2330,28 +2492,7 @@ var PermitUtils = {
|
|
|
2330
2492
|
* Fetch EIP712 domain from the blockchain
|
|
2331
2493
|
*/
|
|
2332
2494
|
fetchEIP712Domain: async (publicClient) => {
|
|
2333
|
-
|
|
2334
|
-
const ACL_IFACE = "function acl() view returns (address)";
|
|
2335
|
-
const EIP712_DOMAIN_IFACE = "function eip712Domain() public view returns (bytes1 fields, string name, string version, uint256 chainId, address verifyingContract, bytes32 salt, uint256[] extensions)";
|
|
2336
|
-
const aclAbi = viem.parseAbi([ACL_IFACE]);
|
|
2337
|
-
const aclAddress = await publicClient.readContract({
|
|
2338
|
-
address: TASK_MANAGER_ADDRESS,
|
|
2339
|
-
abi: aclAbi,
|
|
2340
|
-
functionName: "acl"
|
|
2341
|
-
});
|
|
2342
|
-
const domainAbi = viem.parseAbi([EIP712_DOMAIN_IFACE]);
|
|
2343
|
-
const domain = await publicClient.readContract({
|
|
2344
|
-
address: aclAddress,
|
|
2345
|
-
abi: domainAbi,
|
|
2346
|
-
functionName: "eip712Domain"
|
|
2347
|
-
});
|
|
2348
|
-
const [_fields, name, version, chainId, verifyingContract, _salt, _extensions] = domain;
|
|
2349
|
-
return {
|
|
2350
|
-
name,
|
|
2351
|
-
version,
|
|
2352
|
-
chainId: Number(chainId),
|
|
2353
|
-
verifyingContract
|
|
2354
|
-
};
|
|
2495
|
+
return getAclEIP712Domain(publicClient);
|
|
2355
2496
|
},
|
|
2356
2497
|
/**
|
|
2357
2498
|
* Check if permit's signed domain matches the provided domain
|
|
@@ -2365,8 +2506,15 @@ var PermitUtils = {
|
|
|
2365
2506
|
checkSignedDomainValid: async (permit, publicClient) => {
|
|
2366
2507
|
if (permit._signedDomain == null)
|
|
2367
2508
|
return false;
|
|
2368
|
-
const domain = await
|
|
2509
|
+
const domain = await getAclEIP712Domain(publicClient);
|
|
2369
2510
|
return PermitUtils.matchesDomain(permit, domain);
|
|
2511
|
+
},
|
|
2512
|
+
/**
|
|
2513
|
+
* Check if permit passes the on-chain validation
|
|
2514
|
+
*/
|
|
2515
|
+
checkValidityOnChain: async (permit, publicClient) => {
|
|
2516
|
+
const permission = PermitUtils.getPermission(permit);
|
|
2517
|
+
return checkPermitValidityOnChain(permission, publicClient);
|
|
2370
2518
|
}
|
|
2371
2519
|
};
|
|
2372
2520
|
var PERMIT_STORE_DEFAULTS = {
|
|
@@ -2420,11 +2568,11 @@ var setPermit = (chainId, account, permit) => {
|
|
|
2420
2568
|
state.permits[chainId] = {};
|
|
2421
2569
|
if (state.permits[chainId][account] == null)
|
|
2422
2570
|
state.permits[chainId][account] = {};
|
|
2423
|
-
state.permits[chainId][account][
|
|
2571
|
+
state.permits[chainId][account][permit.hash] = PermitUtils.serialize(permit);
|
|
2424
2572
|
})
|
|
2425
2573
|
);
|
|
2426
2574
|
};
|
|
2427
|
-
var removePermit = (chainId, account, hash
|
|
2575
|
+
var removePermit = (chainId, account, hash) => {
|
|
2428
2576
|
clearStaleStore();
|
|
2429
2577
|
_permitStore.setState(
|
|
2430
2578
|
immer.produce((state) => {
|
|
@@ -2438,15 +2586,7 @@ var removePermit = (chainId, account, hash, force) => {
|
|
|
2438
2586
|
if (accountPermits[hash] == null)
|
|
2439
2587
|
return;
|
|
2440
2588
|
if (state.activePermitHash[chainId][account] === hash) {
|
|
2441
|
-
|
|
2442
|
-
if (otherPermitHash) {
|
|
2443
|
-
state.activePermitHash[chainId][account] = otherPermitHash;
|
|
2444
|
-
} else {
|
|
2445
|
-
if (!force) {
|
|
2446
|
-
throw new Error("Cannot remove the last permit without force flag");
|
|
2447
|
-
}
|
|
2448
|
-
state.activePermitHash[chainId][account] = void 0;
|
|
2449
|
-
}
|
|
2589
|
+
state.activePermitHash[chainId][account] = void 0;
|
|
2450
2590
|
}
|
|
2451
2591
|
accountPermits[hash] = void 0;
|
|
2452
2592
|
})
|
|
@@ -2497,7 +2637,7 @@ var storeActivePermit = async (permit, publicClient, walletClient) => {
|
|
|
2497
2637
|
const chainId = await publicClient.getChainId();
|
|
2498
2638
|
const account = walletClient.account.address;
|
|
2499
2639
|
permitStore.setPermit(chainId, account, permit);
|
|
2500
|
-
permitStore.setActivePermitHash(chainId, account,
|
|
2640
|
+
permitStore.setActivePermitHash(chainId, account, permit.hash);
|
|
2501
2641
|
};
|
|
2502
2642
|
var createPermitWithSign = async (options, publicClient, walletClient, permitMethod) => {
|
|
2503
2643
|
const permit = await permitMethod(options, publicClient, walletClient);
|
|
@@ -2555,7 +2695,7 @@ var getOrCreateSharingPermit = async (publicClient, walletClient, options, chain
|
|
|
2555
2695
|
}
|
|
2556
2696
|
return createSharing(options, publicClient, walletClient);
|
|
2557
2697
|
};
|
|
2558
|
-
var removePermit2 = async (chainId, account, hash
|
|
2698
|
+
var removePermit2 = async (chainId, account, hash) => permitStore.removePermit(chainId, account, hash);
|
|
2559
2699
|
var removeActivePermit = async (chainId, account) => permitStore.removeActivePermitHash(chainId, account);
|
|
2560
2700
|
var permits = {
|
|
2561
2701
|
getSnapshot: permitStore.store.getState,
|
|
@@ -2595,8 +2735,8 @@ var convertViaUtype = (utype, value) => {
|
|
|
2595
2735
|
}
|
|
2596
2736
|
};
|
|
2597
2737
|
|
|
2598
|
-
// core/decrypt/
|
|
2599
|
-
var
|
|
2738
|
+
// core/decrypt/MockThresholdNetworkAbi.ts
|
|
2739
|
+
var MockThresholdNetworkAbi = [
|
|
2600
2740
|
{
|
|
2601
2741
|
type: "function",
|
|
2602
2742
|
name: "acl",
|
|
@@ -2643,11 +2783,7 @@ var MockQueryDecrypterAbi = [
|
|
|
2643
2783
|
{ name: "expiration", type: "uint64", internalType: "uint64" },
|
|
2644
2784
|
{ name: "recipient", type: "address", internalType: "address" },
|
|
2645
2785
|
{ name: "validatorId", type: "uint256", internalType: "uint256" },
|
|
2646
|
-
{
|
|
2647
|
-
name: "validatorContract",
|
|
2648
|
-
type: "address",
|
|
2649
|
-
internalType: "address"
|
|
2650
|
-
},
|
|
2786
|
+
{ name: "validatorContract", type: "address", internalType: "address" },
|
|
2651
2787
|
{ name: "sealingKey", type: "bytes32", internalType: "bytes32" },
|
|
2652
2788
|
{ name: "issuerSignature", type: "bytes", internalType: "bytes" },
|
|
2653
2789
|
{ name: "recipientSignature", type: "bytes", internalType: "bytes" }
|
|
@@ -2676,11 +2812,7 @@ var MockQueryDecrypterAbi = [
|
|
|
2676
2812
|
{ name: "expiration", type: "uint64", internalType: "uint64" },
|
|
2677
2813
|
{ name: "recipient", type: "address", internalType: "address" },
|
|
2678
2814
|
{ name: "validatorId", type: "uint256", internalType: "uint256" },
|
|
2679
|
-
{
|
|
2680
|
-
name: "validatorContract",
|
|
2681
|
-
type: "address",
|
|
2682
|
-
internalType: "address"
|
|
2683
|
-
},
|
|
2815
|
+
{ name: "validatorContract", type: "address", internalType: "address" },
|
|
2684
2816
|
{ name: "sealingKey", type: "bytes32", internalType: "bytes32" },
|
|
2685
2817
|
{ name: "issuerSignature", type: "bytes", internalType: "bytes" },
|
|
2686
2818
|
{ name: "recipientSignature", type: "bytes", internalType: "bytes" }
|
|
@@ -2704,13 +2836,6 @@ var MockQueryDecrypterAbi = [
|
|
|
2704
2836
|
outputs: [{ name: "", type: "bytes32", internalType: "bytes32" }],
|
|
2705
2837
|
stateMutability: "pure"
|
|
2706
2838
|
},
|
|
2707
|
-
{
|
|
2708
|
-
type: "function",
|
|
2709
|
-
name: "taskManager",
|
|
2710
|
-
inputs: [],
|
|
2711
|
-
outputs: [{ name: "", type: "address", internalType: "contract TaskManager" }],
|
|
2712
|
-
stateMutability: "view"
|
|
2713
|
-
},
|
|
2714
2839
|
{
|
|
2715
2840
|
type: "function",
|
|
2716
2841
|
name: "unseal",
|
|
@@ -2721,16 +2846,80 @@ var MockQueryDecrypterAbi = [
|
|
|
2721
2846
|
outputs: [{ name: "", type: "uint256", internalType: "uint256" }],
|
|
2722
2847
|
stateMutability: "pure"
|
|
2723
2848
|
},
|
|
2724
|
-
{
|
|
2725
|
-
|
|
2726
|
-
|
|
2849
|
+
{
|
|
2850
|
+
type: "function",
|
|
2851
|
+
name: "mockAcl",
|
|
2852
|
+
inputs: [],
|
|
2853
|
+
outputs: [{ name: "", type: "address", internalType: "contract MockACL" }],
|
|
2854
|
+
stateMutability: "view"
|
|
2855
|
+
},
|
|
2856
|
+
{
|
|
2857
|
+
type: "function",
|
|
2858
|
+
name: "mockTaskManager",
|
|
2859
|
+
inputs: [],
|
|
2860
|
+
outputs: [{ name: "", type: "address", internalType: "contract MockTaskManager" }],
|
|
2861
|
+
stateMutability: "view"
|
|
2862
|
+
},
|
|
2863
|
+
{
|
|
2864
|
+
type: "function",
|
|
2865
|
+
name: "mockQueryDecrypt",
|
|
2866
|
+
inputs: [
|
|
2867
|
+
{ name: "ctHash", type: "uint256", internalType: "uint256" },
|
|
2868
|
+
{ name: "", type: "uint256", internalType: "uint256" },
|
|
2869
|
+
{ name: "issuer", type: "address", internalType: "address" }
|
|
2870
|
+
],
|
|
2871
|
+
outputs: [
|
|
2872
|
+
{ name: "allowed", type: "bool", internalType: "bool" },
|
|
2873
|
+
{ name: "error", type: "string", internalType: "string" },
|
|
2874
|
+
{ name: "", type: "uint256", internalType: "uint256" }
|
|
2875
|
+
],
|
|
2876
|
+
stateMutability: "view"
|
|
2877
|
+
},
|
|
2878
|
+
{
|
|
2879
|
+
type: "function",
|
|
2880
|
+
name: "decryptForTxWithPermit",
|
|
2881
|
+
inputs: [
|
|
2882
|
+
{ name: "ctHash", type: "uint256", internalType: "uint256" },
|
|
2883
|
+
{
|
|
2884
|
+
name: "permission",
|
|
2885
|
+
type: "tuple",
|
|
2886
|
+
internalType: "struct Permission",
|
|
2887
|
+
components: [
|
|
2888
|
+
{ name: "issuer", type: "address", internalType: "address" },
|
|
2889
|
+
{ name: "expiration", type: "uint64", internalType: "uint64" },
|
|
2890
|
+
{ name: "recipient", type: "address", internalType: "address" },
|
|
2891
|
+
{ name: "validatorId", type: "uint256", internalType: "uint256" },
|
|
2892
|
+
{ name: "validatorContract", type: "address", internalType: "address" },
|
|
2893
|
+
{ name: "sealingKey", type: "bytes32", internalType: "bytes32" },
|
|
2894
|
+
{ name: "issuerSignature", type: "bytes", internalType: "bytes" },
|
|
2895
|
+
{ name: "recipientSignature", type: "bytes", internalType: "bytes" }
|
|
2896
|
+
]
|
|
2897
|
+
}
|
|
2898
|
+
],
|
|
2899
|
+
outputs: [
|
|
2900
|
+
{ name: "allowed", type: "bool", internalType: "bool" },
|
|
2901
|
+
{ name: "error", type: "string", internalType: "string" },
|
|
2902
|
+
{ name: "decryptedValue", type: "uint256", internalType: "uint256" }
|
|
2903
|
+
],
|
|
2904
|
+
stateMutability: "view"
|
|
2905
|
+
},
|
|
2906
|
+
{
|
|
2907
|
+
type: "function",
|
|
2908
|
+
name: "decryptForTxWithoutPermit",
|
|
2909
|
+
inputs: [{ name: "ctHash", type: "uint256", internalType: "uint256" }],
|
|
2910
|
+
outputs: [
|
|
2911
|
+
{ name: "allowed", type: "bool", internalType: "bool" },
|
|
2912
|
+
{ name: "error", type: "string", internalType: "string" },
|
|
2913
|
+
{ name: "decryptedValue", type: "uint256", internalType: "uint256" }
|
|
2914
|
+
],
|
|
2915
|
+
stateMutability: "view"
|
|
2916
|
+
}
|
|
2727
2917
|
];
|
|
2728
2918
|
|
|
2729
|
-
// core/decrypt/
|
|
2730
|
-
|
|
2731
|
-
|
|
2732
|
-
|
|
2733
|
-
await sleep(mocksSealOutputDelay);
|
|
2919
|
+
// core/decrypt/cofheMocksDecryptForView.ts
|
|
2920
|
+
async function cofheMocksDecryptForView(ctHash, utype, permit, publicClient, mocksDecryptDelay) {
|
|
2921
|
+
if (mocksDecryptDelay > 0)
|
|
2922
|
+
await sleep(mocksDecryptDelay);
|
|
2734
2923
|
const permission = PermitUtils.getPermission(permit, true);
|
|
2735
2924
|
const permissionWithBigInts = {
|
|
2736
2925
|
...permission,
|
|
@@ -2738,19 +2927,19 @@ async function cofheMocksSealOutput(ctHash, utype, permit, publicClient, mocksSe
|
|
|
2738
2927
|
validatorId: BigInt(permission.validatorId)
|
|
2739
2928
|
};
|
|
2740
2929
|
const [allowed, error, result] = await publicClient.readContract({
|
|
2741
|
-
address:
|
|
2742
|
-
abi:
|
|
2930
|
+
address: MOCKS_THRESHOLD_NETWORK_ADDRESS,
|
|
2931
|
+
abi: MockThresholdNetworkAbi,
|
|
2743
2932
|
functionName: "querySealOutput",
|
|
2744
2933
|
args: [ctHash, BigInt(utype), permissionWithBigInts]
|
|
2745
2934
|
});
|
|
2746
2935
|
if (error != "") {
|
|
2747
|
-
throw new
|
|
2936
|
+
throw new CofheError({
|
|
2748
2937
|
code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
|
|
2749
2938
|
message: `mocks querySealOutput call failed: ${error}`
|
|
2750
2939
|
});
|
|
2751
2940
|
}
|
|
2752
2941
|
if (allowed == false) {
|
|
2753
|
-
throw new
|
|
2942
|
+
throw new CofheError({
|
|
2754
2943
|
code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
|
|
2755
2944
|
message: `mocks querySealOutput call failed: ACL Access Denied (NotAllowed)`
|
|
2756
2945
|
});
|
|
@@ -2769,7 +2958,7 @@ function numberArrayToUint8Array(arr) {
|
|
|
2769
2958
|
}
|
|
2770
2959
|
function convertSealedData(sealed) {
|
|
2771
2960
|
if (!sealed) {
|
|
2772
|
-
throw new
|
|
2961
|
+
throw new CofheError({
|
|
2773
2962
|
code: "SEAL_OUTPUT_RETURNED_NULL" /* SealOutputReturnedNull */,
|
|
2774
2963
|
message: "Sealed data is missing from completed response"
|
|
2775
2964
|
});
|
|
@@ -2796,7 +2985,7 @@ async function submitSealOutputRequest(thresholdNetworkUrl, ctHash, chainId, per
|
|
|
2796
2985
|
body: JSON.stringify(body)
|
|
2797
2986
|
});
|
|
2798
2987
|
} catch (e) {
|
|
2799
|
-
throw new
|
|
2988
|
+
throw new CofheError({
|
|
2800
2989
|
code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
|
|
2801
2990
|
message: `sealOutput request failed`,
|
|
2802
2991
|
hint: "Ensure the threshold network URL is valid and reachable.",
|
|
@@ -2815,7 +3004,7 @@ async function submitSealOutputRequest(thresholdNetworkUrl, ctHash, chainId, per
|
|
|
2815
3004
|
} catch {
|
|
2816
3005
|
errorMessage = response.statusText || errorMessage;
|
|
2817
3006
|
}
|
|
2818
|
-
throw new
|
|
3007
|
+
throw new CofheError({
|
|
2819
3008
|
code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
|
|
2820
3009
|
message: `sealOutput request failed: ${errorMessage}`,
|
|
2821
3010
|
hint: "Check the threshold network URL and request parameters.",
|
|
@@ -2831,7 +3020,7 @@ async function submitSealOutputRequest(thresholdNetworkUrl, ctHash, chainId, per
|
|
|
2831
3020
|
try {
|
|
2832
3021
|
submitResponse = await response.json();
|
|
2833
3022
|
} catch (e) {
|
|
2834
|
-
throw new
|
|
3023
|
+
throw new CofheError({
|
|
2835
3024
|
code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
|
|
2836
3025
|
message: `Failed to parse sealOutput submit response`,
|
|
2837
3026
|
cause: e instanceof Error ? e : void 0,
|
|
@@ -2842,7 +3031,7 @@ async function submitSealOutputRequest(thresholdNetworkUrl, ctHash, chainId, per
|
|
|
2842
3031
|
});
|
|
2843
3032
|
}
|
|
2844
3033
|
if (!submitResponse.request_id) {
|
|
2845
|
-
throw new
|
|
3034
|
+
throw new CofheError({
|
|
2846
3035
|
code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
|
|
2847
3036
|
message: `sealOutput submit response missing request_id`,
|
|
2848
3037
|
context: {
|
|
@@ -2859,7 +3048,7 @@ async function pollSealOutputStatus(thresholdNetworkUrl, requestId) {
|
|
|
2859
3048
|
let completed = false;
|
|
2860
3049
|
while (!completed) {
|
|
2861
3050
|
if (Date.now() - startTime > POLL_TIMEOUT_MS) {
|
|
2862
|
-
throw new
|
|
3051
|
+
throw new CofheError({
|
|
2863
3052
|
code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
|
|
2864
3053
|
message: `sealOutput polling timed out after ${POLL_TIMEOUT_MS}ms`,
|
|
2865
3054
|
hint: "The request may still be processing. Try again later.",
|
|
@@ -2879,7 +3068,7 @@ async function pollSealOutputStatus(thresholdNetworkUrl, requestId) {
|
|
|
2879
3068
|
}
|
|
2880
3069
|
});
|
|
2881
3070
|
} catch (e) {
|
|
2882
|
-
throw new
|
|
3071
|
+
throw new CofheError({
|
|
2883
3072
|
code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
|
|
2884
3073
|
message: `sealOutput status poll failed`,
|
|
2885
3074
|
hint: "Ensure the threshold network URL is valid and reachable.",
|
|
@@ -2891,7 +3080,7 @@ async function pollSealOutputStatus(thresholdNetworkUrl, requestId) {
|
|
|
2891
3080
|
});
|
|
2892
3081
|
}
|
|
2893
3082
|
if (response.status === 404) {
|
|
2894
|
-
throw new
|
|
3083
|
+
throw new CofheError({
|
|
2895
3084
|
code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
|
|
2896
3085
|
message: `sealOutput request not found: ${requestId}`,
|
|
2897
3086
|
hint: "The request may have expired or been invalid.",
|
|
@@ -2909,7 +3098,7 @@ async function pollSealOutputStatus(thresholdNetworkUrl, requestId) {
|
|
|
2909
3098
|
} catch {
|
|
2910
3099
|
errorMessage = response.statusText || errorMessage;
|
|
2911
3100
|
}
|
|
2912
|
-
throw new
|
|
3101
|
+
throw new CofheError({
|
|
2913
3102
|
code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
|
|
2914
3103
|
message: `sealOutput status poll failed: ${errorMessage}`,
|
|
2915
3104
|
context: {
|
|
@@ -2924,7 +3113,7 @@ async function pollSealOutputStatus(thresholdNetworkUrl, requestId) {
|
|
|
2924
3113
|
try {
|
|
2925
3114
|
statusResponse = await response.json();
|
|
2926
3115
|
} catch (e) {
|
|
2927
|
-
throw new
|
|
3116
|
+
throw new CofheError({
|
|
2928
3117
|
code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
|
|
2929
3118
|
message: `Failed to parse sealOutput status response`,
|
|
2930
3119
|
cause: e instanceof Error ? e : void 0,
|
|
@@ -2937,7 +3126,7 @@ async function pollSealOutputStatus(thresholdNetworkUrl, requestId) {
|
|
|
2937
3126
|
if (statusResponse.status === "COMPLETED") {
|
|
2938
3127
|
if (statusResponse.is_succeed === false) {
|
|
2939
3128
|
const errorMessage = statusResponse.error_message || "Unknown error";
|
|
2940
|
-
throw new
|
|
3129
|
+
throw new CofheError({
|
|
2941
3130
|
code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
|
|
2942
3131
|
message: `sealOutput request failed: ${errorMessage}`,
|
|
2943
3132
|
context: {
|
|
@@ -2948,7 +3137,7 @@ async function pollSealOutputStatus(thresholdNetworkUrl, requestId) {
|
|
|
2948
3137
|
});
|
|
2949
3138
|
}
|
|
2950
3139
|
if (!statusResponse.sealed) {
|
|
2951
|
-
throw new
|
|
3140
|
+
throw new CofheError({
|
|
2952
3141
|
code: "SEAL_OUTPUT_RETURNED_NULL" /* SealOutputReturnedNull */,
|
|
2953
3142
|
message: `sealOutput request completed but returned no sealed data`,
|
|
2954
3143
|
context: {
|
|
@@ -2962,7 +3151,7 @@ async function pollSealOutputStatus(thresholdNetworkUrl, requestId) {
|
|
|
2962
3151
|
}
|
|
2963
3152
|
await new Promise((resolve) => setTimeout(resolve, POLL_INTERVAL_MS));
|
|
2964
3153
|
}
|
|
2965
|
-
throw new
|
|
3154
|
+
throw new CofheError({
|
|
2966
3155
|
code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
|
|
2967
3156
|
message: "Polling loop exited unexpectedly",
|
|
2968
3157
|
context: {
|
|
@@ -2975,9 +3164,99 @@ async function tnSealOutputV2(ctHash, chainId, permission, thresholdNetworkUrl)
|
|
|
2975
3164
|
const requestId = await submitSealOutputRequest(thresholdNetworkUrl, ctHash, chainId, permission);
|
|
2976
3165
|
return await pollSealOutputStatus(thresholdNetworkUrl, requestId);
|
|
2977
3166
|
}
|
|
3167
|
+
async function cofheMocksDecryptForTx(ctHash, utype, permit, publicClient, mocksDecryptForTxDelay) {
|
|
3168
|
+
if (mocksDecryptForTxDelay > 0)
|
|
3169
|
+
await sleep(mocksDecryptForTxDelay);
|
|
3170
|
+
if (permit !== null) {
|
|
3171
|
+
let permission = PermitUtils.getPermission(permit, true);
|
|
3172
|
+
const permissionWithBigInts = {
|
|
3173
|
+
...permission,
|
|
3174
|
+
expiration: BigInt(permission.expiration),
|
|
3175
|
+
validatorId: BigInt(permission.validatorId)
|
|
3176
|
+
};
|
|
3177
|
+
const [allowed2, error2, result2] = await publicClient.readContract({
|
|
3178
|
+
address: MOCKS_THRESHOLD_NETWORK_ADDRESS,
|
|
3179
|
+
abi: MockThresholdNetworkAbi,
|
|
3180
|
+
functionName: "decryptForTxWithPermit",
|
|
3181
|
+
args: [ctHash, permissionWithBigInts]
|
|
3182
|
+
});
|
|
3183
|
+
if (error2 != "") {
|
|
3184
|
+
throw new CofheError({
|
|
3185
|
+
code: "DECRYPT_FAILED" /* DecryptFailed */,
|
|
3186
|
+
message: `mocks decryptForTx call failed: ${error2}`
|
|
3187
|
+
});
|
|
3188
|
+
}
|
|
3189
|
+
if (allowed2 == false) {
|
|
3190
|
+
throw new CofheError({
|
|
3191
|
+
code: "DECRYPT_FAILED" /* DecryptFailed */,
|
|
3192
|
+
message: `mocks decryptForTx call failed: ACL Access Denied (NotAllowed)`
|
|
3193
|
+
});
|
|
3194
|
+
}
|
|
3195
|
+
const chainId2 = await publicClient.getChainId();
|
|
3196
|
+
const ctHashBigInt2 = BigInt(ctHash);
|
|
3197
|
+
const resultBigInt2 = BigInt(result2);
|
|
3198
|
+
const encryptionType2 = Number((ctHashBigInt2 & 0x7fn << 8n) >> 8n);
|
|
3199
|
+
const ctHashBytes322 = viem.pad(viem.toHex(ctHashBigInt2), { size: 32 });
|
|
3200
|
+
const packed2 = viem.encodePacked(
|
|
3201
|
+
["uint256", "uint32", "uint64", "bytes32"],
|
|
3202
|
+
[resultBigInt2, encryptionType2, BigInt(chainId2), ctHashBytes322]
|
|
3203
|
+
);
|
|
3204
|
+
const messageHash2 = viem.keccak256(packed2);
|
|
3205
|
+
const signatureHex2 = await accounts.sign({
|
|
3206
|
+
hash: messageHash2,
|
|
3207
|
+
privateKey: MOCKS_DECRYPT_RESULT_SIGNER_PRIVATE_KEY,
|
|
3208
|
+
to: "hex"
|
|
3209
|
+
});
|
|
3210
|
+
const signature2 = signatureHex2.slice(2);
|
|
3211
|
+
return {
|
|
3212
|
+
ctHash,
|
|
3213
|
+
decryptedValue: BigInt(result2),
|
|
3214
|
+
signature: signature2
|
|
3215
|
+
};
|
|
3216
|
+
}
|
|
3217
|
+
const [allowed, error, result] = await publicClient.readContract({
|
|
3218
|
+
address: MOCKS_THRESHOLD_NETWORK_ADDRESS,
|
|
3219
|
+
abi: MockThresholdNetworkAbi,
|
|
3220
|
+
functionName: "decryptForTxWithoutPermit",
|
|
3221
|
+
args: [ctHash]
|
|
3222
|
+
});
|
|
3223
|
+
if (error != "") {
|
|
3224
|
+
throw new CofheError({
|
|
3225
|
+
code: "DECRYPT_FAILED" /* DecryptFailed */,
|
|
3226
|
+
message: `mocks decryptForTx call failed: ${error}`
|
|
3227
|
+
});
|
|
3228
|
+
}
|
|
3229
|
+
if (allowed == false) {
|
|
3230
|
+
throw new CofheError({
|
|
3231
|
+
code: "DECRYPT_FAILED" /* DecryptFailed */,
|
|
3232
|
+
message: `mocks decryptForTx call failed: ACL Access Denied (NotAllowed)`
|
|
3233
|
+
});
|
|
3234
|
+
}
|
|
3235
|
+
const chainId = await publicClient.getChainId();
|
|
3236
|
+
const ctHashBigInt = BigInt(ctHash);
|
|
3237
|
+
const resultBigInt = BigInt(result);
|
|
3238
|
+
const encryptionType = Number((ctHashBigInt & 0x7fn << 8n) >> 8n);
|
|
3239
|
+
const ctHashBytes32 = viem.pad(viem.toHex(ctHashBigInt), { size: 32 });
|
|
3240
|
+
const packed = viem.encodePacked(
|
|
3241
|
+
["uint256", "uint32", "uint64", "bytes32"],
|
|
3242
|
+
[resultBigInt, encryptionType, BigInt(chainId), ctHashBytes32]
|
|
3243
|
+
);
|
|
3244
|
+
const messageHash = viem.keccak256(packed);
|
|
3245
|
+
const signatureHex = await accounts.sign({
|
|
3246
|
+
hash: messageHash,
|
|
3247
|
+
privateKey: MOCKS_DECRYPT_RESULT_SIGNER_PRIVATE_KEY,
|
|
3248
|
+
to: "hex"
|
|
3249
|
+
});
|
|
3250
|
+
const signature = signatureHex.slice(2);
|
|
3251
|
+
return {
|
|
3252
|
+
ctHash,
|
|
3253
|
+
decryptedValue: BigInt(result),
|
|
3254
|
+
signature
|
|
3255
|
+
};
|
|
3256
|
+
}
|
|
2978
3257
|
|
|
2979
|
-
// core/decrypt/
|
|
2980
|
-
var
|
|
3258
|
+
// core/decrypt/decryptForViewBuilder.ts
|
|
3259
|
+
var DecryptForViewBuilder = class extends BaseBuilder {
|
|
2981
3260
|
ctHash;
|
|
2982
3261
|
utype;
|
|
2983
3262
|
permitHash;
|
|
@@ -3003,12 +3282,12 @@ var DecryptHandlesBuilder = class extends BaseBuilder {
|
|
|
3003
3282
|
*
|
|
3004
3283
|
* Example:
|
|
3005
3284
|
* ```typescript
|
|
3006
|
-
* const unsealed = await
|
|
3285
|
+
* const unsealed = await client.decryptForView(ctHash, utype)
|
|
3007
3286
|
* .setChainId(11155111)
|
|
3008
|
-
* .
|
|
3287
|
+
* .execute();
|
|
3009
3288
|
* ```
|
|
3010
3289
|
*
|
|
3011
|
-
* @returns The chainable
|
|
3290
|
+
* @returns The chainable DecryptForViewBuilder instance.
|
|
3012
3291
|
*/
|
|
3013
3292
|
setChainId(chainId) {
|
|
3014
3293
|
this.chainId = chainId;
|
|
@@ -3024,12 +3303,12 @@ var DecryptHandlesBuilder = class extends BaseBuilder {
|
|
|
3024
3303
|
*
|
|
3025
3304
|
* Example:
|
|
3026
3305
|
* ```typescript
|
|
3027
|
-
* const unsealed = await
|
|
3306
|
+
* const unsealed = await client.decryptForView(ctHash, utype)
|
|
3028
3307
|
* .setAccount('0x1234567890123456789012345678901234567890')
|
|
3029
|
-
* .
|
|
3308
|
+
* .execute();
|
|
3030
3309
|
* ```
|
|
3031
3310
|
*
|
|
3032
|
-
* @returns The chainable
|
|
3311
|
+
* @returns The chainable DecryptForViewBuilder instance.
|
|
3033
3312
|
*/
|
|
3034
3313
|
setAccount(account) {
|
|
3035
3314
|
this.account = account;
|
|
@@ -3038,6 +3317,19 @@ var DecryptHandlesBuilder = class extends BaseBuilder {
|
|
|
3038
3317
|
getAccount() {
|
|
3039
3318
|
return this.account;
|
|
3040
3319
|
}
|
|
3320
|
+
withPermit(permitOrPermitHash) {
|
|
3321
|
+
if (typeof permitOrPermitHash === "string") {
|
|
3322
|
+
this.permitHash = permitOrPermitHash;
|
|
3323
|
+
this.permit = void 0;
|
|
3324
|
+
} else if (permitOrPermitHash === void 0) {
|
|
3325
|
+
this.permitHash = void 0;
|
|
3326
|
+
this.permit = void 0;
|
|
3327
|
+
} else {
|
|
3328
|
+
this.permit = permitOrPermitHash;
|
|
3329
|
+
this.permitHash = void 0;
|
|
3330
|
+
}
|
|
3331
|
+
return this;
|
|
3332
|
+
}
|
|
3041
3333
|
/**
|
|
3042
3334
|
* @param permitHash - Permit hash to decrypt values from. Used to fetch the correct permit.
|
|
3043
3335
|
*
|
|
@@ -3046,16 +3338,16 @@ var DecryptHandlesBuilder = class extends BaseBuilder {
|
|
|
3046
3338
|
*
|
|
3047
3339
|
* Example:
|
|
3048
3340
|
* ```typescript
|
|
3049
|
-
* const unsealed = await
|
|
3341
|
+
* const unsealed = await client.decryptForView(ctHash, utype)
|
|
3050
3342
|
* .setPermitHash('0x1234567890123456789012345678901234567890')
|
|
3051
|
-
* .
|
|
3343
|
+
* .execute();
|
|
3052
3344
|
* ```
|
|
3053
3345
|
*
|
|
3054
|
-
* @returns The chainable
|
|
3346
|
+
* @returns The chainable DecryptForViewBuilder instance.
|
|
3055
3347
|
*/
|
|
3348
|
+
/** @deprecated Use `withPermit(permitHash)` instead. */
|
|
3056
3349
|
setPermitHash(permitHash) {
|
|
3057
|
-
this.permitHash
|
|
3058
|
-
return this;
|
|
3350
|
+
return this.withPermit(permitHash);
|
|
3059
3351
|
}
|
|
3060
3352
|
getPermitHash() {
|
|
3061
3353
|
return this.permitHash;
|
|
@@ -3067,16 +3359,16 @@ var DecryptHandlesBuilder = class extends BaseBuilder {
|
|
|
3067
3359
|
*
|
|
3068
3360
|
* Example:
|
|
3069
3361
|
* ```typescript
|
|
3070
|
-
* const unsealed = await
|
|
3362
|
+
* const unsealed = await client.decryptForView(ctHash, utype)
|
|
3071
3363
|
* .setPermit(permit)
|
|
3072
|
-
* .
|
|
3364
|
+
* .execute();
|
|
3073
3365
|
* ```
|
|
3074
3366
|
*
|
|
3075
|
-
* @returns The chainable
|
|
3367
|
+
* @returns The chainable DecryptForViewBuilder instance.
|
|
3076
3368
|
*/
|
|
3369
|
+
/** @deprecated Use `withPermit(permit)` instead. */
|
|
3077
3370
|
setPermit(permit) {
|
|
3078
|
-
this.permit
|
|
3079
|
-
return this;
|
|
3371
|
+
return this.withPermit(permit);
|
|
3080
3372
|
}
|
|
3081
3373
|
getPermit() {
|
|
3082
3374
|
return this.permit;
|
|
@@ -3087,7 +3379,7 @@ var DecryptHandlesBuilder = class extends BaseBuilder {
|
|
|
3087
3379
|
}
|
|
3088
3380
|
validateUtypeOrThrow() {
|
|
3089
3381
|
if (!isValidUtype(this.utype))
|
|
3090
|
-
throw new
|
|
3382
|
+
throw new CofheError({
|
|
3091
3383
|
code: "INVALID_UTYPE" /* InvalidUtype */,
|
|
3092
3384
|
message: `Invalid utype to decrypt to`,
|
|
3093
3385
|
context: {
|
|
@@ -3103,7 +3395,7 @@ var DecryptHandlesBuilder = class extends BaseBuilder {
|
|
|
3103
3395
|
if (this.permitHash) {
|
|
3104
3396
|
const permit2 = await permits.getPermit(this.chainId, this.account, this.permitHash);
|
|
3105
3397
|
if (!permit2) {
|
|
3106
|
-
throw new
|
|
3398
|
+
throw new CofheError({
|
|
3107
3399
|
code: "PERMIT_NOT_FOUND" /* PermitNotFound */,
|
|
3108
3400
|
message: `Permit with hash <${this.permitHash}> not found for account <${this.account}> and chainId <${this.chainId}>`,
|
|
3109
3401
|
hint: "Ensure the permit exists and is valid.",
|
|
@@ -3118,7 +3410,7 @@ var DecryptHandlesBuilder = class extends BaseBuilder {
|
|
|
3118
3410
|
}
|
|
3119
3411
|
const permit = await permits.getActivePermit(this.chainId, this.account);
|
|
3120
3412
|
if (!permit) {
|
|
3121
|
-
throw new
|
|
3413
|
+
throw new CofheError({
|
|
3122
3414
|
code: "PERMIT_NOT_FOUND" /* PermitNotFound */,
|
|
3123
3415
|
message: `Active permit not found for chainId <${this.chainId}> and account <${this.account}>`,
|
|
3124
3416
|
hint: "Ensure a permit exists for this account on this chain.",
|
|
@@ -3135,8 +3427,8 @@ var DecryptHandlesBuilder = class extends BaseBuilder {
|
|
|
3135
3427
|
*/
|
|
3136
3428
|
async mocksSealOutput(permit) {
|
|
3137
3429
|
this.assertPublicClient();
|
|
3138
|
-
const
|
|
3139
|
-
return
|
|
3430
|
+
const mocksDecryptDelay = this.config.mocks.decryptDelay;
|
|
3431
|
+
return cofheMocksDecryptForView(this.ctHash, this.utype, permit, this.publicClient, mocksDecryptDelay);
|
|
3140
3432
|
}
|
|
3141
3433
|
/**
|
|
3142
3434
|
* In the production context, perform a true decryption with the CoFHE coprocessor.
|
|
@@ -3161,15 +3453,16 @@ var DecryptHandlesBuilder = class extends BaseBuilder {
|
|
|
3161
3453
|
*
|
|
3162
3454
|
* Example:
|
|
3163
3455
|
* ```typescript
|
|
3164
|
-
* const unsealed = await
|
|
3456
|
+
* const unsealed = await client.decryptForView(ctHash, utype)
|
|
3165
3457
|
* .setChainId(11155111) // optional
|
|
3166
3458
|
* .setAccount('0x123...890') // optional
|
|
3167
|
-
* .
|
|
3459
|
+
* .withPermit() // optional
|
|
3460
|
+
* .execute(); // execute
|
|
3168
3461
|
* ```
|
|
3169
3462
|
*
|
|
3170
3463
|
* @returns The unsealed item.
|
|
3171
3464
|
*/
|
|
3172
|
-
async
|
|
3465
|
+
async execute() {
|
|
3173
3466
|
this.validateUtypeOrThrow();
|
|
3174
3467
|
const permit = await this.getResolvedPermit();
|
|
3175
3468
|
PermitUtils.validate(permit);
|
|
@@ -3185,6 +3478,394 @@ var DecryptHandlesBuilder = class extends BaseBuilder {
|
|
|
3185
3478
|
}
|
|
3186
3479
|
};
|
|
3187
3480
|
|
|
3481
|
+
// core/decrypt/tnDecrypt.ts
|
|
3482
|
+
function normalizeSignature(signature) {
|
|
3483
|
+
if (typeof signature !== "string") {
|
|
3484
|
+
throw new CofheError({
|
|
3485
|
+
code: "DECRYPT_RETURNED_NULL" /* DecryptReturnedNull */,
|
|
3486
|
+
message: "decrypt response missing signature",
|
|
3487
|
+
context: {
|
|
3488
|
+
signature
|
|
3489
|
+
}
|
|
3490
|
+
});
|
|
3491
|
+
}
|
|
3492
|
+
const trimmed = signature.trim();
|
|
3493
|
+
if (trimmed.length === 0) {
|
|
3494
|
+
throw new CofheError({
|
|
3495
|
+
code: "DECRYPT_RETURNED_NULL" /* DecryptReturnedNull */,
|
|
3496
|
+
message: "decrypt response returned empty signature"
|
|
3497
|
+
});
|
|
3498
|
+
}
|
|
3499
|
+
return trimmed.startsWith("0x") ? trimmed.slice(2) : trimmed;
|
|
3500
|
+
}
|
|
3501
|
+
function parseDecryptedBytesToBigInt(decrypted) {
|
|
3502
|
+
if (!Array.isArray(decrypted)) {
|
|
3503
|
+
throw new CofheError({
|
|
3504
|
+
code: "DECRYPT_RETURNED_NULL" /* DecryptReturnedNull */,
|
|
3505
|
+
message: "decrypt response field <decrypted> must be a byte array",
|
|
3506
|
+
context: {
|
|
3507
|
+
decrypted
|
|
3508
|
+
}
|
|
3509
|
+
});
|
|
3510
|
+
}
|
|
3511
|
+
if (decrypted.length === 0) {
|
|
3512
|
+
throw new CofheError({
|
|
3513
|
+
code: "DECRYPT_RETURNED_NULL" /* DecryptReturnedNull */,
|
|
3514
|
+
message: "decrypt response field <decrypted> was an empty byte array",
|
|
3515
|
+
context: {
|
|
3516
|
+
decrypted
|
|
3517
|
+
}
|
|
3518
|
+
});
|
|
3519
|
+
}
|
|
3520
|
+
let hex = "";
|
|
3521
|
+
for (const b of decrypted) {
|
|
3522
|
+
if (typeof b !== "number" || !Number.isInteger(b) || b < 0 || b > 255) {
|
|
3523
|
+
throw new CofheError({
|
|
3524
|
+
code: "DECRYPT_RETURNED_NULL" /* DecryptReturnedNull */,
|
|
3525
|
+
message: "decrypt response field <decrypted> contained a non-byte value",
|
|
3526
|
+
context: {
|
|
3527
|
+
badElement: b,
|
|
3528
|
+
decrypted
|
|
3529
|
+
}
|
|
3530
|
+
});
|
|
3531
|
+
}
|
|
3532
|
+
hex += b.toString(16).padStart(2, "0");
|
|
3533
|
+
}
|
|
3534
|
+
return BigInt(`0x${hex}`);
|
|
3535
|
+
}
|
|
3536
|
+
function assertTnDecryptResponse(value) {
|
|
3537
|
+
if (value == null || typeof value !== "object") {
|
|
3538
|
+
throw new CofheError({
|
|
3539
|
+
code: "DECRYPT_FAILED" /* DecryptFailed */,
|
|
3540
|
+
message: "decrypt response must be a JSON object",
|
|
3541
|
+
context: {
|
|
3542
|
+
value
|
|
3543
|
+
}
|
|
3544
|
+
});
|
|
3545
|
+
}
|
|
3546
|
+
const v = value;
|
|
3547
|
+
const decrypted = v.decrypted;
|
|
3548
|
+
const signature = v.signature;
|
|
3549
|
+
const encryptionType = v.encryption_type;
|
|
3550
|
+
const errorMessage = v.error_message;
|
|
3551
|
+
if (!Array.isArray(decrypted)) {
|
|
3552
|
+
throw new CofheError({
|
|
3553
|
+
code: "DECRYPT_RETURNED_NULL" /* DecryptReturnedNull */,
|
|
3554
|
+
message: "decrypt response missing <decrypted> byte array",
|
|
3555
|
+
context: { decryptResponse: value }
|
|
3556
|
+
});
|
|
3557
|
+
}
|
|
3558
|
+
if (typeof signature !== "string") {
|
|
3559
|
+
throw new CofheError({
|
|
3560
|
+
code: "DECRYPT_RETURNED_NULL" /* DecryptReturnedNull */,
|
|
3561
|
+
message: "decrypt response missing <signature> string",
|
|
3562
|
+
context: { decryptResponse: value }
|
|
3563
|
+
});
|
|
3564
|
+
}
|
|
3565
|
+
if (typeof encryptionType !== "number") {
|
|
3566
|
+
throw new CofheError({
|
|
3567
|
+
code: "DECRYPT_FAILED" /* DecryptFailed */,
|
|
3568
|
+
message: "decrypt response missing <encryption_type> number",
|
|
3569
|
+
context: { decryptResponse: value }
|
|
3570
|
+
});
|
|
3571
|
+
}
|
|
3572
|
+
if (!(typeof errorMessage === "string" || errorMessage === null)) {
|
|
3573
|
+
throw new CofheError({
|
|
3574
|
+
code: "DECRYPT_FAILED" /* DecryptFailed */,
|
|
3575
|
+
message: "decrypt response field <error_message> must be string or null",
|
|
3576
|
+
context: { decryptResponse: value }
|
|
3577
|
+
});
|
|
3578
|
+
}
|
|
3579
|
+
return {
|
|
3580
|
+
decrypted,
|
|
3581
|
+
signature,
|
|
3582
|
+
encryption_type: encryptionType,
|
|
3583
|
+
error_message: errorMessage
|
|
3584
|
+
};
|
|
3585
|
+
}
|
|
3586
|
+
async function tnDecrypt(ctHash, chainId, permission, thresholdNetworkUrl) {
|
|
3587
|
+
const body = {
|
|
3588
|
+
ct_tempkey: ctHash.toString(16).padStart(64, "0"),
|
|
3589
|
+
host_chain_id: chainId
|
|
3590
|
+
};
|
|
3591
|
+
if (permission) {
|
|
3592
|
+
body.permit = permission;
|
|
3593
|
+
}
|
|
3594
|
+
let response;
|
|
3595
|
+
try {
|
|
3596
|
+
response = await fetch(`${thresholdNetworkUrl}/decrypt`, {
|
|
3597
|
+
method: "POST",
|
|
3598
|
+
headers: {
|
|
3599
|
+
"Content-Type": "application/json"
|
|
3600
|
+
},
|
|
3601
|
+
body: JSON.stringify(body)
|
|
3602
|
+
});
|
|
3603
|
+
} catch (e) {
|
|
3604
|
+
throw new CofheError({
|
|
3605
|
+
code: "DECRYPT_FAILED" /* DecryptFailed */,
|
|
3606
|
+
message: `decrypt request failed`,
|
|
3607
|
+
hint: "Ensure the threshold network URL is valid and reachable.",
|
|
3608
|
+
cause: e instanceof Error ? e : void 0,
|
|
3609
|
+
context: {
|
|
3610
|
+
thresholdNetworkUrl,
|
|
3611
|
+
body
|
|
3612
|
+
}
|
|
3613
|
+
});
|
|
3614
|
+
}
|
|
3615
|
+
const responseText = await response.text();
|
|
3616
|
+
if (!response.ok) {
|
|
3617
|
+
let errorMessage = response.statusText || `HTTP ${response.status}`;
|
|
3618
|
+
try {
|
|
3619
|
+
const errorBody = JSON.parse(responseText);
|
|
3620
|
+
const maybeMessage = errorBody.error_message || errorBody.message;
|
|
3621
|
+
if (typeof maybeMessage === "string" && maybeMessage.length > 0)
|
|
3622
|
+
errorMessage = maybeMessage;
|
|
3623
|
+
} catch {
|
|
3624
|
+
const trimmed = responseText.trim();
|
|
3625
|
+
if (trimmed.length > 0)
|
|
3626
|
+
errorMessage = trimmed;
|
|
3627
|
+
}
|
|
3628
|
+
throw new CofheError({
|
|
3629
|
+
code: "DECRYPT_FAILED" /* DecryptFailed */,
|
|
3630
|
+
message: `decrypt request failed: ${errorMessage}`,
|
|
3631
|
+
hint: "Check the threshold network URL and request parameters.",
|
|
3632
|
+
context: {
|
|
3633
|
+
thresholdNetworkUrl,
|
|
3634
|
+
status: response.status,
|
|
3635
|
+
statusText: response.statusText,
|
|
3636
|
+
body,
|
|
3637
|
+
responseText
|
|
3638
|
+
}
|
|
3639
|
+
});
|
|
3640
|
+
}
|
|
3641
|
+
let rawJson;
|
|
3642
|
+
try {
|
|
3643
|
+
rawJson = JSON.parse(responseText);
|
|
3644
|
+
} catch (e) {
|
|
3645
|
+
throw new CofheError({
|
|
3646
|
+
code: "DECRYPT_FAILED" /* DecryptFailed */,
|
|
3647
|
+
message: `Failed to parse decrypt response`,
|
|
3648
|
+
cause: e instanceof Error ? e : void 0,
|
|
3649
|
+
context: {
|
|
3650
|
+
thresholdNetworkUrl,
|
|
3651
|
+
body,
|
|
3652
|
+
responseText
|
|
3653
|
+
}
|
|
3654
|
+
});
|
|
3655
|
+
}
|
|
3656
|
+
const decryptResponse = assertTnDecryptResponse(rawJson);
|
|
3657
|
+
if (decryptResponse.error_message) {
|
|
3658
|
+
throw new CofheError({
|
|
3659
|
+
code: "DECRYPT_FAILED" /* DecryptFailed */,
|
|
3660
|
+
message: `decrypt request failed: ${decryptResponse.error_message}`,
|
|
3661
|
+
context: {
|
|
3662
|
+
thresholdNetworkUrl,
|
|
3663
|
+
body,
|
|
3664
|
+
decryptResponse
|
|
3665
|
+
}
|
|
3666
|
+
});
|
|
3667
|
+
}
|
|
3668
|
+
const decryptedValue = parseDecryptedBytesToBigInt(decryptResponse.decrypted);
|
|
3669
|
+
const signature = normalizeSignature(decryptResponse.signature);
|
|
3670
|
+
return { decryptedValue, signature };
|
|
3671
|
+
}
|
|
3672
|
+
|
|
3673
|
+
// core/decrypt/decryptForTxBuilder.ts
|
|
3674
|
+
var DecryptForTxBuilder = class extends BaseBuilder {
|
|
3675
|
+
ctHash;
|
|
3676
|
+
permitHash;
|
|
3677
|
+
permit;
|
|
3678
|
+
permitSelection = "unset";
|
|
3679
|
+
constructor(params) {
|
|
3680
|
+
super({
|
|
3681
|
+
config: params.config,
|
|
3682
|
+
publicClient: params.publicClient,
|
|
3683
|
+
walletClient: params.walletClient,
|
|
3684
|
+
chainId: params.chainId,
|
|
3685
|
+
account: params.account,
|
|
3686
|
+
requireConnected: params.requireConnected
|
|
3687
|
+
});
|
|
3688
|
+
this.ctHash = params.ctHash;
|
|
3689
|
+
}
|
|
3690
|
+
setChainId(chainId) {
|
|
3691
|
+
this.chainId = chainId;
|
|
3692
|
+
return this;
|
|
3693
|
+
}
|
|
3694
|
+
getChainId() {
|
|
3695
|
+
return this.chainId;
|
|
3696
|
+
}
|
|
3697
|
+
setAccount(account) {
|
|
3698
|
+
this.account = account;
|
|
3699
|
+
return this;
|
|
3700
|
+
}
|
|
3701
|
+
getAccount() {
|
|
3702
|
+
return this.account;
|
|
3703
|
+
}
|
|
3704
|
+
withPermit(permitOrPermitHash) {
|
|
3705
|
+
if (this.permitSelection === "with-permit") {
|
|
3706
|
+
throw new CofheError({
|
|
3707
|
+
code: "INTERNAL_ERROR" /* InternalError */,
|
|
3708
|
+
message: "decryptForTx: withPermit() can only be selected once.",
|
|
3709
|
+
hint: "Choose the permit mode once. If you need a different permit, start a new decryptForTx() builder chain."
|
|
3710
|
+
});
|
|
3711
|
+
}
|
|
3712
|
+
if (this.permitSelection === "without-permit") {
|
|
3713
|
+
throw new CofheError({
|
|
3714
|
+
code: "INTERNAL_ERROR" /* InternalError */,
|
|
3715
|
+
message: "decryptForTx: cannot call withPermit() after withoutPermit() has been selected.",
|
|
3716
|
+
hint: "Choose exactly one permit mode: either call .withPermit(...) or .withoutPermit(), but not both."
|
|
3717
|
+
});
|
|
3718
|
+
}
|
|
3719
|
+
this.permitSelection = "with-permit";
|
|
3720
|
+
if (typeof permitOrPermitHash === "string") {
|
|
3721
|
+
this.permitHash = permitOrPermitHash;
|
|
3722
|
+
this.permit = void 0;
|
|
3723
|
+
} else if (permitOrPermitHash === void 0) {
|
|
3724
|
+
this.permitHash = void 0;
|
|
3725
|
+
this.permit = void 0;
|
|
3726
|
+
} else {
|
|
3727
|
+
this.permit = permitOrPermitHash;
|
|
3728
|
+
this.permitHash = void 0;
|
|
3729
|
+
}
|
|
3730
|
+
return this;
|
|
3731
|
+
}
|
|
3732
|
+
/**
|
|
3733
|
+
* Select "no permit" mode.
|
|
3734
|
+
*
|
|
3735
|
+
* This uses global allowance (no permit required) and sends an empty permission payload to `/decrypt`.
|
|
3736
|
+
*/
|
|
3737
|
+
withoutPermit() {
|
|
3738
|
+
if (this.permitSelection === "without-permit") {
|
|
3739
|
+
throw new CofheError({
|
|
3740
|
+
code: "INTERNAL_ERROR" /* InternalError */,
|
|
3741
|
+
message: "decryptForTx: withoutPermit() can only be selected once.",
|
|
3742
|
+
hint: "Choose the permit mode once. If you need a different mode, start a new decryptForTx() builder chain."
|
|
3743
|
+
});
|
|
3744
|
+
}
|
|
3745
|
+
if (this.permitSelection === "with-permit") {
|
|
3746
|
+
throw new CofheError({
|
|
3747
|
+
code: "INTERNAL_ERROR" /* InternalError */,
|
|
3748
|
+
message: "decryptForTx: cannot call withoutPermit() after withPermit() has been selected.",
|
|
3749
|
+
hint: "Choose exactly one permit mode: either call .withPermit(...) or .withoutPermit(), but not both."
|
|
3750
|
+
});
|
|
3751
|
+
}
|
|
3752
|
+
this.permitSelection = "without-permit";
|
|
3753
|
+
this.permitHash = void 0;
|
|
3754
|
+
this.permit = void 0;
|
|
3755
|
+
return this;
|
|
3756
|
+
}
|
|
3757
|
+
getPermit() {
|
|
3758
|
+
return this.permit;
|
|
3759
|
+
}
|
|
3760
|
+
getPermitHash() {
|
|
3761
|
+
return this.permitHash;
|
|
3762
|
+
}
|
|
3763
|
+
async getThresholdNetworkUrl() {
|
|
3764
|
+
this.assertChainId();
|
|
3765
|
+
return getThresholdNetworkUrlOrThrow(this.config, this.chainId);
|
|
3766
|
+
}
|
|
3767
|
+
async getResolvedPermit() {
|
|
3768
|
+
if (this.permitSelection === "unset") {
|
|
3769
|
+
throw new CofheError({
|
|
3770
|
+
code: "INTERNAL_ERROR" /* InternalError */,
|
|
3771
|
+
message: "decryptForTx: missing permit selection; call withPermit(...) or withoutPermit() before execute().",
|
|
3772
|
+
hint: "Call .withPermit() to use the active permit, or .withoutPermit() for global allowance."
|
|
3773
|
+
});
|
|
3774
|
+
}
|
|
3775
|
+
if (this.permitSelection === "without-permit") {
|
|
3776
|
+
return null;
|
|
3777
|
+
}
|
|
3778
|
+
if (this.permit)
|
|
3779
|
+
return this.permit;
|
|
3780
|
+
this.assertChainId();
|
|
3781
|
+
this.assertAccount();
|
|
3782
|
+
if (this.permitHash) {
|
|
3783
|
+
const permit2 = await permits.getPermit(this.chainId, this.account, this.permitHash);
|
|
3784
|
+
if (!permit2) {
|
|
3785
|
+
throw new CofheError({
|
|
3786
|
+
code: "PERMIT_NOT_FOUND" /* PermitNotFound */,
|
|
3787
|
+
message: `Permit with hash <${this.permitHash}> not found for account <${this.account}> and chainId <${this.chainId}>`,
|
|
3788
|
+
hint: "Ensure the permit exists and is valid.",
|
|
3789
|
+
context: {
|
|
3790
|
+
chainId: this.chainId,
|
|
3791
|
+
account: this.account,
|
|
3792
|
+
permitHash: this.permitHash
|
|
3793
|
+
}
|
|
3794
|
+
});
|
|
3795
|
+
}
|
|
3796
|
+
return permit2;
|
|
3797
|
+
}
|
|
3798
|
+
const permit = await permits.getActivePermit(this.chainId, this.account);
|
|
3799
|
+
if (!permit) {
|
|
3800
|
+
throw new CofheError({
|
|
3801
|
+
code: "PERMIT_NOT_FOUND" /* PermitNotFound */,
|
|
3802
|
+
message: `Active permit not found for chainId <${this.chainId}> and account <${this.account}>`,
|
|
3803
|
+
hint: "Create a permit (e.g. client.permits.createSelf(...)) and/or set it active (client.permits.selectActivePermit(hash)).",
|
|
3804
|
+
context: {
|
|
3805
|
+
chainId: this.chainId,
|
|
3806
|
+
account: this.account
|
|
3807
|
+
}
|
|
3808
|
+
});
|
|
3809
|
+
}
|
|
3810
|
+
return permit;
|
|
3811
|
+
}
|
|
3812
|
+
/**
|
|
3813
|
+
* On hardhat, interact with MockThresholdNetwork contract
|
|
3814
|
+
*/
|
|
3815
|
+
async mocksDecryptForTx(permit) {
|
|
3816
|
+
this.assertPublicClient();
|
|
3817
|
+
const delay = this.config.mocks.decryptDelay;
|
|
3818
|
+
const result = await cofheMocksDecryptForTx(this.ctHash, 0, permit, this.publicClient, delay);
|
|
3819
|
+
return result;
|
|
3820
|
+
}
|
|
3821
|
+
/**
|
|
3822
|
+
* In the production context, perform a true decryption with the CoFHE coprocessor.
|
|
3823
|
+
*/
|
|
3824
|
+
async productionDecryptForTx(permit) {
|
|
3825
|
+
this.assertChainId();
|
|
3826
|
+
this.assertPublicClient();
|
|
3827
|
+
const thresholdNetworkUrl = await this.getThresholdNetworkUrl();
|
|
3828
|
+
const permission = permit ? PermitUtils.getPermission(permit, true) : null;
|
|
3829
|
+
const { decryptedValue, signature } = await tnDecrypt(this.ctHash, this.chainId, permission, thresholdNetworkUrl);
|
|
3830
|
+
return {
|
|
3831
|
+
ctHash: this.ctHash,
|
|
3832
|
+
decryptedValue,
|
|
3833
|
+
signature
|
|
3834
|
+
};
|
|
3835
|
+
}
|
|
3836
|
+
/**
|
|
3837
|
+
* Final step of the decryptForTx process. MUST BE CALLED LAST IN THE CHAIN.
|
|
3838
|
+
*
|
|
3839
|
+
* You must explicitly choose one permit mode before calling `execute()`:
|
|
3840
|
+
* - `withPermit(permit)` / `withPermit(permitHash)` / `withPermit()` (active permit)
|
|
3841
|
+
* - `withoutPermit()` (global allowance)
|
|
3842
|
+
*/
|
|
3843
|
+
async execute() {
|
|
3844
|
+
const permit = await this.getResolvedPermit();
|
|
3845
|
+
if (permit !== null) {
|
|
3846
|
+
PermitUtils.validate(permit);
|
|
3847
|
+
PermitUtils.isValid(permit);
|
|
3848
|
+
const chainId = permit._signedDomain.chainId;
|
|
3849
|
+
if (chainId === hardhat2.id) {
|
|
3850
|
+
return await this.mocksDecryptForTx(permit);
|
|
3851
|
+
} else {
|
|
3852
|
+
return await this.productionDecryptForTx(permit);
|
|
3853
|
+
}
|
|
3854
|
+
} else {
|
|
3855
|
+
if (!this.chainId) {
|
|
3856
|
+
this.assertPublicClient();
|
|
3857
|
+
this.chainId = await getPublicClientChainID(this.publicClient);
|
|
3858
|
+
}
|
|
3859
|
+
this.assertChainId();
|
|
3860
|
+
if (this.chainId === hardhat2.id) {
|
|
3861
|
+
return await this.mocksDecryptForTx(null);
|
|
3862
|
+
} else {
|
|
3863
|
+
return await this.productionDecryptForTx(null);
|
|
3864
|
+
}
|
|
3865
|
+
}
|
|
3866
|
+
}
|
|
3867
|
+
};
|
|
3868
|
+
|
|
3188
3869
|
// core/client.ts
|
|
3189
3870
|
var InitialConnectStore = {
|
|
3190
3871
|
connected: false,
|
|
@@ -3195,9 +3876,10 @@ var InitialConnectStore = {
|
|
|
3195
3876
|
publicClient: void 0,
|
|
3196
3877
|
walletClient: void 0
|
|
3197
3878
|
};
|
|
3198
|
-
function
|
|
3879
|
+
function createCofheClientBase(opts) {
|
|
3199
3880
|
const keysStorage = createKeysStore(opts.config.fheKeyStorage);
|
|
3200
3881
|
const connectStore = vanilla.createStore(() => InitialConnectStore);
|
|
3882
|
+
let connectAttemptId = 0;
|
|
3201
3883
|
const updateConnectState = (partial) => {
|
|
3202
3884
|
connectStore.setState((state) => ({ ...state, ...partial }));
|
|
3203
3885
|
};
|
|
@@ -3205,7 +3887,7 @@ function createCofhesdkClientBase(opts) {
|
|
|
3205
3887
|
const state = connectStore.getState();
|
|
3206
3888
|
const notConnected = !state.connected || !state.account || !state.chainId || !state.publicClient || !state.walletClient;
|
|
3207
3889
|
if (notConnected) {
|
|
3208
|
-
throw new
|
|
3890
|
+
throw new CofheError({
|
|
3209
3891
|
code: "NOT_CONNECTED" /* NotConnected */,
|
|
3210
3892
|
message: "Client must be connected, account and chainId must be initialized",
|
|
3211
3893
|
hint: "Ensure client.connect() has been called and awaited.",
|
|
@@ -3223,6 +3905,8 @@ function createCofhesdkClientBase(opts) {
|
|
|
3223
3905
|
const state = connectStore.getState();
|
|
3224
3906
|
if (state.connected && state.publicClient === publicClient && state.walletClient === walletClient)
|
|
3225
3907
|
return;
|
|
3908
|
+
connectAttemptId += 1;
|
|
3909
|
+
const localAttemptId = connectAttemptId;
|
|
3226
3910
|
updateConnectState({
|
|
3227
3911
|
...InitialConnectStore,
|
|
3228
3912
|
connecting: true
|
|
@@ -3230,6 +3914,8 @@ function createCofhesdkClientBase(opts) {
|
|
|
3230
3914
|
try {
|
|
3231
3915
|
const chainId = await getPublicClientChainID(publicClient);
|
|
3232
3916
|
const account = await getWalletClientAccount(walletClient);
|
|
3917
|
+
if (localAttemptId !== connectAttemptId)
|
|
3918
|
+
return;
|
|
3233
3919
|
updateConnectState({
|
|
3234
3920
|
connected: true,
|
|
3235
3921
|
connecting: false,
|
|
@@ -3240,6 +3926,8 @@ function createCofhesdkClientBase(opts) {
|
|
|
3240
3926
|
walletClient
|
|
3241
3927
|
});
|
|
3242
3928
|
} catch (e) {
|
|
3929
|
+
if (localAttemptId !== connectAttemptId)
|
|
3930
|
+
return;
|
|
3243
3931
|
updateConnectState({
|
|
3244
3932
|
...InitialConnectStore,
|
|
3245
3933
|
connectError: e
|
|
@@ -3247,6 +3935,10 @@ function createCofhesdkClientBase(opts) {
|
|
|
3247
3935
|
throw e;
|
|
3248
3936
|
}
|
|
3249
3937
|
}
|
|
3938
|
+
function disconnect() {
|
|
3939
|
+
connectAttemptId += 1;
|
|
3940
|
+
updateConnectState({ ...InitialConnectStore });
|
|
3941
|
+
}
|
|
3250
3942
|
function encryptInputs(inputs) {
|
|
3251
3943
|
const state = connectStore.getState();
|
|
3252
3944
|
return new EncryptInputsBuilder({
|
|
@@ -3266,16 +3958,28 @@ function createCofhesdkClientBase(opts) {
|
|
|
3266
3958
|
requireConnected: _requireConnected
|
|
3267
3959
|
});
|
|
3268
3960
|
}
|
|
3269
|
-
function
|
|
3961
|
+
function decryptForView(ctHash, utype) {
|
|
3270
3962
|
const state = connectStore.getState();
|
|
3271
|
-
return new
|
|
3963
|
+
return new DecryptForViewBuilder({
|
|
3272
3964
|
ctHash,
|
|
3273
3965
|
utype,
|
|
3274
|
-
chainId: state.chainId
|
|
3275
|
-
account: state.account
|
|
3966
|
+
chainId: state.chainId,
|
|
3967
|
+
account: state.account,
|
|
3276
3968
|
config: opts.config,
|
|
3277
|
-
publicClient: state.publicClient
|
|
3278
|
-
walletClient: state.walletClient
|
|
3969
|
+
publicClient: state.publicClient,
|
|
3970
|
+
walletClient: state.walletClient,
|
|
3971
|
+
requireConnected: _requireConnected
|
|
3972
|
+
});
|
|
3973
|
+
}
|
|
3974
|
+
function decryptForTx(ctHash) {
|
|
3975
|
+
const state = connectStore.getState();
|
|
3976
|
+
return new DecryptForTxBuilder({
|
|
3977
|
+
ctHash,
|
|
3978
|
+
chainId: state.chainId,
|
|
3979
|
+
account: state.account,
|
|
3980
|
+
config: opts.config,
|
|
3981
|
+
publicClient: state.publicClient,
|
|
3982
|
+
walletClient: state.walletClient,
|
|
3279
3983
|
requireConnected: _requireConnected
|
|
3280
3984
|
});
|
|
3281
3985
|
}
|
|
@@ -3284,7 +3988,7 @@ function createCofhesdkClientBase(opts) {
|
|
|
3284
3988
|
const _chainId = chainId ?? state.chainId;
|
|
3285
3989
|
const _account = account ?? state.account;
|
|
3286
3990
|
if (_chainId == null || _account == null) {
|
|
3287
|
-
throw new
|
|
3991
|
+
throw new CofheError({
|
|
3288
3992
|
code: "NOT_CONNECTED" /* NotConnected */,
|
|
3289
3993
|
message: "ChainId or account not available.",
|
|
3290
3994
|
hint: "Ensure client.connect() has been called, or provide chainId and account explicitly.",
|
|
@@ -3351,9 +4055,9 @@ function createCofhesdkClientBase(opts) {
|
|
|
3351
4055
|
const { chainId: _chainId, account: _account } = _getChainIdAndAccount(chainId, account);
|
|
3352
4056
|
return permits.selectActivePermit(_chainId, _account, hash);
|
|
3353
4057
|
},
|
|
3354
|
-
removePermit: async (hash, chainId, account
|
|
4058
|
+
removePermit: async (hash, chainId, account) => {
|
|
3355
4059
|
const { chainId: _chainId, account: _account } = _getChainIdAndAccount(chainId, account);
|
|
3356
|
-
return permits.removePermit(_chainId, _account, hash
|
|
4060
|
+
return permits.removePermit(_chainId, _account, hash);
|
|
3357
4061
|
},
|
|
3358
4062
|
removeActivePermit: async (chainId, account) => {
|
|
3359
4063
|
const { chainId: _chainId, account: _account } = _getChainIdAndAccount(chainId, account);
|
|
@@ -3369,6 +4073,9 @@ function createCofhesdkClientBase(opts) {
|
|
|
3369
4073
|
getSnapshot: connectStore.getState,
|
|
3370
4074
|
subscribe: connectStore.subscribe,
|
|
3371
4075
|
// flags (read-only: reflect snapshot)
|
|
4076
|
+
get connection() {
|
|
4077
|
+
return connectStore.getState();
|
|
4078
|
+
},
|
|
3372
4079
|
get connected() {
|
|
3373
4080
|
return connectStore.getState().connected;
|
|
3374
4081
|
},
|
|
@@ -3378,8 +4085,14 @@ function createCofhesdkClientBase(opts) {
|
|
|
3378
4085
|
// config & platform-specific (read-only)
|
|
3379
4086
|
config: opts.config,
|
|
3380
4087
|
connect,
|
|
4088
|
+
disconnect,
|
|
3381
4089
|
encryptInputs,
|
|
3382
|
-
|
|
4090
|
+
decryptForView,
|
|
4091
|
+
/**
|
|
4092
|
+
* @deprecated Use `decryptForView` instead. Kept for backward compatibility.
|
|
4093
|
+
*/
|
|
4094
|
+
decryptHandle: decryptForView,
|
|
4095
|
+
decryptForTx,
|
|
3383
4096
|
permits: clientPermits
|
|
3384
4097
|
// Add SDK-specific methods below that require connection
|
|
3385
4098
|
// Example:
|
|
@@ -3391,24 +4104,31 @@ function createCofhesdkClientBase(opts) {
|
|
|
3391
4104
|
}
|
|
3392
4105
|
|
|
3393
4106
|
exports.CONNECT_STORE_DEFAULTS = InitialConnectStore;
|
|
3394
|
-
exports.
|
|
3395
|
-
exports.
|
|
3396
|
-
exports.
|
|
4107
|
+
exports.CofheError = CofheError;
|
|
4108
|
+
exports.CofheErrorCode = CofheErrorCode;
|
|
4109
|
+
exports.DecryptForTxBuilder = DecryptForTxBuilder;
|
|
4110
|
+
exports.DecryptForViewBuilder = DecryptForViewBuilder;
|
|
3397
4111
|
exports.EncryptInputsBuilder = EncryptInputsBuilder;
|
|
3398
4112
|
exports.EncryptStep = EncryptStep;
|
|
3399
4113
|
exports.Encryptable = Encryptable;
|
|
3400
4114
|
exports.FheAllUTypes = FheAllUTypes;
|
|
3401
4115
|
exports.FheTypes = FheTypes;
|
|
3402
4116
|
exports.FheUintUTypes = FheUintUTypes;
|
|
4117
|
+
exports.MOCKS_DECRYPT_RESULT_SIGNER_PRIVATE_KEY = MOCKS_DECRYPT_RESULT_SIGNER_PRIVATE_KEY;
|
|
4118
|
+
exports.MOCKS_THRESHOLD_NETWORK_ADDRESS = MOCKS_THRESHOLD_NETWORK_ADDRESS;
|
|
4119
|
+
exports.MOCKS_ZK_VERIFIER_ADDRESS = MOCKS_ZK_VERIFIER_ADDRESS;
|
|
3403
4120
|
exports.MOCKS_ZK_VERIFIER_SIGNER_ADDRESS = MOCKS_ZK_VERIFIER_SIGNER_ADDRESS;
|
|
4121
|
+
exports.MOCKS_ZK_VERIFIER_SIGNER_PRIVATE_KEY = MOCKS_ZK_VERIFIER_SIGNER_PRIVATE_KEY;
|
|
4122
|
+
exports.TASK_MANAGER_ADDRESS = TASK_MANAGER_ADDRESS;
|
|
4123
|
+
exports.TEST_BED_ADDRESS = TEST_BED_ADDRESS;
|
|
3404
4124
|
exports.assertCorrectEncryptedItemInput = assertCorrectEncryptedItemInput;
|
|
3405
|
-
exports.
|
|
3406
|
-
exports.
|
|
4125
|
+
exports.createCofheClientBase = createCofheClientBase;
|
|
4126
|
+
exports.createCofheConfigBase = createCofheConfigBase;
|
|
3407
4127
|
exports.createKeysStore = createKeysStore;
|
|
3408
4128
|
exports.fetchKeys = fetchKeys;
|
|
3409
4129
|
exports.fheTypeToString = fheTypeToString;
|
|
3410
|
-
exports.
|
|
3411
|
-
exports.
|
|
4130
|
+
exports.getCofheConfigItem = getCofheConfigItem;
|
|
4131
|
+
exports.isCofheError = isCofheError;
|
|
3412
4132
|
exports.isEncryptableItem = isEncryptableItem;
|
|
3413
4133
|
exports.isLastEncryptionStep = isLastEncryptionStep;
|
|
3414
4134
|
exports.zkProveWithWorker = zkProveWithWorker;
|