@veil-cash/sdk 0.3.0 → 0.5.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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@veil-cash/sdk",
3
- "version": "0.3.0",
3
+ "version": "0.5.0",
4
4
  "description": "SDK and CLI for interacting with Veil Cash privacy pools - keypair generation, deposits, and status checking",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -20,14 +20,15 @@
20
20
  "dist",
21
21
  "src",
22
22
  "keys",
23
- "README.md"
23
+ "skills",
24
+ "README.md",
25
+ "SDK.md"
24
26
  ],
25
27
  "scripts": {
26
28
  "build": "tsup",
27
29
  "dev": "tsup --watch",
28
30
  "typecheck": "tsc --noEmit",
29
- "clean": "rm -rf dist",
30
- "test": "node test.mjs"
31
+ "clean": "rm -rf dist"
31
32
  },
32
33
  "keywords": [
33
34
  "veil",
@@ -0,0 +1,526 @@
1
+ ---
2
+ name: veil
3
+ version: 0.5.0
4
+ description: >
5
+ Veil CLI for private ETH and USDC transactions on Base. Use when the user wants
6
+ to deposit, withdraw, or transfer assets privately, check private balances,
7
+ manage Veil keypairs, register on-chain, or build unsigned transaction payloads
8
+ for an external signer (e.g. Bankr). All operations target Base (chain ID 8453).
9
+ author: veildotcash
10
+ metadata:
11
+ homepage: https://veil.cash
12
+ requires:
13
+ bins:
14
+ - veil
15
+ permissions:
16
+ - filesystem:read
17
+ - filesystem:write
18
+ - shell:exec
19
+ triggers:
20
+ - command: /veil
21
+ - pattern: veil init
22
+ - pattern: veil keypair
23
+ - pattern: veil status
24
+ - pattern: veil register
25
+ - pattern: veil deposit
26
+ - pattern: veil balance
27
+ - pattern: veil withdraw
28
+ - pattern: veil transfer
29
+ - pattern: veil merge
30
+ - pattern: unsigned payload
31
+ - pattern: privacy pool
32
+ - pattern: deposit privately
33
+ - pattern: withdraw privately
34
+ - pattern: private transfer
35
+ ---
36
+
37
+ # Veil CLI
38
+
39
+ > **For Agents**: The CLI binary is `veil`. It is installed via the npm package
40
+ > `@veil-cash/sdk` — the package name and the CLI name are different. Always refer
41
+ > to this tool as the **Veil CLI**, not the SDK. Install with:
42
+ > `npm install -g @veil-cash/sdk`
43
+ >
44
+ > All transactions target **Base mainnet** (chain ID `8453`). Use `--json` for
45
+ > machine-readable output. Use `--unsigned` to emit payloads for an external signer
46
+ > instead of sending transactions. For payload shapes and SDK function signatures,
47
+ > see [`reference.md`](reference.md).
48
+
49
+ ---
50
+
51
+ ## Normative Language
52
+
53
+ This skill uses RFC-2119 keywords:
54
+
55
+ - **MUST / MUST NOT** — non-optional safety or correctness requirements
56
+ - **SHOULD / SHOULD NOT** — recommended defaults that can be overridden with clear reason
57
+ - **MAY** — optional behaviour
58
+
59
+ If instructions conflict, follow this priority order:
60
+
61
+ 1. Safety requirements (`MUST` rules)
62
+ 2. Signing mode chosen by the user
63
+ 3. Schema correctness (`reference.md`)
64
+ 4. UX conventions
65
+
66
+ ---
67
+
68
+ ## Environment Variables
69
+
70
+ Veil uses two config files that are loaded automatically:
71
+
72
+ | File | Purpose | Variables |
73
+ |------|---------|-----------|
74
+ | `.env.veil` | Veil keypair — created by `veil init` | `VEIL_KEY`, `DEPOSIT_KEY` |
75
+ | `.env` | Wallet config — your existing env | `WALLET_KEY` or `SIGNER_ADDRESS`, `RPC_URL`, `RELAY_URL` |
76
+
77
+ **Both files are required** regardless of signing mode. `.env.veil` holds the Veil-specific
78
+ keys; `.env` holds the wallet identity (either a private key or a public address).
79
+
80
+ Full variable reference:
81
+
82
+ | Variable | File | Description |
83
+ |----------|------|-------------|
84
+ | `VEIL_KEY` | `.env.veil` | Veil private key — for ZK proofs, withdrawals, transfers |
85
+ | `DEPOSIT_KEY` | `.env.veil` | Veil deposit key (public) — registered on-chain |
86
+ | `WALLET_KEY` | `.env` | Ethereum private key — CLI signs and sends transactions directly |
87
+ | `SIGNER_ADDRESS` | `.env` | Ethereum address — for external-signer flows; CLI never holds the key |
88
+ | `RPC_URL` | `.env` | Base RPC URL (optional, defaults to public RPC) |
89
+ | `RELAY_URL` | `.env` | Override relay base URL (optional) |
90
+
91
+ > `WALLET_KEY` and `SIGNER_ADDRESS` are **mutually exclusive**. Setting both raises
92
+ > `CONFIG_CONFLICT`. Set only one in `.env`.
93
+
94
+ ---
95
+
96
+ ## Signing Mode — Ask First
97
+
98
+ Before running any setup commands, you **MUST** ask the user which signing mode
99
+ they want to use. Do not assume.
100
+
101
+ Both modes require `.env.veil` (created by `veil init`) for `VEIL_KEY` and `DEPOSIT_KEY`.
102
+ They differ only in what goes into `.env`:
103
+
104
+ **Option A — Local signing (`WALLET_KEY`)**
105
+ The Veil CLI holds an Ethereum private key in `.env` and signs and sends `register` and
106
+ `deposit` transactions directly. Best for personal scripts, local automation,
107
+ or agents that manage their own wallet key.
108
+
109
+ ```
110
+ # .env
111
+ WALLET_KEY=0x...
112
+
113
+ # .env.veil ← created by veil init
114
+ VEIL_KEY=0x...
115
+ DEPOSIT_KEY=0x...
116
+ ```
117
+
118
+ **Option B — External signer (e.g. Bankr)**
119
+ The Veil CLI never sees a private key. Set `SIGNER_ADDRESS` in `.env` so the CLI knows
120
+ the public address, and use `--unsigned` to get transaction payloads. The
121
+ external signer (e.g. Bankr's `POST /wallet/submit`) submits the transaction.
122
+ Best for Bankr-powered agents, MPC wallets, or any setup where the key lives
123
+ outside the CLI environment.
124
+
125
+ ```
126
+ # .env
127
+ SIGNER_ADDRESS=0x...
128
+
129
+ # .env.veil ← created by veil init --signature 0x...
130
+ VEIL_KEY=0x...
131
+ DEPOSIT_KEY=0x...
132
+ ```
133
+
134
+ ---
135
+
136
+ ## Prerequisites
137
+
138
+ Before using the Veil CLI, confirm:
139
+
140
+ - [ ] `veil` CLI installed — `npm install -g @veil-cash/sdk`
141
+ - [ ] Signing mode chosen (Option A or B above)
142
+ - [ ] For **local signing**: `WALLET_KEY` is a valid 0x-prefixed 64-char hex private key
143
+ - [ ] For **external signing**: signer address known and signing service ready (e.g. Bankr API key configured)
144
+ - [ ] ETH on Base for gas (needed for `register` and `deposit`)
145
+
146
+ ---
147
+
148
+ ## What do you want to do?
149
+
150
+ ```
151
+ What do you want to do?
152
+ |
153
+ +-- First-time setup
154
+ | +-- Local signing (WALLET_KEY) → Section 1A
155
+ | +-- Bankr / external signer → Section 1B
156
+ |
157
+ +-- Check current configuration → veil status
158
+ |
159
+ +-- Register deposit key on-chain → veil register [--unsigned]
160
+ |
161
+ +-- Deposit ETH or USDC → veil deposit <asset> <amount> [--unsigned]
162
+ |
163
+ +-- Check balances → veil balance [queue|private] [--pool eth|usdc]
164
+ |
165
+ +-- Withdraw / transfer / merge → Section 5
166
+ |
167
+ +-- Inspect or rotate keypair → veil keypair / veil init --force
168
+ ```
169
+
170
+ ---
171
+
172
+ ## Quick Reference
173
+
174
+ | Task | CLI |
175
+ |------|-----|
176
+ | Derive keypair from wallet | `veil init` |
177
+ | Generate random keypair | `veil init --generate` |
178
+ | Derive keypair from signature | `veil init --signature 0x...` |
179
+ | Show current keypair | `veil keypair` |
180
+ | Check setup and relay | `veil status` |
181
+ | Register deposit key | `veil register` |
182
+ | Build unsigned register payload | `SIGNER_ADDRESS=0x... veil register --unsigned` |
183
+ | Deposit ETH | `veil deposit ETH 0.1` |
184
+ | Deposit USDC | `veil deposit USDC 100` |
185
+ | Show all balances | `veil balance` |
186
+ | Show queue only | `veil balance queue --pool eth` |
187
+ | Show private only | `veil balance private --pool eth` |
188
+ | Withdraw | `veil withdraw ETH 0.05 0xRecipient` |
189
+ | Transfer privately | `veil transfer ETH 0.02 0xRecipient` |
190
+ | Merge UTXOs | `veil merge ETH 0.1` |
191
+
192
+ ---
193
+
194
+ ## 1A. First-Run — Local Signing
195
+
196
+ Use when `WALLET_KEY` is available and the CLI will sign and send transactions directly.
197
+
198
+ ```bash
199
+ # 1. Set your wallet key
200
+ export WALLET_KEY=0x...
201
+
202
+ # 2. Derive and save your Veil keypair (saves VEIL_KEY + DEPOSIT_KEY to .env.veil)
203
+ veil init
204
+
205
+ # 3. Register your deposit key on-chain (one-time)
206
+ veil register
207
+
208
+ # 4. Verify setup
209
+ veil status
210
+
211
+ # 5. Deposit
212
+ veil deposit ETH 0.1
213
+ veil balance
214
+ ```
215
+
216
+ `veil init` defaults to wallet-derived keypair generation. Use `--generate` for a
217
+ random keypair or `--force` to overwrite an existing one without prompting.
218
+
219
+ ---
220
+
221
+ ## 1B. First-Run — Bankr (External Signer)
222
+
223
+ Use when signing is handled outside the CLI (e.g. Bankr's `POST /wallet/sign`).
224
+ The CLI MUST NOT hold a private key in this mode.
225
+
226
+ ```bash
227
+ # 1. Get a personal_sign signature from your external signer.
228
+ # For Bankr, use POST /wallet/sign with signatureType: "personal_sign"
229
+ # and the VEIL_SIGNED_MESSAGE constant from the SDK.
230
+ # Then derive your Veil keypair from the signature:
231
+ veil init --signature 0x...
232
+ # This saves VEIL_KEY and DEPOSIT_KEY to .env.veil.
233
+
234
+ # 2. Add your signer address to .env
235
+ # (WALLET_KEY and SIGNER_ADDRESS are mutually exclusive — set only one)
236
+ echo "SIGNER_ADDRESS=0x..." >> .env
237
+
238
+ # 3. Verify setup
239
+ veil status
240
+
241
+ # 4. Register and deposit via unsigned payloads.
242
+ # Your external signer submits the transactions.
243
+ veil register --unsigned
244
+ veil deposit ETH 0.1 --unsigned
245
+ ```
246
+
247
+ For the Bankr sign API:
248
+
249
+ ```bash
250
+ SIG=$(curl -s -X POST "https://api.bankr.bot/wallet/sign" \
251
+ -H "X-API-Key: $BANKR_API_KEY" \
252
+ -H "Content-Type: application/json" \
253
+ -d "{\"signatureType\":\"personal_sign\",\"message\":\"$(node -e "const{VEIL_SIGNED_MESSAGE}=require('@veil-cash/sdk');console.log(VEIL_SIGNED_MESSAGE)")\"}" \
254
+ | jq -r '.signature')
255
+
256
+ veil init --signature $SIG
257
+ ```
258
+
259
+ ---
260
+
261
+ ## 2. Keypair and Status
262
+
263
+ Generate or inspect keys:
264
+
265
+ ```bash
266
+ veil init # Derive from WALLET_KEY (saves to .env.veil)
267
+ veil init --generate # Generate a random keypair
268
+ veil init --signature 0xSIG # Derive from a pre-computed EIP-191 signature
269
+ veil init --force # Overwrite existing keypair without prompting
270
+ veil init --no-save # Print keypair without saving to disk
271
+ veil init --json # Output as JSON (no prompts, no file save)
272
+ veil keypair
273
+ veil keypair --json
274
+ ```
275
+
276
+ Check environment, wallet, registration, and relay state:
277
+
278
+ ```bash
279
+ veil status
280
+ veil status --json
281
+ ```
282
+
283
+ `veil status` shows:
284
+
285
+ - **Signing** row: `local (WALLET_KEY)`, `external (SIGNER_ADDRESS)`, or `not configured`
286
+ - resolved address (from either `WALLET_KEY` or `SIGNER_ADDRESS`)
287
+ - public ETH balance when available
288
+ - registration and relay status
289
+
290
+ SHOULD run `veil status` after any setup step to confirm state before proceeding.
291
+
292
+ ---
293
+
294
+ ## 3. Register and Deposit
295
+
296
+ Register the current `DEPOSIT_KEY` on-chain:
297
+
298
+ ```bash
299
+ veil register
300
+ veil register --force
301
+ veil register --json
302
+ veil register --unsigned --address 0x...
303
+ SIGNER_ADDRESS=0x... veil register --unsigned
304
+ SIGNER_ADDRESS=0x... veil register --unsigned --force
305
+ ```
306
+
307
+ Important:
308
+
309
+ - `--address` is optional in unsigned mode when `SIGNER_ADDRESS` is set.
310
+ - Use `WALLET_KEY` if the CLI should sign and send the transaction itself.
311
+ - Use `SIGNER_ADDRESS` + `--unsigned` if an external signer will submit.
312
+ - `veil register --unsigned --force` checks chain state first.
313
+ - If the address is already registered, returns `changeDepositKey` payload.
314
+ - If not yet registered, returns a normal `register` payload.
315
+
316
+ Deposits treat the CLI amount as the **net** amount that lands in the pool.
317
+ The `0.3%` protocol fee is calculated on-chain and added automatically.
318
+
319
+ ```bash
320
+ veil deposit ETH 0.1
321
+ veil deposit USDC 100
322
+ veil deposit ETH 0.1 --json
323
+ veil deposit ETH 0.1 --unsigned
324
+ veil deposit USDC 100 --unsigned
325
+ ```
326
+
327
+ Minimums:
328
+
329
+ - ETH: `0.01`
330
+ - USDC: `10`
331
+
332
+ `--unsigned` notes:
333
+
334
+ - ETH returns one payload.
335
+ - USDC returns `[approve, deposit]`.
336
+ - Payloads use `{ to, data, value, chainId }`.
337
+
338
+ ---
339
+
340
+ ## 4. Balance Commands
341
+
342
+ Combined view:
343
+
344
+ ```bash
345
+ veil balance
346
+ veil balance --pool eth
347
+ veil balance --pool usdc
348
+ veil balance --json
349
+ ```
350
+
351
+ Queue only:
352
+
353
+ ```bash
354
+ veil balance queue
355
+ veil balance queue --pool usdc
356
+ veil balance queue --address 0x... --json
357
+ ```
358
+
359
+ Private only:
360
+
361
+ ```bash
362
+ veil balance private
363
+ veil balance private --pool usdc
364
+ veil balance private --json
365
+ ```
366
+
367
+ Human-readable balance output includes:
368
+
369
+ - wallet public balances (`ETH`, `USDC`)
370
+ - queue and private balances
371
+
372
+ ---
373
+
374
+ ## 5. Private Actions
375
+
376
+ Withdraw from the private pool to a public address:
377
+
378
+ ```bash
379
+ veil withdraw ETH 0.05 0xRecipientAddress
380
+ veil withdraw USDC 50 0xRecipientAddress
381
+ veil withdraw ETH 0.05 0xRecipientAddress --json
382
+ ```
383
+
384
+ Transfer privately to another registered address:
385
+
386
+ ```bash
387
+ veil transfer ETH 0.02 0xRecipientAddress
388
+ veil transfer USDC 25 0xRecipientAddress
389
+ veil transfer ETH 0.02 0xRecipientAddress --json
390
+ ```
391
+
392
+ Merge UTXOs:
393
+
394
+ ```bash
395
+ veil merge ETH 0.1
396
+ veil merge USDC 100
397
+ veil merge ETH 0.1 --json
398
+ ```
399
+
400
+ Human-readable transaction output uses Basescan links instead of raw hashes.
401
+
402
+ Note: withdraw proof generation is single-threaded for reliable CLI exit after success.
403
+
404
+ ---
405
+
406
+ ## 6. Unsigned Payloads
407
+
408
+ `--unsigned` is for external signer workflows. The CLI emits a signer-compatible
409
+ payload and does NOT send the transaction.
410
+
411
+ Shape:
412
+
413
+ ```json
414
+ {
415
+ "to": "0x...",
416
+ "data": "0x...",
417
+ "value": "0",
418
+ "chainId": 8453
419
+ }
420
+ ```
421
+
422
+ Extra context fields:
423
+
424
+ - register: `action` (`"register"` or `"changeDepositKey"`)
425
+ - deposit: `step` (`"approve"` for USDC, `"deposit"`)
426
+
427
+ For lower-level payload details, see [`reference.md`](reference.md).
428
+
429
+ ---
430
+
431
+ ## 7. Common Patterns
432
+
433
+ ### Deposit flow
434
+
435
+ ```bash
436
+ veil status # Confirm signing mode and registration
437
+ veil register # If not yet registered
438
+ veil deposit ETH 0.1
439
+ veil balance # Confirm balance updated
440
+ ```
441
+
442
+ ### Withdraw flow
443
+
444
+ ```bash
445
+ veil balance private --pool eth # Confirm available balance
446
+ veil withdraw ETH 0.05 0xRecipient
447
+ # Output includes a Basescan link for the transaction
448
+ ```
449
+
450
+ ### Bankr agent flow (external signer)
451
+
452
+ ```bash
453
+ # Step 1 — derive Veil keypair via Bankr sign API
454
+ SIG=$(curl -s -X POST "https://api.bankr.bot/wallet/sign" \
455
+ -H "X-API-Key: $BANKR_API_KEY" \
456
+ -H "Content-Type: application/json" \
457
+ -d "{\"signatureType\":\"personal_sign\",\"message\":\"$(node -e "const{VEIL_SIGNED_MESSAGE}=require('@veil-cash/sdk');console.log(VEIL_SIGNED_MESSAGE)")\"}" \
458
+ | jq -r '.signature')
459
+ veil init --signature $SIG
460
+
461
+ # Step 2 — set signer address (from Bankr wallet)
462
+ echo "SIGNER_ADDRESS=0x..." >> .env
463
+
464
+ # Step 3 — build unsigned register payload and submit via Bankr
465
+ PAYLOAD=$(veil register --unsigned --json)
466
+ curl -s -X POST "https://api.bankr.bot/wallet/submit" \
467
+ -H "X-API-Key: $BANKR_API_KEY" \
468
+ -H "Content-Type: application/json" \
469
+ -d "{\"transaction\": $PAYLOAD, \"waitForConfirmation\": true}"
470
+
471
+ # Step 4 — build unsigned deposit payload and submit
472
+ PAYLOAD=$(veil deposit ETH 0.1 --unsigned --json)
473
+ # Submit PAYLOAD via Bankr in the same way
474
+ ```
475
+
476
+ ---
477
+
478
+ ## 8. UX Guidelines
479
+
480
+ - MUST NOT display raw `{ to, data, value, chainId }` payloads as the final
481
+ user-facing message. Summarise the action in plain language instead
482
+ (e.g. "Registered deposit key for 0xABC..." or "Deposit of 0.1 ETH submitted").
483
+ - SHOULD run `veil status` after any setup step and show the output to the user
484
+ so they can confirm the configuration is correct before proceeding.
485
+ - SHOULD use `--json` when output will be parsed programmatically.
486
+ - SHOULD use `--unsigned` and route through the external signer when in
487
+ Option B (Bankr / external signer) mode — MUST NOT try to sign directly.
488
+
489
+ ---
490
+
491
+ ## 9. Error Handling
492
+
493
+ All CLI errors output JSON with a standardised `errorCode`:
494
+
495
+ ```json
496
+ { "success": false, "errorCode": "VEIL_KEY_MISSING", "error": "..." }
497
+ ```
498
+
499
+ | Error code | Cause | Fix |
500
+ |---|---|---|
501
+ | `CONFIG_CONFLICT` | Both `WALLET_KEY` and `SIGNER_ADDRESS` are set | Remove one from `.env` — they are mutually exclusive |
502
+ | `WALLET_KEY_MISSING` | Local mode but `WALLET_KEY` not set, or wrong mode for command | Add `WALLET_KEY` to `.env`, or use `--signature` / `--generate` if using external signer |
503
+ | `VEIL_KEY_MISSING` | Private action (`withdraw`, `transfer`, `merge`) without `VEIL_KEY` | Run `veil init` or restore `VEIL_KEY` from backup into `.env.veil` |
504
+ | `DEPOSIT_KEY_MISSING` | `DEPOSIT_KEY` missing from `.env.veil` | Re-run `veil init` to regenerate |
505
+ | `USER_NOT_REGISTERED` | Transfer recipient has no deposit key registered on-chain | Recipient must run `veil register` first |
506
+ | `INVALID_AMOUNT` | Amount below minimum or invalid format | ETH min: `0.01`, USDC min: `10` |
507
+ | `INSUFFICIENT_BALANCE` | Not enough ETH for gas | Top up Base ETH balance |
508
+ | `RPC_ERROR` | Network or RPC failure | Check `RPC_URL` env var or retry |
509
+ | `RELAY_ERROR` | Relayer rejected the proof | Check relay health with `veil status`; retry |
510
+
511
+ ---
512
+
513
+ ## 10. Security
514
+
515
+ - MUST NOT pass `WALLET_KEY` or `VEIL_KEY` as CLI flags — use env vars only.
516
+ - Store `VEIL_KEY` and `DEPOSIT_KEY` in `.env.veil`.
517
+ - Store `WALLET_KEY` in `.env` or the shell environment.
518
+ - Use `SIGNER_ADDRESS` when the signer is external and the CLI MUST NOT hold the wallet key.
519
+ - `WALLET_KEY` and `SIGNER_ADDRESS` are mutually exclusive. Set only one.
520
+ - Never commit `.env` or `.env.veil` to source control.
521
+
522
+ ---
523
+
524
+ ## Additional Resources
525
+
526
+ For exact payload shapes and lower-level SDK function signatures, see [`reference.md`](reference.md).