For the complete documentation index, see llms.txt. This page is also available as Markdown.

Agentic Wallet

The agentic wallet is the architecture behind agent mode in the Doma CLI. It lets an AI agent execute on-chain actions on the user's behalf (within a hard policy) without ever holding the wallet's private key.

This page describes the model. For the user-facing CLI flow, see Wallet Modes.

What it is

Doma's launchpad uses Privy embedded wallets. Each user has an EVM wallet whose private key is generated and held inside Privy's HSM. Neither the user nor Doma ever see it. The wallet is available across both Doma Mainnet (chain 97477) and Doma Testnet (chain 97476); agent mode works on either.

For agent commerce, we attach a delegated agent signer to the wallet, governed by a per-wallet policy. The agent never holds the user's key, and Privy refuses any signature request that falls outside the policy.

Authority model

Delegated-signer authority. The user wallet (EOA, key in Privy HSM) has the user's Privy DID as owner and an additional signer: the agent authorization key, server-side in launchpad infra, bound to the policy doma-agentic-wallet-v1, which allows eth_sendTransaction on Doma mainnet (97477) and testnet (97476), and eth_signTypedData_v4 on Doma testnet (97476) only.

The policy doma-agentic-wallet-v1 is what makes the agent signer safe. Where <Doma chain IDs> in the diagram resolves to 97477 (mainnet) and 97476 (testnet), and <Doma testnet> is 97476 alone. Typed-data signatures are scoped to testnet today (see Known limitation).

  • The wallet's own private key stays in Privy's HSM. It signs every transaction (so on-chain validators see from = wallet_address).

  • The agent authorization key lives server-side in Doma's launchpad infra. It does not sign transactions itself; it tells Privy "this user authorized me, please sign on their behalf."

  • The policy is enforced by Privy. Anything the agent requests outside the policy is rejected before signing.

Policy fields

Field
What it controls
Example

chain_allowlist

Which chain IDs the agent can target

Doma mainnet, Doma testnet, Base

method_allowlist

Which RPC methods the agent can call

eth_sendTransaction, eth_signTypedData_v4

usd_spend_ceiling

Cumulative USD spend before the agent must re-authorize

$200

allowance_window

Refill window for the spend ceiling

rolling 24h

revocable_by_user

User can detach the signer at any time

true

The defaults above describe Doma's doma-agentic-wallet-v1 policy. Future versions may tighten or relax fields.

Session lifecycle

1

Login

User runs doma auth login. The CLI opens a localhost callback URL in the user's browser, which loads Doma's launchpad consent screen.

The launchpad calls Privy's wallets.update() to attach the agent authorization key as an additional signer with the doma-agentic-wallet-v1 policy, then mints a short-lived session JWT keyed to a fresh allowance row in KV (default $200 budget).

The CLI persists the JWT to ~/.doma/credentials.json (mode 0600).

Sessions are network-scoped. To authorize agent mode on both Doma Mainnet and Doma Testnet, run doma auth login once per network (toggle the network with the --testnet flag or doma config set testnet <bool> between runs).

2

Use

Every CLI write command POSTs the session JWT plus the intended transaction payload to the launchpad's /api/agent/execute endpoint. The launchpad:

  1. Validates the JWT.

  2. Decodes the calldata, computes the USD value of the transaction (using oracle prices).

  3. Checks the policy: chain allowed? method allowed? cumulative spend within ceiling?

  4. If all checks pass, instructs Privy to sign on behalf of the user.

  5. Submits the signed transaction to the chain RPC.

  6. Decrements the allowance row by the USD value.

If any check fails, the launchpad returns a structured error and the CLI surfaces it cleanly to the user.

3

Revoke

User runs doma auth revoke. The launchpad calls Privy's removeSigners to detach the agent authorization key from the user's wallet, deletes the allowance row, invalidates the session JWT, and clears ~/.doma/credentials.json.

The user can also revoke from the launchpad's "Authorized agents" panel. Useful if the CLI machine is lost or compromised.

The three signing paths

A given Doma CLI action falls into one of three patterns based on what kind of signature it needs:

Action
RPC method
Signed by
Status

marketplace buy, swap, bridge, dns set, subdomain claim

eth_sendTransaction

wallet's own key (via Privy)

✅ working

marketplace cancel --type on-chain

eth_sendTransaction

wallet's own key

✅ working

marketplace offer, listing, off-chain cancel

eth_signTypedData_v4

agent authorization key, not the wallet

⚠️ off-chain signature limitation

The first two rows are "transactions": they're submitted on-chain and validators only care about from = wallet_address, which is true.

The third row is "off-chain typed data" used by gasless protocols like Seaport. The signing address must equal the wallet address. Today Privy uses the agent authorization key for these, so the signing address ≠ the wallet address, and Seaport rejects the signature.

Known limitation

Gasless typed-data flows (marketplace offer, listing, off-chain cancel) don't work in agent mode today. Workaround: use private-key mode for those specific actions.

The path forward is a smart-wallet migration: instead of the user's EOA, the wallet becomes a smart contract that validates signatures via on-chain logic (ERC-1271). The contract can be programmed to accept signatures from the agent authorization key as if they were the wallet's own. This eliminates the off-chain asymmetry entirely.

Tracked separately; not in scope for V1 of agent mode.

Security posture

  • The launchpad's agent authorization key is rotated on a schedule and stored in HSM-backed cloud KMS. Compromise requires breaching both Privy and the launchpad infra.

  • Session JWTs are short-lived and tied to a specific wallet + allowance row. Theft of a JWT bounds the attacker by the remaining ceiling.

  • The user's wallet key remains in Privy's HSM at all times. Even an attacker with full launchpad access cannot exfiltrate it.

What's next

Last updated