@cofhe/sdk 0.6.0 → 0.7.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.
Files changed (114) hide show
  1. package/CHANGELOG.md +49 -0
  2. package/acps/acp.ts +411 -0
  3. package/acps/index.ts +70 -0
  4. package/{permits → acps}/onchain-utils.ts +49 -24
  5. package/acps/sealing.ts +90 -0
  6. package/acps/signature.ts +89 -0
  7. package/acps/store.ts +172 -0
  8. package/acps/test/acp.test.ts +615 -0
  9. package/acps/test/localstorage.test.ts +105 -0
  10. package/acps/test/sealing.test.ts +77 -0
  11. package/acps/test/store.test.ts +88 -0
  12. package/acps/test/validation.test.ts +361 -0
  13. package/acps/test-utils.ts +32 -0
  14. package/acps/types.ts +252 -0
  15. package/acps/validation.ts +392 -0
  16. package/adapters/test/ethers5.test.ts +4 -1
  17. package/adapters/test/ethers6.test.ts +4 -1
  18. package/adapters/test/wagmi.test.ts +5 -2
  19. package/chains/chains/stagingCofhe.ts +21 -0
  20. package/chains/index.ts +3 -1
  21. package/chains/test/chains.test.ts +2 -1
  22. package/core/acps.ts +625 -0
  23. package/core/client.ts +136 -39
  24. package/core/clientTypes.ts +52 -41
  25. package/core/config.ts +66 -5
  26. package/core/debug.ts +72 -0
  27. package/core/decrypt/MockThresholdNetworkAbi.ts +20 -11
  28. package/core/decrypt/apiError.ts +104 -0
  29. package/core/decrypt/cofheMocksDecryptForTx.ts +11 -11
  30. package/core/decrypt/cofheMocksDecryptForView.ts +7 -7
  31. package/core/decrypt/decryptForTxBuilder.ts +102 -102
  32. package/core/decrypt/decryptForViewBuilder.ts +90 -90
  33. package/core/decrypt/submitRetry.ts +38 -30
  34. package/core/decrypt/tnDecryptV1.ts +5 -5
  35. package/core/decrypt/tnDecryptV2.ts +45 -34
  36. package/core/decrypt/tnSealOutputV1.ts +4 -3
  37. package/core/decrypt/tnSealOutputV2.ts +44 -31
  38. package/core/encrypt/cofheMocksZkVerifySign.ts +59 -74
  39. package/core/encrypt/encryptInputsBuilder.ts +86 -52
  40. package/core/encrypt/zkPackProveVerify.ts +25 -18
  41. package/core/error.ts +34 -6
  42. package/core/index.ts +14 -14
  43. package/core/test/acpDefaults.test.ts +52 -0
  44. package/core/test/acps.test.ts +596 -0
  45. package/core/test/apiError.test.ts +130 -0
  46. package/core/test/client.test.ts +22 -19
  47. package/core/test/config.test.ts +25 -5
  48. package/core/test/decrypt.test.ts +40 -35
  49. package/core/test/decryptBuilders.test.ts +68 -68
  50. package/core/test/decryptErrorCodes.test.ts +217 -0
  51. package/core/test/encryptInputsBuilder.test.ts +72 -41
  52. package/core/test/pollCallbacks.test.ts +89 -18
  53. package/core/test/stagingRedirect.ts +18 -0
  54. package/core/test/submitRetry.test.ts +182 -0
  55. package/core/types.ts +9 -69
  56. package/dist/acp-Wi6isVQI.d.cts +407 -0
  57. package/dist/acp-Wi6isVQI.d.ts +407 -0
  58. package/dist/acps.cjs +1081 -0
  59. package/dist/acps.d.cts +480 -0
  60. package/dist/acps.d.ts +480 -0
  61. package/dist/acps.js +2 -0
  62. package/dist/chains.cjs +14 -1
  63. package/dist/chains.d.cts +30 -1
  64. package/dist/chains.d.ts +30 -1
  65. package/dist/chains.js +1 -1
  66. package/dist/{chunk-PE5V5CCV.js → chunk-43USWPEH.js} +1000 -604
  67. package/dist/{chunk-MTRAXQXC.js → chunk-N6IDQRRU.js} +14 -2
  68. package/dist/chunk-Q7CBWGQX.js +1029 -0
  69. package/dist/{clientTypes-CyUvRRzA.d.ts → clientTypes-BN3nbzYM.d.ts} +342 -165
  70. package/dist/{clientTypes-BDy1qIBu.d.cts → clientTypes-CYZjFznO.d.cts} +342 -165
  71. package/dist/core.cjs +1431 -1026
  72. package/dist/core.d.cts +55 -10
  73. package/dist/core.d.ts +55 -10
  74. package/dist/core.js +3 -3
  75. package/dist/node.cjs +1356 -976
  76. package/dist/node.d.cts +2 -2
  77. package/dist/node.d.ts +2 -2
  78. package/dist/node.js +3 -3
  79. package/dist/web.cjs +1356 -976
  80. package/dist/web.d.cts +2 -2
  81. package/dist/web.d.ts +2 -2
  82. package/dist/web.js +3 -3
  83. package/node/test/inherited.test.ts +75 -65
  84. package/node/test/tfheinit.test.ts +23 -8
  85. package/package.json +6 -6
  86. package/web/test/client.web.test.ts +5 -1
  87. package/web/test/inherited.web.test.ts +75 -65
  88. package/web/test/tfheinit.web.test.ts +14 -5
  89. package/web/test/worker.config.web.test.ts +38 -23
  90. package/web/test/worker.output.web.test.ts +25 -24
  91. package/core/encrypt/encryptUtils.ts +0 -67
  92. package/core/permits.ts +0 -206
  93. package/core/test/permits.test.ts +0 -534
  94. package/dist/chunk-VB62WYPL.js +0 -978
  95. package/dist/permit-DnVMDT5h.d.cts +0 -376
  96. package/dist/permit-DnVMDT5h.d.ts +0 -376
  97. package/dist/permits.cjs +0 -1026
  98. package/dist/permits.d.cts +0 -353
  99. package/dist/permits.d.ts +0 -353
  100. package/dist/permits.js +0 -2
  101. package/permits/index.ts +0 -68
  102. package/permits/permit.ts +0 -385
  103. package/permits/sealing.ts +0 -131
  104. package/permits/signature.ts +0 -79
  105. package/permits/store.ts +0 -157
  106. package/permits/test/localstorage.test.ts +0 -113
  107. package/permits/test/permit.test.ts +0 -557
  108. package/permits/test/sealing.test.ts +0 -84
  109. package/permits/test/store.test.ts +0 -88
  110. package/permits/test/validation.test.ts +0 -361
  111. package/permits/test-utils.ts +0 -28
  112. package/permits/types.ts +0 -204
  113. package/permits/validation.ts +0 -327
  114. /package/{permits → acps}/utils.ts +0 -0
@@ -1,557 +0,0 @@
1
- import { describe, it, expect } from 'vitest';
2
- import {
3
- PermitUtils,
4
- type CreateSelfPermitOptions,
5
- type CreateSharingPermitOptions,
6
- type ImportSharedPermitOptions,
7
- } from '../index.js';
8
- import { createPublicClient, createWalletClient, http, type PublicClient, type WalletClient } from 'viem';
9
- import { arbitrumSepolia } from 'viem/chains';
10
- import { privateKeyToAccount } from 'viem/accounts';
11
-
12
- // Test private keys (well-known test keys from Anvil/Hardhat)
13
- const BOB_PRIVATE_KEY = '0xac0974bec39a17e36ba4a6b4d238ff944bacb478cbed5efcae784d7bf4f2ff80'; // Bob - always issuer
14
- const ALICE_PRIVATE_KEY = '0x59c6995e998f97a5a0044966f0945389dc9e86dae88c7a8412f4603b6b78690d'; // Alice - always recipient
15
-
16
- // Create real viem clients for Arbitrum Sepolia
17
- const publicClient: PublicClient = createPublicClient({
18
- chain: arbitrumSepolia,
19
- transport: http(),
20
- });
21
-
22
- const bobWalletClient: WalletClient = createWalletClient({
23
- chain: arbitrumSepolia,
24
- transport: http(),
25
- account: privateKeyToAccount(BOB_PRIVATE_KEY),
26
- });
27
-
28
- const aliceWalletClient: WalletClient = createWalletClient({
29
- chain: arbitrumSepolia,
30
- transport: http(),
31
- account: privateKeyToAccount(ALICE_PRIVATE_KEY),
32
- });
33
-
34
- // Helper to get the wallet addresses
35
- const bobAddress = bobWalletClient.account!.address;
36
- const aliceAddress = aliceWalletClient.account!.address;
37
-
38
- describe('PermitUtils Tests', () => {
39
- describe('createSelf', () => {
40
- it('should create a self permit with valid options', async () => {
41
- const options: CreateSelfPermitOptions = {
42
- type: 'self',
43
- issuer: bobAddress,
44
- name: 'Test Permit',
45
- };
46
-
47
- const permit = PermitUtils.createSelf(options);
48
-
49
- expect(permit.hash).toBe(PermitUtils.getHash(permit));
50
- expect(permit.type).toBe('self');
51
- expect(permit.name).toBe('Test Permit');
52
- expect(permit.type).toBe('self');
53
- expect(permit.issuer).toBe(bobAddress);
54
- expect(permit.sealingPair).toBeDefined();
55
- expect(permit.sealingPair.privateKey).toBeDefined();
56
- expect(permit.sealingPair.publicKey).toBeDefined();
57
-
58
- // Should not be signed yet
59
- expect(permit.issuerSignature).toBe('0x');
60
- expect(permit.recipientSignature).toBe('0x');
61
- });
62
-
63
- it('should throw error for invalid options', async () => {
64
- const options: CreateSelfPermitOptions = {
65
- type: 'self',
66
- issuer: 'invalid-address',
67
- name: 'Test Permit',
68
- };
69
-
70
- expect(() => PermitUtils.createSelf(options)).toThrowError();
71
- });
72
- });
73
-
74
- describe('createSharing', () => {
75
- it('should create a sharing permit with valid options', async () => {
76
- const options: CreateSharingPermitOptions = {
77
- type: 'sharing',
78
- issuer: bobAddress,
79
- recipient: aliceAddress,
80
- name: 'Test Sharing Permit',
81
- };
82
-
83
- const permit = PermitUtils.createSharing(options);
84
-
85
- expect(permit.hash).toBe(PermitUtils.getHash(permit));
86
- expect(permit.type).toBe('sharing');
87
- expect(permit.name).toBe('Test Sharing Permit');
88
- expect(permit.type).toBe('sharing');
89
- expect(permit.issuer).toBe(bobAddress);
90
- expect(permit.recipient).toBe(aliceAddress);
91
- expect(permit.sealingPair).toBeDefined();
92
- expect(permit.sealingPair.privateKey).toBeDefined();
93
- expect(permit.sealingPair.publicKey).toBeDefined();
94
-
95
- // Should not be signed yet
96
- expect(permit.issuerSignature).toBe('0x');
97
- expect(permit.recipientSignature).toBe('0x');
98
- });
99
-
100
- it('should throw error for invalid recipient', async () => {
101
- const options: CreateSharingPermitOptions = {
102
- type: 'sharing',
103
- issuer: bobAddress,
104
- recipient: 'invalid-address',
105
- name: 'Test Sharing Permit',
106
- };
107
-
108
- expect(() => PermitUtils.createSharing(options)).toThrow();
109
- });
110
- });
111
-
112
- describe('importShared', () => {
113
- it('should import a shared permit with valid options', async () => {
114
- const options: ImportSharedPermitOptions = {
115
- issuer: bobAddress,
116
- expiration: Math.floor(Date.now() / 1000) + 3600, // 1 hour from now
117
- recipient: aliceAddress,
118
- issuerSignature: '0x1234567890abcdef',
119
- name: 'Test Import Permit',
120
- };
121
-
122
- const permit = PermitUtils.importShared(options);
123
-
124
- expect(permit.hash).toBe(PermitUtils.getHash(permit));
125
- expect(permit.type).toBe('recipient');
126
- expect(permit.name).toBe('Test Import Permit');
127
- expect(permit.issuer).toBe(bobAddress);
128
- expect(permit.recipient).toBe(aliceAddress);
129
- expect(permit.issuerSignature).toBe('0x1234567890abcdef');
130
- expect(permit.sealingPair).toBeDefined();
131
- expect(permit.sealingPair.privateKey).toBeDefined();
132
- expect(permit.sealingPair.publicKey).toBeDefined();
133
-
134
- // Should not be signed yet
135
- expect(permit.recipientSignature).toBe('0x');
136
- });
137
-
138
- it('should import a shared permit with valid options as string', async () => {
139
- const options: ImportSharedPermitOptions = {
140
- issuer: bobAddress,
141
- expiration: Math.floor(Date.now() / 1000) + 3600, // 1 hour from now
142
- recipient: aliceAddress,
143
- issuerSignature: '0x1234567890abcdef',
144
- };
145
-
146
- const stringOptions = JSON.stringify(options);
147
-
148
- const permit = PermitUtils.importShared(stringOptions);
149
-
150
- expect(permit.type).toBe('recipient');
151
- });
152
-
153
- it('should throw error for invalid permit type', async () => {
154
- const options = {
155
- type: 'self',
156
- issuer: bobAddress,
157
- recipient: aliceAddress,
158
- issuerSignature: '0x1234567890abcdef',
159
- } as unknown as ImportSharedPermitOptions;
160
-
161
- expect(() => PermitUtils.importShared(options)).toThrow();
162
-
163
- const options2 = {
164
- type: 'recipient',
165
- issuer: bobAddress,
166
- recipient: aliceAddress,
167
- issuerSignature: '0x1234567890abcdef',
168
- } as unknown as ImportSharedPermitOptions;
169
-
170
- expect(() => PermitUtils.importShared(options2)).toThrow();
171
- });
172
-
173
- it('should throw error for missing issuerSignature', async () => {
174
- const options: ImportSharedPermitOptions = {
175
- issuer: bobAddress,
176
- expiration: Math.floor(Date.now() / 1000) + 3600, // 1 hour from now
177
- recipient: aliceAddress,
178
- issuerSignature: '0x', // Invalid empty signature
179
- name: 'Test Import Permit',
180
- };
181
-
182
- expect(() => PermitUtils.importShared(options)).toThrow();
183
- });
184
-
185
- it('should throw error for missing expiration', async () => {
186
- const options = {
187
- issuer: bobAddress,
188
- recipient: aliceAddress,
189
- issuerSignature: '0x1234567890abcdef',
190
- } as unknown as ImportSharedPermitOptions;
191
- expect(() => PermitUtils.importShared(options)).toThrow();
192
- });
193
- });
194
-
195
- describe('createSelfAndSign', () => {
196
- it('should create and sign a self permit', async () => {
197
- const options: CreateSelfPermitOptions = {
198
- issuer: bobAddress,
199
- name: 'Test Permit',
200
- };
201
-
202
- const permit = await PermitUtils.createSelfAndSign(options, publicClient, bobWalletClient);
203
-
204
- expect(permit.type).toBe('self');
205
- expect(permit.issuerSignature).toBeDefined();
206
- expect(permit.issuerSignature).not.toBe('0x');
207
- expect(permit.recipientSignature).toBe('0x');
208
- expect(permit._signedDomain).toBeDefined();
209
- });
210
- });
211
-
212
- describe('createSharingAndSign', () => {
213
- it('should create and sign a sharing permit', async () => {
214
- const options: CreateSharingPermitOptions = {
215
- issuer: bobAddress,
216
- recipient: aliceAddress,
217
- name: 'Test Sharing Permit',
218
- };
219
-
220
- const permit = await PermitUtils.createSharingAndSign(options, publicClient, bobWalletClient);
221
-
222
- expect(permit.type).toBe('sharing');
223
- expect(permit.issuerSignature).toBeDefined();
224
- expect(permit.issuerSignature).not.toBe('0x');
225
- expect(permit.recipientSignature).toBe('0x');
226
- expect(permit._signedDomain).toBeDefined();
227
- });
228
- });
229
-
230
- describe('importSharedAndSign', () => {
231
- it('should import and sign a shared permit', async () => {
232
- const options: ImportSharedPermitOptions = {
233
- issuer: bobAddress,
234
- recipient: aliceAddress,
235
- expiration: Math.floor(Date.now() / 1000) + 3600, // 1 hour from now
236
- issuerSignature: '0x1234567890abcdef',
237
- name: 'Test Import Permit',
238
- };
239
-
240
- const permit = await PermitUtils.importSharedAndSign(options, publicClient, aliceWalletClient);
241
-
242
- expect(permit.type).toBe('recipient');
243
- expect(permit.recipientSignature).toBeDefined();
244
- expect(permit.recipientSignature).not.toBe('0x');
245
- expect(permit._signedDomain).toBeDefined();
246
- });
247
-
248
- it('should import and sign a shared permit string', async () => {
249
- const options: ImportSharedPermitOptions = {
250
- issuer: bobAddress,
251
- recipient: aliceAddress,
252
- expiration: Math.floor(Date.now() / 1000) + 3600, // 1 hour from now
253
- issuerSignature: '0x1234567890abcdef',
254
- };
255
-
256
- const stringOptions = JSON.stringify(options);
257
-
258
- const permit = await PermitUtils.importSharedAndSign(stringOptions, publicClient, aliceWalletClient);
259
-
260
- expect(permit.type).toBe('recipient');
261
- expect(permit.recipientSignature).toBeDefined();
262
- expect(permit.recipientSignature).not.toBe('0x');
263
- expect(permit._signedDomain).toBeDefined();
264
- });
265
-
266
- it('should import and sign a shared permit json object', async () => {
267
- const options: ImportSharedPermitOptions = {
268
- issuer: bobAddress,
269
- recipient: aliceAddress,
270
- expiration: Math.floor(Date.now() / 1000) + 3600, // 1 hour from now
271
- issuerSignature: '0x1234567890abcdef',
272
- };
273
-
274
- const jsonOptions = JSON.parse(JSON.stringify(options));
275
-
276
- const permit = await PermitUtils.importSharedAndSign(jsonOptions, publicClient, aliceWalletClient);
277
-
278
- expect(permit.type).toBe('recipient');
279
- expect(permit.recipientSignature).toBeDefined();
280
- expect(permit.recipientSignature).not.toBe('0x');
281
- expect(permit._signedDomain).toBeDefined();
282
- });
283
- });
284
-
285
- describe('sign', () => {
286
- it('should sign a self permit', async () => {
287
- const permit = PermitUtils.createSelf({
288
- issuer: bobAddress,
289
- name: 'Test Permit',
290
- });
291
-
292
- const signedPermit = await PermitUtils.sign(permit, publicClient, bobWalletClient);
293
-
294
- expect(signedPermit.type).toBe('self');
295
- expect(signedPermit.issuerSignature).toBeDefined();
296
- expect(signedPermit.issuerSignature).not.toBe('0x');
297
- expect(signedPermit._signedDomain).toBeDefined();
298
- });
299
-
300
- it('should sign a recipient permit', async () => {
301
- const permit = PermitUtils.importShared({
302
- issuer: bobAddress,
303
- recipient: aliceAddress,
304
- expiration: Math.floor(Date.now() / 1000) + 3600, // 1 hour from now
305
- issuerSignature: '0x1111111111111111111111111111111111111111111111111111111111111111',
306
- name: 'Test Permit',
307
- });
308
-
309
- const signedPermit = await PermitUtils.sign(permit, publicClient, aliceWalletClient);
310
-
311
- expect(signedPermit.recipientSignature).toBeDefined();
312
- expect(signedPermit.recipientSignature).not.toBe('0x');
313
- expect(signedPermit._signedDomain).toBeDefined();
314
- });
315
-
316
- it('should throw error for undefined signer', async () => {
317
- const permit = PermitUtils.createSelf({
318
- issuer: bobAddress,
319
- name: 'Test Permit',
320
- });
321
-
322
- await expect(
323
- // @ts-expect-error - undefined signer
324
- PermitUtils.sign(permit, publicClient, undefined)
325
- ).rejects.toThrow();
326
- });
327
- });
328
-
329
- describe('serialize/deserialize', () => {
330
- it('should serialize and deserialize a permit', async () => {
331
- const originalPermit = PermitUtils.createSelf({
332
- issuer: bobAddress,
333
- name: 'Test Permit',
334
- });
335
-
336
- const serialized = PermitUtils.serialize(originalPermit);
337
- const deserialized = PermitUtils.deserialize(serialized);
338
-
339
- expect(deserialized.type).toBe('self');
340
- expect(deserialized.name).toBe(originalPermit.name);
341
- expect(deserialized.type).toBe(originalPermit.type);
342
- expect(deserialized.issuer).toBe(originalPermit.issuer);
343
- expect(deserialized.sealingPair.privateKey).toBe(originalPermit.sealingPair.privateKey);
344
- expect(deserialized.sealingPair.publicKey).toBe(originalPermit.sealingPair.publicKey);
345
- });
346
- });
347
-
348
- describe('getPermission', () => {
349
- it('should extract permission from permit', async () => {
350
- const permit = await PermitUtils.createSelfAndSign(
351
- {
352
- issuer: bobAddress,
353
- name: 'Test Permit',
354
- },
355
- publicClient,
356
- bobWalletClient
357
- );
358
-
359
- const permission = PermitUtils.getPermission(permit);
360
-
361
- expect(permission.issuer).toBe(permit.issuer);
362
- expect(permission.sealingKey).toBe(`0x${permit.sealingPair.publicKey}`);
363
- expect(permission).not.toHaveProperty('name');
364
- expect(permission).not.toHaveProperty('type');
365
- });
366
- });
367
-
368
- describe('getHash', () => {
369
- it('should generate consistent hash for same permit data', async () => {
370
- const expiration = Math.floor(Date.now() / 1000) + 3600; // 1 hour from now
371
- const permit1 = PermitUtils.createSelf({
372
- expiration,
373
- issuer: bobAddress,
374
- name: 'Test Permit',
375
- });
376
-
377
- const permit2 = PermitUtils.createSelf({
378
- expiration,
379
- issuer: bobAddress,
380
- name: 'Test Permit',
381
- });
382
-
383
- expect(permit1.hash).toBe(permit2.hash);
384
- });
385
- });
386
-
387
- describe('export', () => {
388
- it('should export permit data without sensitive fields', async () => {
389
- const permit = PermitUtils.createSelf({
390
- issuer: bobAddress,
391
- name: 'Test Permit',
392
- });
393
-
394
- const exported = PermitUtils.export(permit);
395
- const parsed = JSON.parse(exported);
396
-
397
- expect(parsed.name).toBe('Test Permit');
398
- expect(parsed.issuer).toBe(bobAddress);
399
- expect(parsed).not.toHaveProperty('sealingPair');
400
- expect(parsed).not.toHaveProperty('issuerSignature');
401
- });
402
-
403
- it('should export sharing permit data with recipient and issuerSignature', async () => {
404
- const permit = await PermitUtils.createSharingAndSign(
405
- {
406
- issuer: bobAddress,
407
- recipient: aliceAddress,
408
- name: 'Test Sharing Permit',
409
- },
410
- publicClient,
411
- bobWalletClient
412
- );
413
-
414
- const exported = PermitUtils.export(permit);
415
- const parsed = JSON.parse(exported);
416
-
417
- expect(parsed.name).toBe('Test Sharing Permit');
418
- expect(parsed.type).toBe('sharing');
419
- expect(parsed.issuer).toBe(bobAddress);
420
- expect(parsed.recipient).toBe(aliceAddress);
421
- expect(parsed.issuerSignature).toBeDefined();
422
- expect(parsed.issuerSignature).not.toBe('0x');
423
- expect(parsed).not.toHaveProperty('sealingPair');
424
- });
425
- });
426
-
427
- describe('updateName', () => {
428
- it('should update permit name immutably', async () => {
429
- const permit = PermitUtils.createSelf({
430
- issuer: bobAddress,
431
- name: 'Original Name',
432
- });
433
-
434
- const updatedPermit = PermitUtils.updateName(permit, 'New Name');
435
-
436
- expect(updatedPermit.name).toBe('New Name');
437
- expect(permit.name).toBe('Original Name'); // Original should be unchanged
438
- expect(updatedPermit).not.toBe(permit); // Should be a new object
439
- });
440
- });
441
-
442
- describe('validation helpers', () => {
443
- it('should check if permit is expired', async () => {
444
- const expiredPermit = PermitUtils.createSelf({
445
- issuer: bobAddress,
446
- name: 'Test Permit',
447
- expiration: Math.floor(Date.now() / 1000) - 3600, // 1 hour ago
448
- });
449
-
450
- const validPermit = PermitUtils.createSelf({
451
- issuer: bobAddress,
452
- name: 'Test Permit',
453
- expiration: Math.floor(Date.now() / 1000) + 3600, // 1 hour from now
454
- });
455
-
456
- expect(PermitUtils.isExpired(expiredPermit)).toBe(true);
457
- expect(PermitUtils.isExpired(validPermit)).toBe(false);
458
- });
459
-
460
- it('should check if permit is signed', async () => {
461
- const unsignedPermit = PermitUtils.createSelf({
462
- issuer: bobAddress,
463
- name: 'Test Permit',
464
- });
465
-
466
- const signedPermit = await PermitUtils.sign(unsignedPermit, publicClient, bobWalletClient);
467
-
468
- expect(PermitUtils.isSigned(unsignedPermit)).toBe(false);
469
- expect(PermitUtils.isSigned(signedPermit)).toBe(true);
470
- });
471
-
472
- it('should check overall validity', async () => {
473
- const validPermit = PermitUtils.createSelf({
474
- issuer: bobAddress,
475
- name: 'Test Permit',
476
- expiration: Math.floor(Date.now() / 1000) + 3600,
477
- });
478
-
479
- const signedPermit = await PermitUtils.sign(validPermit, publicClient, bobWalletClient);
480
-
481
- const validation = PermitUtils.isValid(signedPermit);
482
- expect(validation.valid).toBe(true);
483
- expect(validation.error).toBeNull();
484
- });
485
-
486
- it('should throw on validate() for expired signed permit', async () => {
487
- const expiredPermit = PermitUtils.createSelf({
488
- issuer: bobAddress,
489
- name: 'Expired Permit',
490
- expiration: Math.floor(Date.now() / 1000) - 3600,
491
- });
492
-
493
- const signedExpiredPermit = await PermitUtils.sign(expiredPermit, publicClient, bobWalletClient);
494
- expect(() => PermitUtils.validate(signedExpiredPermit)).toThrow('Permit is expired');
495
- });
496
- });
497
-
498
- describe('real contract interactions', () => {
499
- it('should fetch EIP712 domain from real Arbitrum Sepolia contract', async () => {
500
- // This test uses the real public client to fetch actual contract data
501
- const domain = await PermitUtils.fetchEIP712Domain(publicClient);
502
-
503
- expect(domain).toBeDefined();
504
- expect(domain.name).toBeDefined();
505
- expect(domain.version).toBeDefined();
506
- expect(domain.chainId).toBeDefined();
507
- expect(domain.verifyingContract).toBeDefined();
508
- expect(domain.verifyingContract).toMatch(/^0x[a-fA-F0-9]{40}$/); // Valid Ethereum address
509
- }, 10000); // 10 second timeout for network call
510
-
511
- it('should check signed domain validity with real contract data', async () => {
512
- const permit = PermitUtils.createSelf({
513
- type: 'self',
514
- issuer: bobAddress,
515
- name: 'Test Permit',
516
- });
517
-
518
- // Sign the permit to get a domain
519
- const signedPermit = await PermitUtils.sign(permit, publicClient, bobWalletClient);
520
-
521
- // Check if the signed domain is valid against the real contract
522
- const isValid = await PermitUtils.checkSignedDomainValid(signedPermit, publicClient);
523
-
524
- expect(typeof isValid).toBe('boolean');
525
- }, 10000); // 10 second timeout for network call
526
-
527
- // TODO: Uncomment when updated ACL with checkPermitValidity function is deployed
528
-
529
- // it('should check permit validity on chain with real contract data', async () => {
530
- // const permit = PermitUtils.createSelf({
531
- // type: 'self',
532
- // issuer: bobAddress,
533
- // name: 'Test Permit',
534
- // });
535
-
536
- // const signedPermit = await PermitUtils.sign(permit, publicClient, bobWalletClient);
537
-
538
- // const isValid = await PermitUtils.checkValidityOnChain(signedPermit, publicClient);
539
-
540
- // expect(typeof isValid).toBe('boolean');
541
- // expect(isValid).toBe(true);
542
-
543
- // const permitInvalid = PermitUtils.createSelf({
544
- // type: 'self',
545
- // issuer: bobAddress,
546
- // name: 'Test Permit',
547
- // expiration: Math.floor(Date.now() / 1000) - 3600, // 1 hour ago
548
- // });
549
-
550
- // const signedPermitInvalid = await PermitUtils.sign(permitInvalid, publicClient, bobWalletClient);
551
- // const isValidInvalid = await PermitUtils.checkValidityOnChain(signedPermitInvalid, publicClient);
552
-
553
- // expect(typeof isValidInvalid).toBe('boolean');
554
- // expect(isValidInvalid).toBe(false);
555
- // });
556
- });
557
- });
@@ -1,84 +0,0 @@
1
- import { describe, it, expect } from 'vitest';
2
- import { SealingKey, GenerateSealingKey } from '../index.js';
3
-
4
- describe('SealingKey', () => {
5
- it('should create a SealingKey with valid keys', () => {
6
- const privateKey = 'a'.repeat(64);
7
- const publicKey = 'b'.repeat(64);
8
-
9
- const sealingKey = new SealingKey(privateKey, publicKey);
10
-
11
- expect(sealingKey.privateKey).toBe(privateKey);
12
- expect(sealingKey.publicKey).toBe(publicKey);
13
- });
14
-
15
- it('should throw error for invalid private key length', () => {
16
- const privateKey = 'a'.repeat(32); // Too short
17
- const publicKey = 'b'.repeat(64);
18
-
19
- expect(() => {
20
- new SealingKey(privateKey, publicKey);
21
- }).toThrow('Private key must be of length 64');
22
- });
23
-
24
- it('should throw error for invalid public key length', () => {
25
- const privateKey = 'a'.repeat(64);
26
- const publicKey = 'b'.repeat(32); // Too short
27
-
28
- expect(() => {
29
- new SealingKey(privateKey, publicKey);
30
- }).toThrow('Public key must be of length 64');
31
- });
32
-
33
- it('should seal and unseal data correctly', () => {
34
- const publicKey = 'b'.repeat(64);
35
- const value = BigInt(12345);
36
-
37
- // Seal the data
38
- const encryptedData = SealingKey.seal(value, publicKey);
39
-
40
- expect(encryptedData).toHaveProperty('data');
41
- expect(encryptedData).toHaveProperty('public_key');
42
- expect(encryptedData).toHaveProperty('nonce');
43
- expect(encryptedData.data).toBeInstanceOf(Uint8Array);
44
- expect(encryptedData.public_key).toBeInstanceOf(Uint8Array);
45
- expect(encryptedData.nonce).toBeInstanceOf(Uint8Array);
46
- });
47
-
48
- it('should throw error for invalid public key in seal', () => {
49
- const value = BigInt(12345);
50
- const invalidPublicKey = 'invalid';
51
-
52
- expect(() => {
53
- SealingKey.seal(value, invalidPublicKey);
54
- }).toThrow('bad public key size');
55
- });
56
-
57
- it('should throw error for invalid value in seal', () => {
58
- const publicKey = 'b'.repeat(64);
59
- const invalidValue = 'not a number';
60
-
61
- expect(() => {
62
- // @ts-expect-error - invalid value
63
- SealingKey.seal(invalidValue, publicKey);
64
- }).toThrow('Value not a number is not a number or bigint: string');
65
- });
66
- });
67
-
68
- describe('GenerateSealingKey', () => {
69
- it('should generate a valid SealingKey', async () => {
70
- const sealingKey = GenerateSealingKey();
71
-
72
- expect(sealingKey).toBeInstanceOf(SealingKey);
73
- expect(sealingKey.privateKey).toHaveLength(64);
74
- expect(sealingKey.publicKey).toHaveLength(64);
75
- });
76
-
77
- it('should generate different keys on each call', async () => {
78
- const key1 = GenerateSealingKey();
79
- const key2 = GenerateSealingKey();
80
-
81
- expect(key1.privateKey).not.toBe(key2.privateKey);
82
- expect(key1.publicKey).not.toBe(key2.publicKey);
83
- });
84
- });