diff --git a/README.md b/README.md index fde4cae334a8..2597792c511e 100644 --- a/README.md +++ b/README.md @@ -99,6 +99,7 @@ All documentation lives at **[hermes-agent.nousresearch.com/docs](https://hermes | [MCP Integration](https://hermes-agent.nousresearch.com/docs/user-guide/features/mcp) | Connect any MCP server for extended capabilities | | [Cron Scheduling](https://hermes-agent.nousresearch.com/docs/user-guide/features/cron) | Scheduled tasks with platform delivery | | [Context Files](https://hermes-agent.nousresearch.com/docs/user-guide/features/context-files) | Project context that shapes every conversation | +| [Wallet](https://hermes-agent.nousresearch.com/docs/user-guide/features/wallet) | Crypto wallet — keystore, transactions, policies, approval flow | | [Architecture](https://hermes-agent.nousresearch.com/docs/developer-guide/architecture) | Project structure, agent loop, key classes | | [Contributing](https://hermes-agent.nousresearch.com/docs/developer-guide/contributing) | Development setup, PR process, code style | | [CLI Reference](https://hermes-agent.nousresearch.com/docs/reference/cli-commands) | All commands and flags | @@ -106,6 +107,38 @@ All documentation lives at **[hermes-agent.nousresearch.com/docs](https://hermes --- +## Crypto Wallet + +Give your agent its own wallet. Hermes can hold funds, check balances, and send transactions on Solana and EVM chains — with encrypted key storage and policy-controlled spending limits. + +```bash +pip install 'hermes-agent[wallet]' # EVM (Ethereum, Base, Polygon, etc.) +pip install 'hermes-agent[wallet-solana]' # + Solana support +``` + +**Quick start:** +```bash +hermes keystore init # Set a master passphrase (one-time) +hermes wallet create --chain solana # Create a fresh wallet +hermes wallet fund # Shows the deposit address +# Send some tokens to the address, then: +hermes wallet balance # Check it arrived +``` + +Add `wallet` to your toolsets in `config.yaml` (or `hermes chat -t hermes-cli,wallet`), and the agent gets 7 tools: `wallet_list`, `wallet_balance`, `wallet_address`, `wallet_send`, `wallet_history`, `wallet_estimate_gas`, `wallet_networks`. + +**Key design:** +- 🔐 Private keys are encrypted at rest (Argon2id + XChaCha20-Poly1305) and never exposed to the agent +- 📋 Policy engine enforces spending limits, rate limits, and approval thresholds +- ✅ **User wallets** require owner approval for every transaction +- 🤖 **Agent wallets** (`hermes wallet create-agent`) auto-approve within configurable limits +- 🔒 Kill switch: `hermes wallet freeze` blocks everything instantly +- 📦 Migration: `hermes wallet export` / `hermes wallet import` to move between machines + +See the [full wallet documentation](https://hermes-agent.nousresearch.com/docs/user-guide/features/wallet) for details. + +--- + ## Migrating from OpenClaw If you're coming from OpenClaw, Hermes can automatically import your settings, memories, skills, and API keys. diff --git a/docs/wallet.md b/docs/wallet.md new file mode 100644 index 000000000000..63b5392a3a6a --- /dev/null +++ b/docs/wallet.md @@ -0,0 +1,83 @@ +# Wallet & Keystore + +## Overview + +Hermes Agent includes an optional crypto wallet with an encrypted keystore. The agent can hold funds, check balances, and send native tokens on Solana and EVM chains — with policy-controlled spending limits and owner approval for transactions. + +## Install + +```bash +pip install 'hermes-agent[wallet]' # EVM chains +pip install 'hermes-agent[wallet-solana]' # + Solana +``` + +## Quick Start + +```bash +hermes keystore init # Set master passphrase +hermes wallet create --chain solana # Create wallet +hermes wallet fund # Show deposit address +hermes wallet balance # Check balance +``` + +Enable the `wallet` toolset in `config.yaml` or via `hermes chat -t hermes-cli,wallet`. + +## Wallet CLI + +| Command | Description | +|---------|-------------| +| `hermes wallet create --chain ` | Create a fresh user wallet | +| `hermes wallet create-agent --chain ` | Create agent wallet (auto-approve within limits) | +| `hermes wallet import --chain ` | Import from exported private key | +| `hermes wallet export` | Export private key for migration | +| `hermes wallet list` | List wallets + balances | +| `hermes wallet balance` | Check balance | +| `hermes wallet send ` | Send tokens (interactive confirmation) | +| `hermes wallet fund` | Show deposit address | +| `hermes wallet history` | Transaction history | +| `hermes wallet freeze` | Kill switch — block everything | +| `hermes wallet unfreeze` | Resume after freeze | +| `hermes wallet status` | Wallet overview | + +## Keystore CLI + +| Command | Description | +|---------|-------------| +| `hermes keystore init` | Create encrypted keystore | +| `hermes keystore list` | List secrets (names only) | +| `hermes keystore set ` | Add/update a secret | +| `hermes keystore show ` | Decrypt and display | +| `hermes keystore delete ` | Remove a secret | +| `hermes keystore migrate` | Import from `.env` | +| `hermes keystore remember` | Cache passphrase in OS credential store | +| `hermes keystore forget` | Remove cached passphrase | +| `hermes keystore change-passphrase` | Re-encrypt everything | +| `hermes keystore audit` | Access log | + +## Agent Tools + +| Tool | Description | +|------|-------------| +| `wallet_list` | List wallets + balances | +| `wallet_balance` | Check specific balance | +| `wallet_address` | Get deposit address | +| `wallet_send` | Send tokens (policy-gated) | +| `wallet_estimate_gas` | Fee estimation | +| `wallet_history` | Transaction log | +| `wallet_networks` | Supported chains | + +## Security + +- **Encryption:** Argon2id KDF + XChaCha20-Poly1305 per-secret AEAD +- **Agent never sees keys:** Private keys are `sealed` — the agent uses tools, not keys +- **Policies:** Spending limits, rate limits, daily caps, approval thresholds, recipient lists +- **User wallets:** Every transaction requires owner approval +- **Agent wallets:** Auto-approve within limits, escalate above threshold +- **Kill switch:** `hermes wallet freeze` — instant, no exceptions + +## Supported Chains + +**Mainnet:** Ethereum, Base, Polygon, Arbitrum, Optimism, Solana +**Testnet:** Ethereum Sepolia, Base Sepolia, Solana Devnet + +Custom RPC endpoints via `wallet.rpc_endpoints` in `config.yaml`. diff --git a/website/docs/user-guide/features/wallet.md b/website/docs/user-guide/features/wallet.md new file mode 100644 index 000000000000..259d7e4e0e55 --- /dev/null +++ b/website/docs/user-guide/features/wallet.md @@ -0,0 +1,254 @@ +--- +sidebar_position: 18 +--- + +# Crypto Wallet + +Give your agent its own crypto wallet. Hermes can hold funds, check balances, and send native tokens on Solana and EVM chains — with encrypted key storage and policy-controlled spending limits. + +The agent **never has access to private keys**. Keys are encrypted at rest in a local keystore, and every transaction goes through a policy engine that enforces spending limits, rate limits, and owner approval thresholds. + +## Installation + +The wallet is an optional extra — install what you need: + +```bash +# EVM chains (Ethereum, Base, Polygon, Arbitrum, Optimism) +pip install 'hermes-agent[wallet]' + +# + Solana support +pip install 'hermes-agent[wallet-solana]' +``` + +## Setup + +### 1. Initialize the encrypted keystore + +The keystore holds all your secrets (API keys, wallet private keys) encrypted with a master passphrase. + +```bash +hermes keystore init +``` + +You'll be prompted to create a passphrase. This is needed each time Hermes starts. To avoid typing it every time: + +```bash +# Save to your OS credential store (macOS Keychain, GNOME Keyring, etc.) +hermes keystore remember + +# Or set an env var (for Docker / systemd / headless) +export HERMES_KEYSTORE_PASSPHRASE="your-passphrase" +``` + +### 2. Create a wallet + +```bash +# Create a user wallet (all sends require your approval) +hermes wallet create --chain solana + +# Or create an agent wallet (auto-approves within policy limits) +hermes wallet create-agent --chain solana --label "Trading Bot" +``` + +:::tip Fresh wallets recommended +We recommend creating fresh wallets for your agent rather than importing personal wallets. Send the agent some tokens to get started — keep your personal funds separate. +::: + +### 3. Fund the wallet + +```bash +hermes wallet fund +``` + +This displays the deposit address. Send tokens to it from your personal wallet or an exchange. + +### 4. Enable the wallet toolset + +Add `wallet` to your toolsets in `~/.hermes/config.yaml`: + +```yaml +toolsets: +- hermes-cli +- wallet +``` + +Or pass it at runtime: + +```bash +hermes chat -t hermes-cli,wallet +``` + +## Agent Tools + +Once the wallet toolset is enabled, the agent gets these tools: + +| Tool | Description | +|------|-------------| +| `wallet_list` | List all wallets with addresses and balances | +| `wallet_balance` | Check balance of a specific wallet | +| `wallet_address` | Get a wallet's deposit address (for sharing / receiving) | +| `wallet_send` | Send native tokens — goes through the policy engine | +| `wallet_estimate_gas` | Estimate transaction fees | +| `wallet_history` | View recent transaction history | +| `wallet_networks` | List supported blockchain networks | + +The agent can check its own balances, share its address to receive funds, estimate fees, and initiate transfers. It **cannot** read private keys, bypass spending policies, or disable the kill switch. + +## CLI Commands + +``` +hermes wallet create Create a new wallet (fresh keypair) +hermes wallet create-agent Create an agent wallet (auto-approve within limits) +hermes wallet import Import wallet from exported private key (migration) +hermes wallet export Export private key for migration to another machine +hermes wallet list List all wallets with balances +hermes wallet balance Check a wallet's balance +hermes wallet send Send tokens (interactive confirmation) +hermes wallet fund Show deposit address for receiving tokens +hermes wallet history View transaction history +hermes wallet freeze Kill switch — block ALL transactions +hermes wallet unfreeze Resume after freeze +hermes wallet status Overview of wallet state +``` + +## Keystore Commands + +The keystore manages all encrypted secrets (API keys, wallet keys): + +``` +hermes keystore init Create a new encrypted keystore +hermes keystore list List stored secrets (names only, no values) +hermes keystore set Add or update a secret +hermes keystore show Decrypt and display a secret +hermes keystore delete Remove a secret +hermes keystore set-category Change a secret's access category +hermes keystore migrate Import secrets from .env file +hermes keystore remember Cache passphrase in OS credential store +hermes keystore forget Remove cached passphrase +hermes keystore change-passphrase Re-encrypt with a new passphrase +hermes keystore audit Show access log +hermes keystore status Show keystore status +``` + +## Security Model + +### Encryption + +- Master key derived from your passphrase via **Argon2id** (memory-hard KDF, 64MB) +- Each secret encrypted with **XChaCha20-Poly1305** (AEAD, random nonce per write) +- Master key held in memory only — never written to disk +- Keystore DB file permissions: `0600`, directory: `0700` + +### Secret Categories + +| Category | Who can access | Examples | +|----------|---------------|----------| +| `injectable` | Agent (via `os.environ`) | API keys — `OPENROUTER_API_KEY` | +| `gated` | Agent on request (logged) | `GITHUB_TOKEN` | +| `sealed` | **Never** the agent | Wallet private keys | +| `user_only` | CLI only | `SUDO_PASSWORD` | + +### Policy Engine + +Every transaction is evaluated against a configurable set of policies: + +| Policy | Description | Default (agent wallet) | +|--------|-------------|----------------------| +| `spending_limit` | Max per transaction | 1.0 native token | +| `daily_limit` | Aggregate daily cap | 5.0 native token | +| `rate_limit` | Max transactions per window | 5 per hour | +| `cooldown` | Minimum time between txns | 30 seconds | +| `require_approval` | Owner approval above threshold | 0.5 native token | +| `allowed_recipients` | Address whitelist | — | +| `blocked_recipients` | Address blacklist | — | + +**User wallets** require owner approval for all transactions by default. + +**Agent wallets** auto-approve within limits — transactions above the threshold trigger an owner approval prompt. + +### Kill Switch + +```bash +hermes wallet freeze +``` + +Instantly blocks all transactions across all wallets. No policy exceptions. Resume with `hermes wallet unfreeze`. + +## Transaction Approval + +When a transaction requires approval: + +**CLI mode:** An interactive prompt appears with the transaction details and approve/deny choices — identical to the dangerous command approval prompt. + +**Gateway mode (Telegram/Discord/etc.):** The transaction summary is shown with instructions to reply `/approve` or `/deny`. + +## Supported Networks + +### Mainnets +- Ethereum (ETH) +- Base (ETH) +- Polygon (POL) +- Arbitrum One (ETH) +- Optimism (ETH) +- Solana (SOL) + +### Testnets +- Ethereum Sepolia +- Base Sepolia +- Solana Devnet + +### Custom RPC Endpoints + +Override default RPC endpoints in `config.yaml`: + +```yaml +wallet: + rpc_endpoints: + solana: "https://my-custom-rpc.example.com" + ethereum: "https://eth-mainnet.alchemyapi.io/v2/YOUR_KEY" +``` + +## Migration Between Machines + +To move a wallet to a new machine: + +**On the source machine:** +```bash +hermes wallet export --chain solana +# Re-enter your keystore passphrase +# Private key is displayed — copy it securely +``` + +**On the destination machine:** +```bash +hermes keystore init # Set up keystore (if not already done) +hermes wallet import --chain solana --type agent +# Paste the private key when prompted +``` + +:::warning +The exported private key gives full control of the wallet. Never share it, transmit it over unencrypted channels, or store it in plaintext. +::: + +## Configuration + +Full wallet configuration in `~/.hermes/config.yaml`: + +```yaml +wallet: + enabled: true + default_chain: solana + + # Override default RPC endpoints + rpc_endpoints: + solana: "https://api.mainnet-beta.solana.com" + ethereum: "https://eth.llamarpc.com" + + # Agent wallet policy overrides (tightens defaults, cannot loosen) + agent_wallet: + enabled: true + auto_approve_below_native: "0.5" + daily_limit_native: "5.0" + max_per_tx_native: "1.0" + rate_limit: "5/hour" +```