@cofhe/sdk 1.0.0-alpha.0 → 1.1.0-alpha.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/dist/node.cjs CHANGED
@@ -44,6 +44,100 @@ function toBigInt(value) {
44
44
  }
45
45
  }
46
46
 
47
+ // core/error.ts
48
+ var CofheError = class _CofheError extends Error {
49
+ code;
50
+ cause;
51
+ hint;
52
+ context;
53
+ apiErrorCode;
54
+ constructor({ code, message, cause, hint, context, apiErrorCode }) {
55
+ const fullMessage = cause ? `${message} | Caused by: ${cause.message}` : message;
56
+ super(fullMessage);
57
+ this.name = "CofheError";
58
+ this.code = code;
59
+ this.cause = cause;
60
+ this.hint = hint;
61
+ this.context = context;
62
+ this.apiErrorCode = apiErrorCode;
63
+ if (Error.captureStackTrace) {
64
+ Error.captureStackTrace(this, _CofheError);
65
+ }
66
+ }
67
+ /**
68
+ * Creates a CofheError from an unknown error
69
+ * If the error is a CofheError, it is returned unchanged, else a new CofheError is created
70
+ * If a wrapperError is provided, it is used to create the new CofheError, else a default is used
71
+ */
72
+ static fromError(error, wrapperError) {
73
+ if (isCofheError(error))
74
+ return error;
75
+ const cause = error instanceof Error ? error : new Error(`${error}`);
76
+ return new _CofheError({
77
+ code: wrapperError?.code ?? "INTERNAL_ERROR" /* InternalError */,
78
+ message: wrapperError?.message ?? "An internal error occurred",
79
+ hint: wrapperError?.hint,
80
+ context: wrapperError?.context,
81
+ apiErrorCode: wrapperError?.apiErrorCode,
82
+ cause
83
+ });
84
+ }
85
+ /**
86
+ * Serializes the error to JSON string with proper handling of Error objects
87
+ */
88
+ serialize() {
89
+ return bigintSafeJsonStringify({
90
+ name: this.name,
91
+ code: this.code,
92
+ message: this.message,
93
+ hint: this.hint,
94
+ context: this.context,
95
+ apiErrorCode: this.apiErrorCode,
96
+ cause: this.cause ? {
97
+ name: this.cause.name,
98
+ message: this.cause.message,
99
+ stack: this.cause.stack
100
+ } : void 0,
101
+ stack: this.stack
102
+ });
103
+ }
104
+ /**
105
+ * Returns a human-readable string representation of the error
106
+ */
107
+ toString() {
108
+ const codeSuffix = this.apiErrorCode ? ` (api: ${this.apiErrorCode})` : "";
109
+ const parts = [`${this.name} [${this.code}]${codeSuffix}: ${this.message}`];
110
+ if (this.hint) {
111
+ parts.push(`Hint: ${this.hint}`);
112
+ }
113
+ if (this.context && Object.keys(this.context).length > 0) {
114
+ parts.push(`Context: ${bigintSafeJsonStringify(this.context)}`);
115
+ }
116
+ if (this.stack) {
117
+ parts.push(`
118
+ Stack trace:`);
119
+ parts.push(this.stack);
120
+ }
121
+ if (this.cause) {
122
+ parts.push(`
123
+ Caused by: ${this.cause.name}: ${this.cause.message}`);
124
+ if (this.cause.stack) {
125
+ parts.push(this.cause.stack);
126
+ }
127
+ }
128
+ return parts.join("\n");
129
+ }
130
+ };
131
+ var bigintSafeJsonStringify = (value) => {
132
+ return JSON.stringify(value, (key, value2) => {
133
+ if (typeof value2 === "bigint") {
134
+ return `${value2}n`;
135
+ }
136
+ return value2;
137
+ });
138
+ };
139
+ var isCofheError = (error) => error instanceof CofheError;
140
+
47
141
  // acps/sealing.ts
48
142
  var KEY_HEX_LENGTH = 64;
49
143
  var GenerateSealingKey = () => {
@@ -58,9 +152,25 @@ var unsealWithPrivateKey = (privateKey, parsedData) => {
58
152
  const nonce = parsedData.nonce instanceof Uint8Array ? parsedData.nonce : new Uint8Array(parsedData.nonce);
59
153
  const ephemPublicKey = parsedData.public_key instanceof Uint8Array ? parsedData.public_key : new Uint8Array(parsedData.public_key);
60
154
  const dataToDecrypt = parsedData.data instanceof Uint8Array ? parsedData.data : new Uint8Array(parsedData.data);
61
- const decryptedMessage = nacl__default.default.box.open(dataToDecrypt, nonce, ephemPublicKey, fromHexString(privateKey));
155
+ let decryptedMessage;
156
+ let cause;
157
+ try {
158
+ decryptedMessage = nacl__default.default.box.open(dataToDecrypt, nonce, ephemPublicKey, fromHexString(privateKey));
159
+ } catch (e) {
160
+ decryptedMessage = null;
161
+ cause = e instanceof Error ? e : void 0;
162
+ }
62
163
  if (!decryptedMessage) {
63
- throw new Error("Failed to decrypt message");
164
+ throw new CofheError({
165
+ code: "SEAL_OUTPUT_FAILED" /* SealOutputFailed */,
166
+ message: "Failed to unseal decrypt response",
167
+ cause,
168
+ context: {
169
+ dataLength: dataToDecrypt.length,
170
+ nonceLength: nonce.length,
171
+ publicKeyLength: ephemPublicKey.length
172
+ }
173
+ });
64
174
  }
65
175
  return toBigInt(decryptedMessage);
66
176
  };
@@ -378,100 +488,6 @@ var TFHE_RS_ZK_MAX_BITS = 2048;
378
488
  var TFHE_RS_SAFE_SERIALIZATION_SIZE_LIMIT = BigInt(1 << 30);
379
489
  var TFHE_RS_KEY_VERSION = 2;
380
490
 
381
- // core/error.ts
382
- var CofheError = class _CofheError extends Error {
383
- code;
384
- cause;
385
- hint;
386
- context;
387
- apiErrorCode;
388
- constructor({ code, message, cause, hint, context, apiErrorCode }) {
389
- const fullMessage = cause ? `${message} | Caused by: ${cause.message}` : message;
390
- super(fullMessage);
391
- this.name = "CofheError";
392
- this.code = code;
393
- this.cause = cause;
394
- this.hint = hint;
395
- this.context = context;
396
- this.apiErrorCode = apiErrorCode;
397
- if (Error.captureStackTrace) {
398
- Error.captureStackTrace(this, _CofheError);
399
- }
400
- }
401
- /**
402
- * Creates a CofheError from an unknown error
403
- * If the error is a CofheError, it is returned unchanged, else a new CofheError is created
404
- * If a wrapperError is provided, it is used to create the new CofheError, else a default is used
405
- */
406
- static fromError(error, wrapperError) {
407
- if (isCofheError(error))
408
- return error;
409
- const cause = error instanceof Error ? error : new Error(`${error}`);
410
- return new _CofheError({
411
- code: wrapperError?.code ?? "INTERNAL_ERROR" /* InternalError */,
412
- message: wrapperError?.message ?? "An internal error occurred",
413
- hint: wrapperError?.hint,
414
- context: wrapperError?.context,
415
- apiErrorCode: wrapperError?.apiErrorCode,
416
- cause
417
- });
418
- }
419
- /**
420
- * Serializes the error to JSON string with proper handling of Error objects
421
- */
422
- serialize() {
423
- return bigintSafeJsonStringify({
424
- name: this.name,
425
- code: this.code,
426
- message: this.message,
427
- hint: this.hint,
428
- context: this.context,
429
- apiErrorCode: this.apiErrorCode,
430
- cause: this.cause ? {
431
- name: this.cause.name,
432
- message: this.cause.message,
433
- stack: this.cause.stack
434
- } : void 0,
435
- stack: this.stack
436
- });
437
- }
438
- /**
439
- * Returns a human-readable string representation of the error
440
- */
441
- toString() {
442
- const codeSuffix = this.apiErrorCode ? ` (api: ${this.apiErrorCode})` : "";
443
- const parts = [`${this.name} [${this.code}]${codeSuffix}: ${this.message}`];
444
- if (this.hint) {
445
- parts.push(`Hint: ${this.hint}`);
446
- }
447
- if (this.context && Object.keys(this.context).length > 0) {
448
- parts.push(`Context: ${bigintSafeJsonStringify(this.context)}`);
449
- }
450
- if (this.stack) {
451
- parts.push(`
452
- Stack trace:`);
453
- parts.push(this.stack);
454
- }
455
- if (this.cause) {
456
- parts.push(`
457
- Caused by: ${this.cause.name}: ${this.cause.message}`);
458
- if (this.cause.stack) {
459
- parts.push(this.cause.stack);
460
- }
461
- }
462
- return parts.join("\n");
463
- }
464
- };
465
- var bigintSafeJsonStringify = (value) => {
466
- return JSON.stringify(value, (key, value2) => {
467
- if (typeof value2 === "bigint") {
468
- return `${value2}n`;
469
- }
470
- return value2;
471
- });
472
- };
473
- var isCofheError = (error) => error instanceof CofheError;
474
-
475
491
  // core/taskManager.ts
476
492
  var ADDRESS_BOOK_ABI = viem.parseAbi([
477
493
  "function getTm(uint256 id) view returns (address)",
@@ -779,15 +795,22 @@ var getAclServedAddresses = async (publicClient, chainId) => {
779
795
  } catch {
780
796
  return {};
781
797
  }
798
+ let transient = false;
799
+ const readServedAddress = (functionName) => publicClient.readContract({ address: aclAddress, abi: ACL_SERVED_ADDRESSES_ABI, functionName }).catch((err) => {
800
+ if (revertErrorName(err, ACL_SERVED_ADDRESSES_ABI) === void 0)
801
+ transient = true;
802
+ return void 0;
803
+ });
782
804
  const [defaultRevoker, shareRegistry] = await Promise.all([
783
- publicClient.readContract({ address: aclAddress, abi: ACL_SERVED_ADDRESSES_ABI, functionName: "defaultRevokerContract" }).catch(() => void 0),
784
- publicClient.readContract({ address: aclAddress, abi: ACL_SERVED_ADDRESSES_ABI, functionName: "shareRegistry" }).catch(() => void 0)
805
+ readServedAddress("defaultRevokerContract"),
806
+ readServedAddress("shareRegistry")
785
807
  ]);
786
808
  const resolved = {
787
809
  defaultRevoker: defaultRevoker != null && defaultRevoker !== viem.zeroAddress ? defaultRevoker : void 0,
788
810
  shareRegistry: shareRegistry != null && shareRegistry !== viem.zeroAddress ? shareRegistry : void 0
789
811
  };
790
- aclServedAddressesCache.set(chainId, resolved);
812
+ if (!transient)
813
+ aclServedAddressesCache.set(chainId, resolved);
791
814
  return resolved;
792
815
  };
793
816
 
@@ -3234,23 +3257,25 @@ var getBlockRevokerData = async (publicClient) => {
3234
3257
  }
3235
3258
  return revokerData;
3236
3259
  };
3237
- var revokeACP = async (acp, walletClient) => {
3260
+ var prepareRevokeACP = (acp) => {
3238
3261
  if (acp.revokerContract === viem.zeroAddress || acp.revokerData === 0) {
3239
3262
  throw new Error("ACP is not revocable: it has no revoker (revokerContract/revokerData unset)");
3240
3263
  }
3264
+ return {
3265
+ address: acp.revokerContract,
3266
+ abi: ACP_REVOKER_ABI,
3267
+ functionName: "revokeSingle",
3268
+ args: [BigInt(acp.revokerData)]
3269
+ };
3270
+ };
3271
+ var revokeACP = async (acp, walletClient) => {
3272
+ const write = prepareRevokeACP(acp);
3241
3273
  if (walletClient.account == null)
3242
3274
  throw new Error("Missing walletClient account");
3243
3275
  if (walletClient.account.address.toLowerCase() !== acp.issuer.toLowerCase()) {
3244
3276
  throw new Error("Only the acp issuer can revoke it");
3245
3277
  }
3246
- return walletClient.writeContract({
3247
- address: acp.revokerContract,
3248
- abi: ACP_REVOKER_ABI,
3249
- functionName: "revokeSingle",
3250
- args: [BigInt(acp.revokerData)],
3251
- account: walletClient.account,
3252
- chain: walletClient.chain
3253
- });
3278
+ return walletClient.writeContract({ ...write, account: walletClient.account, chain: walletClient.chain });
3254
3279
  };
3255
3280
  var revokeAllACPs = async (walletClient, publicClient, revokerContract) => {
3256
3281
  if (walletClient.account == null)
@@ -3301,28 +3326,36 @@ var metadataOf = (acp, { labels, metadata, appKey }) => {
3301
3326
  }
3302
3327
  return encodeShareMetadata(labels, { issuer: acp.issuer, appKey });
3303
3328
  };
3304
- var shareOnChain = async (acp, walletClient, registry, options = {}) => {
3329
+ var prepareShareOnChain = (acp, registry, options = {}) => {
3305
3330
  if (acp.type !== "sharing") {
3306
3331
  throw new Error(`Cannot share a '${acp.type}' ACP on-chain \u2014 only 'sharing' ACPs are shareable.`);
3307
3332
  }
3308
3333
  if (acp.issuerSignature === "0x") {
3309
3334
  throw new Error("Cannot share an unsigned sharing ACP \u2014 sign it first.");
3310
3335
  }
3336
+ return {
3337
+ write: {
3338
+ address: registry,
3339
+ abi: ACP_SHARE_REGISTRY_ABI,
3340
+ functionName: "share",
3341
+ args: [toChainShare(acp), metadataOf(acp, options)]
3342
+ },
3343
+ shareId: computeShareId(acp)
3344
+ };
3345
+ };
3346
+ var shareOnChain = async (acp, walletClient, registry, options = {}) => {
3347
+ const { write, shareId } = prepareShareOnChain(acp, registry, options);
3311
3348
  if (walletClient.account == null)
3312
3349
  throw new Error("Missing walletClient account");
3313
3350
  if (walletClient.account.address.toLowerCase() !== acp.issuer.toLowerCase()) {
3314
3351
  throw new Error("Only the ACP issuer can share it on-chain");
3315
3352
  }
3316
- const metadata = metadataOf(acp, options);
3317
3353
  const txHash = await walletClient.writeContract({
3318
- address: registry,
3319
- abi: ACP_SHARE_REGISTRY_ABI,
3320
- functionName: "share",
3321
- args: [toChainShare(acp), metadata],
3354
+ ...write,
3322
3355
  account: walletClient.account,
3323
3356
  chain: walletClient.chain ?? null
3324
3357
  });
3325
- return { txHash, shareId: computeShareId(acp) };
3358
+ return { txHash, shareId };
3326
3359
  };
3327
3360
  var toIncomingShare = ({ shareId, share: s, metadata }) => ({
3328
3361
  shareId,
@@ -3357,14 +3390,17 @@ var importFromChain = async (share, publicClient, walletClient, importOptions =
3357
3390
  const { shareId: _shareId, appKey: _appKey, ...options } = share;
3358
3391
  return importShared({ ...options, type: "sharing" }, publicClient, walletClient, importOptions);
3359
3392
  };
3393
+ var prepareRemoveShare = (shareId, registry) => ({
3394
+ address: registry,
3395
+ abi: ACP_SHARE_REGISTRY_ABI,
3396
+ functionName: "removeShare",
3397
+ args: [shareId]
3398
+ });
3360
3399
  var removeShareOnChain = async (shareId, walletClient, registry) => {
3361
3400
  if (walletClient.account == null)
3362
3401
  throw new Error("Missing walletClient account");
3363
3402
  return walletClient.writeContract({
3364
- address: registry,
3365
- abi: ACP_SHARE_REGISTRY_ABI,
3366
- functionName: "removeShare",
3367
- args: [shareId],
3403
+ ...prepareRemoveShare(shareId, registry),
3368
3404
  account: walletClient.account,
3369
3405
  chain: walletClient.chain ?? null
3370
3406
  });
@@ -3391,14 +3427,17 @@ var acps = {
3391
3427
  selectActiveACP,
3392
3428
  removeActiveACP,
3393
3429
  revokeACP,
3430
+ prepareRevokeACP,
3394
3431
  revokeAllACPs,
3395
3432
  isACPRevoked,
3396
3433
  checkAccess,
3397
3434
  shareOnChain,
3435
+ prepareShareOnChain,
3398
3436
  getIncomingShares,
3399
3437
  getShareFromChain,
3400
3438
  importFromChain,
3401
3439
  removeShareOnChain,
3440
+ prepareRemoveShare,
3402
3441
  computeShareId,
3403
3442
  applyACPDefaultsFromChain,
3404
3443
  getAclServedAddresses,
@@ -5174,6 +5213,12 @@ function createCofheClientBase(opts) {
5174
5213
  });
5175
5214
  }
5176
5215
  };
5216
+ const _requireIssuer = (acp, what) => {
5217
+ const sender = connectStore.getState().walletClient?.account?.address;
5218
+ if (sender == null || sender.toLowerCase() !== acp.issuer.toLowerCase()) {
5219
+ throw new Error(`Only the acp issuer can ${what}`);
5220
+ }
5221
+ };
5177
5222
  async function connect(publicClient, walletClient) {
5178
5223
  const state = connectStore.getState();
5179
5224
  if (state.connected && state.publicClient === publicClient && state.walletClient === walletClient)
@@ -5341,6 +5386,11 @@ function createCofheClientBase(opts) {
5341
5386
  const { walletClient } = connectStore.getState();
5342
5387
  return acps.revokeACP(acp, walletClient);
5343
5388
  },
5389
+ prepareRevokeACP: (acp) => {
5390
+ _requireConnected();
5391
+ _requireIssuer(acp, "revoke it");
5392
+ return acps.prepareRevokeACP(acp);
5393
+ },
5344
5394
  revokeAllACPs: async (revokerContract) => {
5345
5395
  _requireConnected();
5346
5396
  const { publicClient, walletClient } = connectStore.getState();
@@ -5364,6 +5414,21 @@ function createCofheClientBase(opts) {
5364
5414
  const sharingRegistry = await _resolveSharingRegistry(publicClient, chainId);
5365
5415
  return acps.shareOnChain(acp, walletClient, sharingRegistry, { ...withAppKey(), ...options });
5366
5416
  },
5417
+ prepareShareOnChain: async (acp, options) => {
5418
+ _requireConnected();
5419
+ _requireIssuer(acp, "share it on-chain");
5420
+ const { publicClient } = connectStore.getState();
5421
+ const chainId = await publicClient.getChainId();
5422
+ const sharingRegistry = await _resolveSharingRegistry(publicClient, chainId);
5423
+ return acps.prepareShareOnChain(acp, sharingRegistry, { ...withAppKey(), ...options });
5424
+ },
5425
+ prepareRemoveShare: async (shareId) => {
5426
+ _requireConnected();
5427
+ const { publicClient } = connectStore.getState();
5428
+ const chainId = await publicClient.getChainId();
5429
+ const sharingRegistry = await _resolveSharingRegistry(publicClient, chainId);
5430
+ return acps.prepareRemoveShare(shareId, sharingRegistry);
5431
+ },
5367
5432
  getIncomingShares: async () => {
5368
5433
  _requireConnected();
5369
5434
  const { publicClient, walletClient } = connectStore.getState();
package/dist/node.d.cts CHANGED
@@ -1,8 +1,8 @@
1
- import { C as CofheInputConfig, a as CofheConfig, b as CofheClient } from './clientTypes-C0A9ji5O.cjs';
1
+ import { C as CofheInputConfig, a as CofheConfig, b as CofheClient } from './clientTypes-RXwLVWou.cjs';
2
2
  import 'viem';
3
3
  import './types-C07FK-cL.cjs';
4
4
  import 'zod';
5
- import './onchain-utils-D9Z33IP7.cjs';
5
+ import './onchain-utils-Ns56cBm0.cjs';
6
6
  import 'zustand/vanilla';
7
7
 
8
8
  /**
package/dist/node.d.ts CHANGED
@@ -1,8 +1,8 @@
1
- import { C as CofheInputConfig, a as CofheConfig, b as CofheClient } from './clientTypes-CcU5WvdV.js';
1
+ import { C as CofheInputConfig, a as CofheConfig, b as CofheClient } from './clientTypes-CnslFzxB.js';
2
2
  import 'viem';
3
3
  import './types-C07FK-cL.js';
4
4
  import 'zod';
5
- import './onchain-utils-D9Z33IP7.js';
5
+ import './onchain-utils-Ns56cBm0.js';
6
6
  import 'zustand/vanilla';
7
7
 
8
8
  /**
package/dist/node.js CHANGED
@@ -1,8 +1,8 @@
1
- import { createCofheConfigBase, createCofheClientBase } from './chunk-OL3DZN7A.js';
1
+ import { createCofheConfigBase, createCofheClientBase } from './chunk-2EO4JSR7.js';
2
2
  import './chunk-UKQAJK4N.js';
3
- import './chunk-BQWHPIYU.js';
4
- import { fromHexString } from './chunk-6ZW76ZKB.js';
5
- import { TFHE_RS_SAFE_SERIALIZATION_SIZE_LIMIT } from './chunk-XQ32JG3T.js';
3
+ import './chunk-3L2IVPMI.js';
4
+ import { fromHexString } from './chunk-WJGTPW7K.js';
5
+ import { TFHE_RS_SAFE_SERIALIZATION_SIZE_LIMIT } from './chunk-J23FYAI2.js';
6
6
  import { promises } from 'fs';
7
7
  import { join } from 'path';
8
8
  import { init_panic_hook, ProvenCompactCiphertextList, CompactPkeCrs, TfheCompactPublicKey } from 'node-tfhe';