Skip to main content

Canonical data shape

Both Transact and TransactSwap use:
  • proof_bytes: 256-byte Groth16 proof
  • public_inputs: 264-byte packed blob
Public input layout:
  • root[32]
  • publicAmount[8] (signed LE)
  • extDataHash[32]
  • mintAddress[32]
  • nullifiers[64]
  • commitments[64]
  • chainNoteHash[32]

Deposit flow (publicAmount > 0)

  1. SDK creates output UTXOs and generates proof inputs.
  2. SDK resolves Merkle data from chain.
  3. Transaction is submitted (direct signer path for deposit variants).
  4. Program verifies proof and appends commitments to the tree.
  5. SDK resolves commitment index and persists local proof context.

Withdraw/transfer flow

  1. SDK builds 2-in/2-out witness and computes nullifiers.
  2. SDK optionally ensures viewing-key registration.
  3. SDK submits the proof + public inputs and the resulting on-chain transaction lands.
  4. Program rejects reused nullifiers and enforces amount/fee constraints.
  5. Client polls transaction status until completed or failed.

Swap flow

  1. SDK generates proof for withdraw-like step with swap params.
  2. TransactSwap (Tx1) opens SwapState.
  3. Settlement path (Tx2) executes the swap and validates output min amount.
  4. Status includes swap_phase, signatures, and error context.
  5. Timeout/close paths can reclaim state if settlement cannot complete.

Reliability behaviors

  • Stale root retries: SDK regenerates proofs when root history moved, on a bounded retry budget
  • Nullifier preflight: preflightNullifiers throws UtxoAlreadySpentError before a spend, in one batched RPC call
  • Settlement confirmation: confirmTransactSettlement decides from chain state whether a submission landed by polling input-nullifier PDAs; a verdict of unknown means the SDK could not check and is never success
  • Direct-submission gating: assertDirectSubmissionLanded throws SettlementVerificationError unless nullifier PDAs prove the transaction was applied, because a confirmed-looking status field is not proof
  • Swap refund recovery: discoverSwapRefunds plus deriveSwapRefundAuthorization re-derive and reclaim a stranded swap refund. Discovery is forward-looking only: it finds refunds whose authorization was derived from the wallet’s nk, so an empty result is not proof that no stranded refund exists
  • Pending-deposit recovery: loadPendingDeposits and cleanupStalePendingOperations persist in-flight deposits so a crash or navigation away does not strand a note. Browser storage is used by default and the records carry spending secrets, so encrypt that storage in production

Where to go next

  1. Shield Pool Program
  2. UTXO Transactions
  3. Code Examples
  4. Security controls