@inco/js 0.8.0-devnet-11 → 0.8.0-devnet-13

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 (50) hide show
  1. package/README.md +541 -47
  2. package/dist/cjs/binary.d.ts +84 -0
  3. package/dist/cjs/binary.js +81 -4
  4. package/dist/cjs/chain.d.ts +21 -4
  5. package/dist/cjs/chain.js +18 -7
  6. package/dist/cjs/encryption/encryption.d.ts +115 -0
  7. package/dist/cjs/encryption/encryption.js +98 -7
  8. package/dist/cjs/generated/local-node.d.ts +2 -2
  9. package/dist/cjs/generated/local-node.js +2 -2
  10. package/dist/cjs/handle.d.ts +41 -0
  11. package/dist/cjs/handle.js +31 -6
  12. package/dist/cjs/lite/lightning.d.ts +19 -0
  13. package/dist/cjs/lite/lightning.js +20 -5
  14. package/dist/cjs/local/local-node.d.ts +18 -0
  15. package/dist/cjs/local/local-node.js +18 -3
  16. package/dist/cjs/reencryption/eip712.d.ts +27 -0
  17. package/dist/cjs/reencryption/eip712.js +20 -7
  18. package/dist/cjs/reencryption/types.d.ts +24 -0
  19. package/dist/cjs/viem.d.ts +11 -0
  20. package/dist/cjs/viem.js +12 -1
  21. package/dist/esm/binary.d.ts +84 -0
  22. package/dist/esm/binary.js +81 -4
  23. package/dist/esm/chain.d.ts +21 -4
  24. package/dist/esm/chain.js +17 -6
  25. package/dist/esm/encryption/encryption.d.ts +115 -0
  26. package/dist/esm/encryption/encryption.js +98 -7
  27. package/dist/esm/generated/local-node.d.ts +2 -2
  28. package/dist/esm/generated/local-node.js +2 -2
  29. package/dist/esm/handle.d.ts +41 -0
  30. package/dist/esm/handle.js +31 -6
  31. package/dist/esm/lite/lightning.d.ts +19 -0
  32. package/dist/esm/lite/lightning.js +20 -5
  33. package/dist/esm/local/local-node.d.ts +18 -0
  34. package/dist/esm/local/local-node.js +18 -3
  35. package/dist/esm/reencryption/eip712.d.ts +27 -0
  36. package/dist/esm/reencryption/eip712.js +20 -7
  37. package/dist/esm/reencryption/types.d.ts +24 -0
  38. package/dist/esm/viem.d.ts +11 -0
  39. package/dist/esm/viem.js +12 -1
  40. package/dist/types/binary.d.ts +84 -0
  41. package/dist/types/chain.d.ts +21 -4
  42. package/dist/types/encryption/encryption.d.ts +115 -0
  43. package/dist/types/generated/local-node.d.ts +2 -2
  44. package/dist/types/handle.d.ts +41 -0
  45. package/dist/types/lite/lightning.d.ts +19 -0
  46. package/dist/types/local/local-node.d.ts +18 -0
  47. package/dist/types/reencryption/eip712.d.ts +27 -0
  48. package/dist/types/reencryption/types.d.ts +24 -0
  49. package/dist/types/viem.d.ts +11 -0
  50. package/package.json +1 -7
package/README.md CHANGED
@@ -1,100 +1,594 @@
1
1
  # @inco/js
2
2
 
3
- The @inco/js package contains the TypeScript SDK for creating dapps built on Inco.
3
+ TypeScript SDK for building privacy-preserving dapps on [Inco Lightning](https://docs.inco.org). Encrypt values client-side, post ciphertexts to smart contracts for confidential computation, and retrieve attested decryptions — all with post-quantum hybrid encryption (X-Wing KEM).
4
4
 
5
5
  ## Current Status: Active Development
6
6
 
7
- The SDK is currently going through active development, to support all new features that Inco offers. As such, do expect breaking changes in subsequent releases, which will be documented in the [CHANGELOG](./CHANGELOG.md).
7
+ The SDK is under active development. Expect breaking changes in subsequent releases, documented in the [CHANGELOG](./CHANGELOG.md).
8
8
 
9
- ## Install
10
-
11
- Choose your favorite package manager:
9
+ ## Installation
12
10
 
13
11
  ```bash
14
12
  npm install @inco/js
15
13
  # or
16
- bun install @inco/js
17
- # or
18
14
  yarn add @inco/js
15
+ # or
16
+ bun add @inco/js
19
17
  ```
20
18
 
21
- ## Usage
19
+ **Peer dependency:** [viem](https://viem.sh) `^2.39.3` is used for Ethereum interactions.
22
20
 
23
- A typical usage of `@inco/js` includes 3 steps:
21
+ > **Note:** The library has currently only been tested with Webpack and Next.js. If you encounter issues with Rollup or Vite, please open an issue.
24
22
 
25
- 1. Encrypting a value.
26
- 2. Posting the ciphertext to the contract, which will perform confidential computes on it.
27
- 3. Requesting an attested decryption of the result of the computation.
23
+ ## Quick Start
28
24
 
29
- ### 1. Encrypt a value
25
+ A typical workflow has three steps:
26
+
27
+ 1. **Encrypt** a value client-side
28
+ 2. **Submit** the ciphertext to a smart contract for confidential computation
29
+ 3. **Decrypt** the result via attested decryption
30
30
 
31
31
  ```ts
32
- import { getViemChain, supportedChains } from '@inco/js';
32
+ import { getViemChain, supportedChains, handleTypes } from '@inco/js';
33
33
  import { Lightning } from '@inco/js/lite';
34
34
  import { createWalletClient } from 'viem';
35
35
 
36
- // Setup: do it once at initialization
36
+ // 1. Setup
37
37
  const chainId = supportedChains.baseSepolia;
38
- const zap = Lightning.latest('testnet', chainId); // Connect to Inco's latest public testnet
38
+ const zap = await Lightning.latest('testnet', chainId);
39
39
  const walletClient = createWalletClient({
40
40
  chain: getViemChain(chainId),
41
- account: /* Choose your account, e.g. from window.ethereum */,
42
- transport: /* Choose your transport, e.g. from Alchemy */,
41
+ account: /* your account */,
42
+ transport: /* your transport */,
43
43
  });
44
- const dappAddress = '0x00000000000000000000000000000000deadbeef'; // Put your contract address here
44
+ const dappAddress = '0x...'; // Your contract address
45
45
 
46
- // Encrypt the plaintext value
47
- const plaintext = 42;
48
- const ciphertext = await zap.encrypt(plaintext, {
46
+ // 2. Encrypt
47
+ const ciphertext = await zap.encrypt(42n, {
49
48
  accountAddress: walletClient.account.address,
50
49
  dappAddress,
50
+ handleType: handleTypes.euint256,
51
51
  });
52
52
 
53
- console.log(ciphertext); // A long hex string representing the encrypted value
53
+ // 3. Submit ciphertext to contract via viem writeContract (not SDK-specific)
54
+
55
+ // 4. Decrypt the result
56
+ const resultHandle = '0x...'; // Retrieved from the contract
57
+ const [attestation] = await zap.attestedDecrypt(walletClient, [resultHandle]);
58
+ console.log(attestation.plaintext.value);
54
59
  ```
55
60
 
56
- ### 2. Post the ciphertext to the contract
61
+ ---
62
+
63
+ ## Package Exports
64
+
65
+ | Import Path | Description |
66
+ | ----------------------- | ---------------------------------------------------------------------------------------------- |
67
+ | `@inco/js` | Core utilities: binary helpers, chain definitions, handle types, viem integration |
68
+ | `@inco/js/lite` | Main SDK: `Lightning` class, encryption, attested decrypt/compute, X-Wing crypto, session keys |
69
+ | `@inco/js/encryption` | Encryption types, plaintext/ciphertext conversions, scheme constants |
70
+ | `@inco/js/reencryption` | Reencryption types, EIP-712 payload creation |
71
+ | `@inco/js/abis` | Generated smart contract ABIs (Lightning, Verifier) |
72
+ | `@inco/js/local` | Local node environment parsing for development |
73
+
74
+ ---
75
+
76
+ ## API Reference
77
+
78
+ ### `Lightning` Class
79
+
80
+ **Import:** `import { Lightning } from '@inco/js/lite'`
57
81
 
58
- This step does not require any specific `@inco/js` functionality. We recommend using [viem](https://viem.sh) to interact with the blockchain. Specifically, use the [`writeContract`](https://viem.sh/docs/contract/writeContract) method to submit transactions. Pass the `ciphertext` from the previous encryption step as the input ciphertext parameter of type `bytes`.
82
+ The primary entry point for all SDK operations. Binds to a specific Inco Lightning deployment and provides encryption, attested decryption, attested compute, and session key management.
59
83
 
60
- ### 3. Request a reencryption
84
+ #### Factory Methods
61
85
 
62
- Following transaction submission, the Inco covalidator processes the computation request. The contract stores the computation result as a handle on-chain. This handle, referenced below as `resultHandle`, is a hexadecimal string of type `Handle` that serves as a reference to the encrypted computation output.
86
+ The constructor is private. Use one of the static factory methods:
63
87
 
64
88
  ```ts
65
- import { Hex } from "viem";
89
+ // Connect to the latest deployment for a given pepper and chain
90
+ const zap = await Lightning.latest("testnet", supportedChains.baseSepolia);
91
+ // Connect with custom configuration
92
+ const zap = await Lightning.custom({
93
+ executorAddress: "0x...",
94
+ chainId: 84532,
95
+ covalidatorUrls: ["https://..."],
96
+ });
97
+
98
+ // Connect to a local development node
99
+ const zap = await Lightning.localNode(); // default testnet pepper
100
+ const zap = await Lightning.localNodeFromEnv(".env"); // from env file
101
+ ```
102
+
103
+ | Method | Returns | Description |
104
+ | --------------------------------------------- | -------------------- | ----------------------------------------------- |
105
+ | `Lightning.baseSepoliaTestnet()` | `Promise<Lightning>` | Latest testnet deployment on Base Sepolia |
106
+ | `Lightning.latest(pepper, chainId)` | `Promise<Lightning>` | Latest deployment for a given pepper and chain |
107
+ | `Lightning.latestDeployment(pepper, chainId)` | `Deployment` | Synchronous deployment lookup (no network call) |
108
+ | `Lightning.at(id)` | `Promise<Lightning>` | Deployment by name or executor address |
109
+ | `Lightning.custom(config)` | `Promise<Lightning>` | Custom deployment configuration |
110
+ | `Lightning.localNode(env?)` | `Promise<Lightning>` | Local development node |
111
+ | `Lightning.localNodeFromEnv(source?)` | `Promise<Lightning>` | Local node from dotenv file or buffer |
112
+
113
+ #### Properties
114
+
115
+ | Property | Type | Description |
116
+ | ----------------- | --------- | -------------------------------------------- |
117
+ | `executorAddress` | `Address` | The executor contract address |
118
+ | `chainId` | `bigint` | The host chain ID |
119
+ | `deployment` | `T` | Shallow copy of the deployment configuration |
66
120
 
67
- // Request a re-encryption of the result ciphertext
68
- const resultHandle = "0x..." as Hex; // Retrieve the handle from the contract, e.g. using viem
69
- // Use same walletClient as previous step
70
- const resultPlaintext = await zap.attestedDecrypt(walletClient, [resultHandle]);
121
+ #### `encrypt(value, context)`
71
122
 
72
- console.log(resultPlaintext[0].plaintext.value); // The decrypted value
123
+ Encrypts a plaintext value using the network's public key.
124
+
125
+ ```ts
126
+ async encrypt<T extends boolean | bigint | number>(
127
+ value: T,
128
+ context: {
129
+ accountAddress: string; // EOA interacting with the dapp
130
+ dappAddress: string; // Contract address
131
+ handleType?: FheType; // Optional, defaults based on value type
132
+ }
133
+ ): Promise<HexString>
73
134
  ```
74
135
 
75
- Handles are processed asynchronously so you may need to wait for our covalidators to catch and compute the value. If you request an attested decryption before it has been processed you will get an error. To help ameliorate this the `attestedDecrypt` has built-in retries, you can further customise by passing a `BackoffConfig` as an extra argument:
136
+ **Supported types and default handle mappings:**
137
+
138
+ | Value Type | Default Handle Type | Example |
139
+ | ------------------- | ---------------------- | ------------------------------------------------------------------------- |
140
+ | `boolean` | `handleTypes.ebool` | `zap.encrypt(true, ctx)` |
141
+ | `bigint` / `number` | `handleTypes.euint256` | `zap.encrypt(42n, ctx)` |
142
+ | `bigint` (address) | `handleTypes.euint160` | `zap.encrypt(BigInt(addr), { ...ctx, handleType: handleTypes.euint160 })` |
143
+
144
+ Returns a hex string ciphertext to pass to your contract as `bytes`.
145
+
146
+ #### `attestedDecrypt(walletClient, handles, ...)`
147
+
148
+ Requests attested decryption of one or more handles. Only handles approved via `e.allow()` can be decrypted.
149
+
150
+ **Three calling modes:**
76
151
 
77
152
  ```ts
78
- type BackoffConfig = {
79
- maxRetries: number;
80
- baseDelayInMs: number;
81
- backoffFactor: number;
82
- };
153
+ // Mode 1: Plaintext result (auto-generates ephemeral keypair internally)
154
+ const attestations = await zap.attestedDecrypt(walletClient, [handle]);
155
+ attestations[0].plaintext.value; // The decrypted value
156
+
157
+ // Mode 2: Reencrypt for a delegate (returns encrypted result)
158
+ const encrypted = await zap.attestedDecrypt(
159
+ walletClient,
160
+ [handle],
161
+ delegatePubKey,
162
+ );
163
+ encrypted[0].encryptedPlaintext.ciphertext.value;
164
+
165
+ // Mode 3: Reencrypt and decrypt locally
166
+ const decrypted = await zap.attestedDecrypt(
167
+ walletClient,
168
+ [handle],
169
+ keypair.encodePublicKey(),
170
+ keypair,
171
+ );
172
+ decrypted[0].plaintext.value;
173
+ ```
83
174
 
84
- const resultHandle = "0x..." as Hex;
85
- // Default backoff config shown for reference
86
- const backoffConfig: BackoffConfig = {
175
+ All modes accept an optional `BackoffConfig` as the last argument for retry tuning:
176
+
177
+ ```ts
178
+ const attestations = await zap.attestedDecrypt(walletClient, [handle], {
87
179
  maxRetries: 10,
88
180
  baseDelayInMs: 1000,
89
181
  backoffFactor: 1.5,
90
- };
91
- const resultPlaintext = await zap.attestedDecrypt(
182
+ });
183
+ ```
184
+
185
+ **Return types:**
186
+
187
+ | Mode | Return Type |
188
+ | ------------------------- | ----------------------------------------------------------------------------------------------------------------- |
189
+ | Plaintext | `DecryptionAttestation[]` — `{ handle, plaintext, covalidatorSignatures }` |
190
+ | Reencrypt | `EncryptedDecryptionAttestation[]` — `{ handle, encryptedPlaintext, encryptedSignatures, covalidatorSignatures }` |
191
+ | Reencrypt + local decrypt | `DecryptionAttestation[]` |
192
+
193
+ #### `attestedReveal(handles, backoffConfig?)`
194
+
195
+ Decrypts publicly revealed handles (those marked with `e.reveal()`). Does not require a wallet — anyone can call this.
196
+
197
+ ```ts
198
+ const attestations = await zap.attestedReveal([handle]);
199
+ attestations[0].plaintext.value;
200
+ ```
201
+
202
+ > **Warning:** Once `e.reveal()` is called on-chain, the ciphertext is considered public and can be accessed by anyone. This cannot be undone.
203
+
204
+ #### `attestedCompute(walletClient, lhsHandle, op, rhsPlaintext, ...)`
205
+
206
+ Performs an off-chain comparison operation on an encrypted handle against a plaintext scalar, returning an attested result.
207
+
208
+ ```ts
209
+ import { AttestedComputeSupportedOps } from "@inco/js/lite";
210
+
211
+ // Plaintext result
212
+ const result = await zap.attestedCompute(
92
213
  walletClient,
93
- [resultHandle],
94
- backoffConfig,
214
+ handle,
215
+ AttestedComputeSupportedOps.Ge,
216
+ 700n,
217
+ );
218
+ console.log(result.plaintext.value); // true or false
219
+ ```
220
+
221
+ **Supported operations:**
222
+
223
+ | Operation | Description |
224
+ | -------------------------------- | --------------------- |
225
+ | `AttestedComputeSupportedOps.Eq` | Equal |
226
+ | `AttestedComputeSupportedOps.Ne` | Not equal |
227
+ | `AttestedComputeSupportedOps.Ge` | Greater than or equal |
228
+ | `AttestedComputeSupportedOps.Gt` | Greater than |
229
+ | `AttestedComputeSupportedOps.Le` | Less than or equal |
230
+ | `AttestedComputeSupportedOps.Lt` | Less than |
231
+
232
+ Supports the same three calling modes as `attestedDecrypt` (plaintext, reencrypt, reencrypt + local decrypt).
233
+
234
+ #### Session Key Methods
235
+
236
+ Session keys (allowance vouchers) enable delegated decryption without requiring the data owner's wallet signature for each request.
237
+
238
+ ```ts
239
+ // Owner grants a session key to a delegate
240
+ const voucher = await zap.grantSessionKeyAllowanceVoucher(
241
+ walletClient, // Owner's wallet
242
+ granteeAddress, // Delegate's address
243
+ expiresAt, // Expiration Date
244
+ sessionVerifierAddr, // Session verifier contract
245
+ );
246
+
247
+ // Delegate decrypts using the voucher
248
+ const attestations = await zap.attestedDecryptWithVoucher(
249
+ ephemeralAccount,
250
+ voucher,
251
+ ethClient,
252
+ [handle],
253
+ );
254
+
255
+ // Delegate computes using the voucher
256
+ const result = await zap.attestedComputeWithVoucher(
257
+ ephemeralAccount,
258
+ voucher,
259
+ ethClient,
260
+ handle,
261
+ AttestedComputeSupportedOps.Eq,
262
+ 42n,
95
263
  );
264
+
265
+ // Owner revokes all active vouchers
266
+ const txHash = await zap.updateActiveVouchersSessionNonce(walletClient);
96
267
  ```
97
268
 
269
+ | Method | Description |
270
+ | ------------------------------------------------------------------------------ | ------------------------------------ |
271
+ | `grantSessionKeyAllowanceVoucher(walletClient, grantee, expiresAt, verifier)` | Grant a time-limited session key |
272
+ | `grantCustomSessionKeyAllowanceVoucher(walletClient, verifier, sharerArgData)` | Grant with custom verifier arguments |
273
+ | `attestedDecryptWithVoucher(account, voucher, client, handles, ...)` | Decrypt using a session key |
274
+ | `attestedComputeWithVoucher(account, voucher, client, handle, op, rhs, ...)` | Compute using a session key |
275
+ | `updateActiveVouchersSessionNonce(walletClient)` | Revoke all active vouchers |
276
+
277
+ #### Static Helpers
278
+
279
+ ```ts
280
+ // Read network public key from on-chain verifier
281
+ const pubkey = await Lightning.getNetworkPubkey(publicClient, executorAddress);
282
+
283
+ // Get the IncoVerifier contract instance
284
+ const verifier = await Lightning.getIncoVerifierContract(
285
+ publicClient,
286
+ executorAddress,
287
+ );
288
+
289
+ // Get covalidator URLs for a deployment
290
+ const urls = Lightning.getCovalidatorUrls(deployment, threshold);
291
+ ```
292
+
293
+ ---
294
+
295
+ ### Core Utilities (`@inco/js`)
296
+
297
+ #### Chain Support
298
+
299
+ ```ts
300
+ import { supportedChains, getSupportedChain, getViemChain } from "@inco/js";
301
+
302
+ // Supported chains
303
+ supportedChains.baseSepolia; // 84532
304
+ supportedChains.sepolia; // 11155111
305
+ supportedChains.monadTestnet; // 10143
306
+ supportedChains.plasmaTestnet; // 9746
307
+ supportedChains.worldchainSepolia; // 4801
308
+ supportedChains.anvil; // 31337
309
+
310
+ // Resolve chain from ID, name, or object
311
+ const chain = getSupportedChain(84532);
312
+ const chain = getSupportedChain("baseSepolia");
313
+ const chain = getSupportedChain({ id: 84532 });
314
+
315
+ // Get viem Chain object
316
+ const viemChain = getViemChain(84532);
317
+ ```
318
+
319
+ #### Handle Types
320
+
321
+ ```ts
322
+ import {
323
+ handleTypes,
324
+ isFheType,
325
+ validateHandle,
326
+ getHandleType,
327
+ } from "@inco/js";
328
+
329
+ // FHE type identifiers
330
+ handleTypes.ebool; // 0
331
+ handleTypes.euint4; // 1
332
+ handleTypes.euint8; // 2
333
+ handleTypes.euint16; // 3
334
+ handleTypes.euint32; // 4
335
+ handleTypes.euint64; // 5
336
+ handleTypes.euint128; // 6
337
+ handleTypes.euint160; // 7
338
+ handleTypes.euint256; // 8
339
+ handleTypes.ebytes64; // 9
340
+ handleTypes.ebytes128; // 10
341
+ handleTypes.ebytes256; // 11
342
+
343
+ // Validate and inspect handles
344
+ validateHandle("0x..."); // throws if malformed
345
+ const fheType = getHandleType("0x..."); // extracts FheType from handle
346
+ isFheType(5); // true (euint64)
347
+ ```
348
+
349
+ #### Binary Utilities
350
+
351
+ ```ts
352
+ import {
353
+ bytesToBigInt,
354
+ bigintToBytes,
355
+ bigintToBytes32,
356
+ bytes32ToBigint,
357
+ bytesFromHexString,
358
+ bytesToHex,
359
+ mustBeHex,
360
+ normaliseToHex,
361
+ padLeft,
362
+ asBytes32,
363
+ parseAddress,
364
+ parseHex,
365
+ } from "@inco/js";
366
+
367
+ // Conversions
368
+ bytesToBigInt(new Uint8Array([1, 0])); // 256n
369
+ bigintToBytes(42n); // 32-byte Buffer
370
+ bigintToBytes32(42n); // '0x000...002a' (Bytes32)
371
+
372
+ // Hex helpers
373
+ mustBeHex("0xdead"); // returns typed Hex, throws if invalid
374
+ normaliseToHex("dead"); // '0xdead'
375
+ bytesToHex(new Uint8Array()); // '0x'
376
+
377
+ // Parsing with validation
378
+ parseAddress("0x1234...5678"); // validated Address (20 bytes)
379
+ parseHex("0xabcd"); // validated HexString
380
+ asBytes32("0x00...00"); // validated Bytes32 (32 bytes)
381
+ ```
382
+
383
+ #### Handle Computation
384
+
385
+ ````ts
386
+ import { computePrehandle, computeHandle, hashInputContext, HANDLE_VERSION } from '@inco/js';
387
+
388
+ const prehandle = computePrehandle({
389
+ ciphertext: new Uint8Array([...]),
390
+ indexHandle: 0,
391
+ handleType: handleTypes.euint256,
392
+ handleVersion: HANDLE_VERSION,
393
+ });
394
+
395
+ const handle = computeHandle({ prehandle, context: inputContext });
396
+ const contextHash = hashInputContext(inputContext);
397
+
398
+ ---
399
+
400
+ ### Encryption Module (`@inco/js/encryption`)
401
+
402
+ Types and conversion utilities for plaintexts and ciphertexts.
403
+
404
+ ```ts
405
+ import {
406
+ // Constants
407
+ encryptionSchemes, // { xwing: 2 }
408
+ supportedFheTypes, // { euint64: 5, euint160: 7, euint256: 8, ebool: 0 }
409
+
410
+ // Conversions
411
+ bigintToPlaintext, // (scheme, type, bigint) => Plaintext
412
+ plaintextToBigint, // (plaintext) => bigint
413
+ plaintextToBytes32, // (plaintext) => Bytes32
414
+ plaintextToBytes, // (plaintext) => Buffer
415
+ bytes32ToPlaintext, // (bytes32, scheme, type) => Plaintext
416
+ bytesToPlaintext, // (bytes, scheme, type) => Plaintext
417
+
418
+ // Ciphertext input encoding (for on-chain format)
419
+ encodeCiphertextInput, // (version, handle, ciphertext) => Hex
420
+ decodeCiphertextInput, // (input) => { version, handle, ciphertext }
421
+
422
+ // Helpers
423
+ getEncryptionSchemeName, // (scheme) => 'X-Wing'
424
+ } from '@inco/js/encryption';
425
+ ````
426
+
427
+ **Key types:**
428
+
429
+ | Type | Description |
430
+ | ------------------ | -------------------------------------------------------------------------------------- |
431
+ | `Plaintext` | `{ scheme, type, value }` — value is `bigint` for integer types, `boolean` for `ebool` |
432
+ | `Ciphertext` | `{ scheme, type, value }` — value is a hex string |
433
+ | `EncryptResult` | `{ ciphertext, context, prehandle, handle }` |
434
+ | `EncryptionScheme` | Currently only `2` (X-Wing) |
435
+ | `SupportedFheType` | `0`, `5`, `7`, `8` (ebool, euint64, euint160, euint256) |
436
+ | `Encryptor<S>` | `(plaintext) => Promise<EncryptResult>` |
437
+ | `Decryptor<S>` | `(ciphertext) => Promise<Plaintext>` |
438
+
439
+ ---
440
+
441
+ ### X-Wing Cryptography (`@inco/js/lite`)
442
+
443
+ Post-quantum hybrid encryption using X-Wing KEM (ML-KEM-768 + X25519).
444
+
445
+ ```ts
446
+ import {
447
+ generateXwingKeypair,
448
+ deriveXwingKeypairFromSeed,
449
+ decodeXwingPublicKey,
450
+ decodeXwingPrivateKey,
451
+ encodeXwingPublicKey,
452
+ getXwingEncryptor,
453
+ getXwingDecryptor,
454
+ encrypt,
455
+ decrypt,
456
+ XWING_PUBLIC_KEY_SIZE, // 1216 bytes
457
+ } from "@inco/js/lite";
458
+
459
+ // Generate a random keypair
460
+ const keypair = await generateXwingKeypair();
461
+ const pubKeyBytes = keypair.encodePublicKey(); // Uint8Array (1216 bytes)
462
+
463
+ // Deterministic keypair from a 32-byte seed
464
+ const keypair = await deriveXwingKeypairFromSeed(seed);
465
+
466
+ // Create encryptor/decryptor functions
467
+ const encryptor = getXwingEncryptor({ pubKeyA: keypair.publicKey });
468
+ const decryptor = getXwingDecryptor({ privKeyA: keypair });
469
+
470
+ // Low-level HPKE encrypt/decrypt
471
+ const encrypted = await encrypt(publicKey, message);
472
+ const decrypted = await decrypt(keypair, encrypted);
473
+ ```
474
+
475
+ ---
476
+
477
+ ### Deployment Utilities (`@inco/js/lite`)
478
+
479
+ ```ts
480
+ import {
481
+ getActiveLightningDeployment,
482
+ getLightningDeployments,
483
+ } from "@inco/js/lite";
484
+
485
+ // Get the latest active deployment for a chain
486
+ const deployment = getActiveLightningDeployment("baseSepolia");
487
+
488
+ // Get all deployments for a chain
489
+ const deployments = getLightningDeployments(84532);
490
+ ```
491
+
492
+ ---
493
+
494
+ ### Reencryption Module (`@inco/js/reencryption`)
495
+
496
+ EIP-712 typed data utilities for signing reencryption requests.
497
+
498
+ ```ts
499
+ import { createEIP712Payload } from "@inco/js/reencryption";
500
+
501
+ const payload = createEIP712Payload({
502
+ chainId: 84532n,
503
+ primaryType: "Reencrypt",
504
+ primaryTypeFields: [{ name: "publicKey", type: "bytes" }],
505
+ message: { publicKey: "0x..." },
506
+ domainName: "IncoLite",
507
+ domainVersion: "1",
508
+ verifyingContract: "0x...",
509
+ });
510
+ ```
511
+
512
+ **Key types:**
513
+
514
+ | Type | Description |
515
+ | ----------------- | ---------------------------------------------- |
516
+ | `Reencryptor<S>` | `(args, backoffConfig?) => Promise<Plaintext>` |
517
+ | `PubKeyEncodable` | `{ encodePublicKey(): Uint8Array }` |
518
+ | `EIP712<Message>` | Full EIP-712 typed data payload |
519
+
520
+ ---
521
+
522
+ ### Local Development (`@inco/js/local`)
523
+
524
+ Tools for connecting to a local Anvil + Covalidator development node.
525
+
526
+ ```ts
527
+ import { parseLocalEnv } from "@inco/js/local";
528
+
529
+ // Parse from dotenv string/buffer
530
+ const env = parseLocalEnv(fs.readFileSync(".env"));
531
+
532
+ // Parse from process.env
533
+ const env = parseLocalEnv();
534
+
535
+ // Use with Lightning
536
+ const zap = await Lightning.localNode(env);
537
+ ```
538
+
539
+ Docker images for local development:
540
+
541
+ - `inconetwork/local-node-anvil`
542
+ - `inconetwork/local-node-covalidator`
543
+
544
+ ---
545
+
546
+ ### ABIs (`@inco/js/abis`)
547
+
548
+ Generated contract ABIs for direct contract interaction with viem.
549
+
550
+ ```ts
551
+ import { incoLightningAbi } from "@inco/js/abis/lightning";
552
+ import { incoVerifierAbi } from "@inco/js/abis/verifier";
553
+ ```
554
+
555
+ ---
556
+
557
+ ## Supported Chains
558
+
559
+ | Chain | Chain ID | Name |
560
+ | -------------- | -------- | --------------- |
561
+ | Base Sepolia | `84532` | `baseSepolia` |
562
+ | Plasma Testnet | `9746` | `plasmaTestnet` |
563
+
564
+ ---
565
+
566
+ ## BackoffConfig
567
+
568
+ All attested decrypt/compute methods support optional retry configuration:
569
+
570
+ ```ts
571
+ type BackoffConfig = {
572
+ maxRetries: number; // Default: 5
573
+ baseDelayInMs: number; // Default: 1000
574
+ backoffFactor: number; // Default: 1.5
575
+ errHandler?: (error: Error, attempt: number) => "stop" | "continue";
576
+ };
577
+ ```
578
+
579
+ Only transient errors (timeouts, connection issues, 503s) are retried. Security-critical errors (auth failures, invalid signatures) fail immediately.
580
+
581
+ ---
582
+
583
+ ## Further Reading
584
+
585
+ - [Inco Documentation](https://docs.inco.org)
586
+ - [Encryption Guide](https://docs.inco.org/js-sdk/encryption)
587
+ - [Attested Decrypt](https://docs.inco.org/js-sdk/attestations/attested-decrypt)
588
+ - [Attested Compute](https://docs.inco.org/js-sdk/attestations/attested-compute)
589
+ - [Attested Reveal](https://docs.inco.org/js-sdk/attestations/attested-reveal)
590
+ - [Allowance Vouchers](https://docs.inco.org/js-sdk/voucher/allowance-voucher)
591
+
98
592
  ## License
99
593
 
100
- See the [LICENSE](./LICENSE) file.
594
+ [Apache-2.0](./LICENSE)