<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Wallet Guy</title>
    <description>The latest articles on DEV Community by Wallet Guy (@walletguy).</description>
    <link>https://dev.to/walletguy</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F3839576%2Fca8024e8-c8ac-4f6a-845c-e8ad44732a67.jpeg</url>
      <title>DEV Community: Wallet Guy</title>
      <link>https://dev.to/walletguy</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/walletguy"/>
    <language>en</language>
    <item>
      <title>Hardware-Secured Trading Bots: D'CENT Integration for High-Value DeFi Operations</title>
      <dc:creator>Wallet Guy</dc:creator>
      <pubDate>Tue, 07 Jul 2026 10:03:57 +0000</pubDate>
      <link>https://dev.to/walletguy/hardware-secured-trading-bots-dcent-integration-for-high-value-defi-operations-3e9n</link>
      <guid>https://dev.to/walletguy/hardware-secured-trading-bots-dcent-integration-for-high-value-defi-operations-3e9n</guid>
      <description>&lt;h1&gt;
  
  
  Hardware-Secured Trading Bots: D'CENT Integration for High-Value DeFi Operations
&lt;/h1&gt;

&lt;p&gt;Hardware-secured trading bots are no longer a luxury — for high-value DeFi operations, they're the difference between sleeping soundly and watching your treasury drain overnight. If you're running arbitrage systems, MEV strategies, or algorithmic trading across multiple protocols, you already know the signing layer is your biggest attack surface. WAIaaS addresses this directly with D'CENT hardware wallet integration for human-in-the-loop signing, wrapped inside a full-stack wallet infrastructure designed for automated agents.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why the Signing Layer Is Your Biggest Risk
&lt;/h2&gt;

&lt;p&gt;Most trading bot architectures treat the private key as an operational detail — stuff it in an environment variable, load it at runtime, sign transactions in memory. That works until it doesn't. Compromised servers, leaked &lt;code&gt;.env&lt;/code&gt; files, supply chain attacks on npm packages — any of these can drain a hot wallet in seconds. The faster your bot executes, the faster an attacker can too.&lt;/p&gt;

&lt;p&gt;At the same time, pure cold storage doesn't work for automated systems. You can't physically approve every Jupiter swap or Drift perp position. What you actually need is a tiered system: most operations run automatically under defined rules, but specific high-value transactions require hardware confirmation. That's the model WAIaaS is built around.&lt;/p&gt;

&lt;h2&gt;
  
  
  What WAIaaS Provides for Trading Bot Infrastructure
&lt;/h2&gt;

&lt;p&gt;Before getting into the hardware security angle, it's worth understanding what's underneath. WAIaaS is a 15-package monorepo running a daemon process that exposes 39 REST API route modules. Your trading bot talks to this daemon via a session token — the bot never touches private keys directly.&lt;/p&gt;

&lt;p&gt;The infrastructure includes:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;15 DeFi protocol providers&lt;/strong&gt;: aave-v3, across, dcent-swap, drift, erc8004, hyperliquid, jito-staking, jupiter-swap, kamino, lido-staking, lifi, pendle, polymarket, xrpl-dex, zerox-swap&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;7 transaction types&lt;/strong&gt;: Transfer, TokenTransfer, ContractCall, Approve, Batch, NftTransfer, ContractDeploy&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;7-stage transaction pipeline&lt;/strong&gt;: validate → auth → policy → wait → execute → confirm&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;45 MCP tools&lt;/strong&gt; for AI agent integration&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;2 chain types&lt;/strong&gt; (EVM and Solana) across 18 networks&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;For a trading bot, the relevant part is that you get a single API surface for Jupiter swaps, Drift perpetuals, Hyperliquid spot and perps, LI.FI bridging, and Across cross-chain — with the same auth model and the same policy engine governing all of them.&lt;/p&gt;

&lt;h2&gt;
  
  
  D'CENT Integration: Hardware-in-the-Loop for High-Value Ops
&lt;/h2&gt;

&lt;p&gt;The D'CENT integration in WAIaaS is implemented as a signing channel — specifically one of three signing channels (push-relay-signing-channel, telegram-signing-channel, wallet-notification-channel) that route transaction approval requests to external signers.&lt;/p&gt;

&lt;p&gt;What this means practically: your bot submits a transaction through the standard API. The transaction hits the 7-stage pipeline. At the policy stage, if the transaction exceeds your APPROVAL tier threshold, the pipeline pauses and routes the signing request to your D'CENT device. You physically confirm on the hardware wallet. The pipeline resumes and executes.&lt;/p&gt;

&lt;p&gt;For trading operations, you configure this threshold carefully. You might want:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Small rebalancing trades (&amp;lt; $100) to execute instantly with no friction&lt;/li&gt;
&lt;li&gt;Medium-sized swaps ($100–$1,000) to notify you but execute automatically
&lt;/li&gt;
&lt;li&gt;Large position entries ($1,000–$10,000) to delay 15 minutes, giving you a cancellation window&lt;/li&gt;
&lt;li&gt;Anything above $10,000 or unusual contract interactions to require D'CENT hardware confirmation&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Configuring the Policy Engine for Trading Operations
&lt;/h2&gt;

&lt;p&gt;The policy engine has 21 policy types. For a trading bot, the core ones you'll configure are SPENDING_LIMIT, CONTRACT_WHITELIST, ALLOWED_TOKENS, PERP_MAX_LEVERAGE, PERP_MAX_POSITION_USD, PERP_ALLOWED_MARKETS, and VENUE_WHITELIST.&lt;/p&gt;

&lt;p&gt;Start with a SPENDING_LIMIT that maps to your risk tolerance:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "SPENDING_LIMIT",
    "rules": {
      "instant_max_usd": 100,
      "notify_max_usd": 500,
      "delay_max_usd": 2000,
      "delay_seconds": 900,
      "daily_limit_usd": 5000
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This gives you four tiers: instant execution under $100, notification at $100–$500, 15-minute delay at $500–$2,000, and full APPROVAL (via D'CENT or other signing channel) above $2,000. The &lt;code&gt;delay_seconds: 900&lt;/code&gt; means large trades queue for 15 minutes — enough time to catch anomalous bot behavior before it executes.&lt;/p&gt;

&lt;p&gt;The policy system is default-deny. If you don't configure ALLOWED_TOKENS, token transfers are blocked. If you don't configure CONTRACT_WHITELIST, contract calls are blocked. This is intentional — a compromised session token can't suddenly start sending tokens to unknown addresses or calling arbitrary contracts.&lt;/p&gt;

&lt;p&gt;For perpetual futures operations on Hyperliquid or Drift, you have dedicated policy types:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"PERP_MAX_LEVERAGE"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"rules"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"max_leverage"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;10&lt;/span&gt;&lt;span class="p"&gt;}}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"PERP_MAX_POSITION_USD"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"rules"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"max_position_usd"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;50000&lt;/span&gt;&lt;span class="p"&gt;}}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"type"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"PERP_ALLOWED_MARKETS"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"rules"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"markets"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"BTC-USD"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"ETH-USD"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"SOL-USD"&lt;/span&gt;&lt;span class="p"&gt;]}}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;These enforce risk limits at the infrastructure level, not the application level. Even if your bot's logic has a bug and tries to open a 50x leveraged position in a small-cap market, the policy engine blocks it before the transaction ever reaches the chain.&lt;/p&gt;

&lt;h2&gt;
  
  
  Gas Conditional Execution
&lt;/h2&gt;

&lt;p&gt;One of the more useful features for trading bots is gas conditional execution — transactions execute only when gas price meets your configured threshold. For EVM operations, this means your bot can queue a transaction and the pipeline will wait until gas drops below your threshold before executing.&lt;/p&gt;

&lt;p&gt;This matters for strategies that aren't time-critical. If you're rebalancing a Aave position or collecting yield, there's no reason to pay peak gas. Queue the transaction, set your gas condition, and let the pipeline handle timing. Your bot doesn't need to implement gas monitoring logic — it's handled at the infrastructure layer.&lt;/p&gt;

&lt;h2&gt;
  
  
  Executing Multi-Protocol Trading Strategies
&lt;/h2&gt;

&lt;p&gt;Here's what a real trading operation looks like through the API. Your bot spots an arbitrage opportunity: buy on Jupiter, hedge the delta on Drift. Two separate calls, one session token:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Leg 1: Swap on Jupiter&lt;/span&gt;
curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/actions/jupiter-swap/swap &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "inputMint": "So11111111111111111111111111111111111111112",
    "outputMint": "EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v",
    "amount": "1000000000"
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Before committing to the trade, your bot can simulate first:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Dry-run to validate before execution&lt;/span&gt;
curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/send &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "type": "TRANSFER",
    "to": "recipient-address",
    "amount": "0.1",
    "dryRun": true
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The dry-run API lets you simulate transactions before execution. For arb systems where execution failure has a cost (locked capital, partial fills), validating the transaction path before committing is worth the extra round-trip.&lt;/p&gt;

&lt;p&gt;If a transaction hits the APPROVAL tier and needs D'CENT confirmation, the approval endpoint is:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/&amp;lt;tx-id&amp;gt;/approve &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Owner-Signature: &amp;lt;ed25519-or-secp256k1-signature&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Owner-Message: &amp;lt;signed-message&amp;gt;"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The owner authentication uses ed25519 or secp256k1 signatures — the same cryptographic primitives your hardware wallet produces. D'CENT signs the approval message, you pass the signature to the endpoint, the pipeline resumes.&lt;/p&gt;

&lt;h2&gt;
  
  
  Three-Layer Security Model
&lt;/h2&gt;

&lt;p&gt;WAIaaS uses three auth methods that map to three distinct principals:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;masterAuth&lt;/strong&gt; (Argon2id): the system operator — creates wallets, manages sessions, sets policies&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;sessionAuth&lt;/strong&gt; (JWT HS256): the trading bot — executes transactions within policy bounds&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;ownerAuth&lt;/strong&gt; (SIWE/SIWS signatures): the fund owner — approves high-value transactions, emergency kill switch&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;For a trading operation, your bot only ever holds a session token. That token is scoped to one wallet, operates within the policies you've set, and can be revoked instantly. Session tokens have configurable TTL, maxRenewals, and absoluteLifetime. A compromised session token has bounded damage — it can only do what the policies allow, and only until the token expires.&lt;/p&gt;

&lt;p&gt;The owner layer is where D'CENT fits. The fund owner's approval (hardware-signed) is required for APPROVAL-tier transactions. Even if someone gains access to your server and the session token, they cannot move funds that exceed your DELAY threshold without hardware confirmation from the owner.&lt;/p&gt;

&lt;h2&gt;
  
  
  Quick Start for Trading Bot Builders
&lt;/h2&gt;

&lt;p&gt;Getting a secured trading infrastructure running takes about 10 minutes:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 1: Deploy the daemon&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;docker run &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--name&lt;/span&gt; waiaas &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-p&lt;/span&gt; 127.0.0.1:3100:3100 &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-v&lt;/span&gt; waiaas-data:/data &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-e&lt;/span&gt; &lt;span class="nv"&gt;WAIAAS_AUTO_PROVISION&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nb"&gt;true&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  ghcr.io/minhoyoo-iotrust/waiaas:latest

docker &lt;span class="nb"&gt;exec &lt;/span&gt;waiaas &lt;span class="nb"&gt;cat&lt;/span&gt; /data/recovery.key
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 2: Create a trading wallet and session&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Create wallet&lt;/span&gt;
curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/wallets &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"name": "trading-wallet", "chain": "solana", "environment": "mainnet"}'&lt;/span&gt;

&lt;span class="c"&gt;# Create session for your bot&lt;/span&gt;
curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/sessions &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"walletId": "&amp;lt;wallet-uuid&amp;gt;"}'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 3: Set trading policies&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Configure SPENDING_LIMIT, CONTRACT_WHITELIST, and ALLOWED_TOKENS before your bot starts operating. Default-deny means nothing works until you explicitly allow it — which is exactly what you want for a production trading system.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 4: Connect your bot via SDK&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSClient&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSError&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@waiaas/sdk&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;WAIaaSClient&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="na"&gt;baseUrl&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;WAIAAS_BASE_URL&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;??&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;http://localhost:3100&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;sessionToken&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;WAIAAS_SESSION_TOKEN&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;balance&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getBalance&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`Balance: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt; &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;symbol&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt; (&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;chain&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;/&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;network&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;)`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="k"&gt;try&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;tx&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;sendToken&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
    &lt;span class="na"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;TRANSFER&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;to&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;recipient-address&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;amount&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;0.001&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;});&lt;/span&gt;
  &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`Transaction submitted: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;tx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt; (status: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;tx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;status&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;)`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;catch &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;error&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;error&lt;/span&gt; &lt;span class="k"&gt;instanceof&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSError&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;error&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`API Error: [&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;error&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;code&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;] &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;error&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;message&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="c1"&gt;// Handles: INSUFFICIENT_BALANCE, POLICY_DENIED, TOKEN_EXPIRED&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 5: Explore the API reference&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;The OpenAPI 3.0 spec is auto-generated and available at &lt;code&gt;/doc&lt;/code&gt;. The interactive Scalar API reference UI is at &lt;code&gt;/reference&lt;/code&gt;. All 39 route modules are documented there — useful when you're integrating specific DeFi protocol endpoints.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;open http://127.0.0.1:3100/reference
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Production Hardening
&lt;/h2&gt;

&lt;p&gt;For production deployments handling real capital, use Docker Secrets instead of environment variables:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; secrets
&lt;span class="nb"&gt;echo&lt;/span&gt; &lt;span class="s2"&gt;"your-secure-password"&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; secrets/master_password.txt
&lt;span class="nb"&gt;chmod &lt;/span&gt;600 secrets/master_password.txt

docker compose &lt;span class="nt"&gt;-f&lt;/span&gt; docker-compose.yml &lt;span class="nt"&gt;-f&lt;/span&gt; docker-compose.secrets.yml up &lt;span class="nt"&gt;-d&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The secrets overlay (&lt;code&gt;docker-compose.secrets.yml&lt;/code&gt;) routes your master password through Docker Secrets rather than environment variables, keeping it out of &lt;code&gt;docker inspect&lt;/code&gt; output and process lists.&lt;/p&gt;

&lt;p&gt;The daemon runs as a non-root user (UID 1001) and includes healthcheck configuration out of the box. For automated deployments, the entrypoint supports auto-provision mode — useful for ephemeral environments where you don't want to manage password rotation manually.&lt;/p&gt;

&lt;h2&gt;
  
  
  What's Next
&lt;/h2&gt;

&lt;p&gt;The architecture described here — hardware-confirmed high-value transactions, policy-bounded session tokens, multi-protocol DeFi access through a single API — is the foundation for building trading systems that can actually operate at scale without keeping you up at night. The 683+ test files across the WAIaaS codebase reflect the level of reliability this kind of infrastructure demands.&lt;/p&gt;

&lt;p&gt;Explore the full codebase and contribute at &lt;a href="https://github.com/minhoyoo-iotrust/WAIaaS" rel="noopener noreferrer"&gt;GitHub&lt;/a&gt;, or check the documentation and deployment guides at &lt;a href="https://waiaas.ai" rel="noopener noreferrer"&gt;waiaas.ai&lt;/a&gt;. If you're building something serious on top of this, the 45 MCP tools and OpenClaw plugin are worth looking at for AI agent integration beyond direct API calls.&lt;/p&gt;

</description>
      <category>security</category>
      <category>defi</category>
      <category>trading</category>
      <category>hardware</category>
    </item>
    <item>
      <title>The API Payment Revolution: Building x402 Infrastructure for Autonomous Machines</title>
      <dc:creator>Wallet Guy</dc:creator>
      <pubDate>Mon, 06 Jul 2026 16:28:19 +0000</pubDate>
      <link>https://dev.to/walletguy/the-api-payment-revolution-building-x402-infrastructure-for-autonomous-machines-2f6f</link>
      <guid>https://dev.to/walletguy/the-api-payment-revolution-building-x402-infrastructure-for-autonomous-machines-2f6f</guid>
      <description>&lt;h1&gt;
  
  
  The API Payment Revolution: Building x402 Infrastructure for Autonomous Machines
&lt;/h1&gt;

&lt;p&gt;AI agents will need to pay for compute, data, and API calls — and right now, almost no infrastructure exists to let them do it autonomously. We talk endlessly about agentic AI, multi-agent systems, and autonomous workflows, but there's a gap nobody likes to admit: agents can't actually pay for things. Not independently. Not without a human holding the credit card somewhere in the loop.&lt;/p&gt;

&lt;p&gt;That gap is closing. Here's what the plumbing looks like today.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Real Problem with "Autonomous" Agents
&lt;/h2&gt;

&lt;p&gt;Spend five minutes with any serious AI agent framework and you'll hit the same wall. The agent can reason, plan, and execute — until it needs to spend money. Then it either stops and asks a human, or it operates inside some pre-funded, centrally managed account that a human topped up before the session started.&lt;/p&gt;

&lt;p&gt;That's not autonomous. That's supervised.&lt;/p&gt;

&lt;p&gt;The economics of the emerging agent layer are going to look very different from today's SaaS billing. Agents won't pay monthly subscriptions. They'll pay per inference call, per API request, per dataset query. The billing model will look more like a vending machine than a software license — and the machine doing the paying will be the agent itself.&lt;/p&gt;

&lt;p&gt;This requires two things working together: a payment protocol that operates at HTTP layer (so agents can pay for API calls inline, without a separate billing integration), and wallet infrastructure that the agent can actually operate. Not wallet infrastructure managed on behalf of the agent. Infrastructure the agent holds and uses directly.&lt;/p&gt;

&lt;p&gt;That combination exists today with x402 and WAIaaS. Let's look at how it works.&lt;/p&gt;

&lt;h2&gt;
  
  
  x402: Payments as HTTP
&lt;/h2&gt;

&lt;p&gt;The x402 HTTP payment protocol is elegant in its simplicity. When an API requires payment, it returns an HTTP 402 ("Payment Required") status with payment terms in the response headers. The client — in this case an AI agent — sees the 402, pays the stated amount using its wallet, attaches a payment receipt to the retry request, and gets the resource.&lt;/p&gt;

&lt;p&gt;The entire payment happens inline with the API call. No billing dashboard. No OAuth flow for payment authorization. No human in the loop. The agent reads the 402, executes the payment, and continues.&lt;/p&gt;

&lt;p&gt;WAIaaS exposes this as a first-class capability via the &lt;code&gt;x402Fetch&lt;/code&gt; method in the TypeScript SDK:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSClient&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@waiaas/sdk&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;WAIaaSClient&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="na"&gt;baseUrl&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;http://127.0.0.1:3100&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;sessionToken&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;WAIAAS_SESSION_TOKEN&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;

&lt;span class="c1"&gt;// This fetch handles 402 responses automatically&lt;/span&gt;
&lt;span class="c1"&gt;// If the endpoint charges for access, the agent pays inline&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;response&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;x402Fetch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;https://api.example.com/inference-data&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's it. The agent calls &lt;code&gt;x402Fetch&lt;/code&gt; instead of the standard &lt;code&gt;fetch&lt;/code&gt;, and WAIaaS handles the 402 negotiation, payment execution, and retry transparently. From the agent's perspective, it made an API call and got data back. The payment was infrastructure.&lt;/p&gt;

&lt;p&gt;The MCP layer exposes this same capability as the &lt;code&gt;x402-fetch&lt;/code&gt; tool, so agents operating through Claude Desktop or any MCP-compatible host can make paid API calls directly — without custom code.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Wallet Infrastructure Layer
&lt;/h2&gt;

&lt;p&gt;x402 handles the payment protocol. But the agent still needs a wallet it can actually operate. That's the harder problem.&lt;/p&gt;

&lt;p&gt;A wallet an agent can "operate" means several things:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The agent can check its own balance&lt;/li&gt;
&lt;li&gt;The agent can sign and submit transactions&lt;/li&gt;
&lt;li&gt;The agent can execute DeFi actions (swapping, bridging, staking) without human involvement&lt;/li&gt;
&lt;li&gt;The wallet has guardrails so the agent can't do catastrophic things even if it misbehaves or gets compromised&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;WAIaaS is built specifically for this. It's a self-hosted Wallet-as-a-Service that runs as a daemon — a 15-package monorepo with a REST API, CLI, and MCP server — designed for the case where the "user" is an AI agent rather than a human.&lt;/p&gt;

&lt;p&gt;The architecture separates concerns cleanly:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;masterAuth&lt;/strong&gt; (Argon2id): System administrator — creates wallets, manages sessions, sets policies&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;sessionAuth&lt;/strong&gt; (JWT HS256): The AI agent — executes transactions within the bounds the admin established&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;ownerAuth&lt;/strong&gt; (SIWS/SIWE signatures): The fund owner — approves large transactions, has kill switch access&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The agent gets a session token. It uses that token for everything it does. The token operates within whatever policy envelope the admin configured. The owner can intervene at any time via WalletConnect or other signing channels.&lt;/p&gt;

&lt;h2&gt;
  
  
  What the Agent Can Actually Do
&lt;/h2&gt;

&lt;p&gt;The session token the agent holds is a key to 45 MCP tools and a full REST API. The agent can:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Check balances and portfolio state:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl http://127.0.0.1:3100/v1/wallet/balance &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_eyJhbGciOiJIUzI1NiJ9..."&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Send tokens:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/send &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "type": "TRANSFER",
    "to": "recipient-address",
    "amount": "0.1"
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Execute DeFi operations&lt;/strong&gt; — including swaps on Jupiter (Solana), lending on Aave v3, perpetual futures on Hyperliquid, prediction market trades on Polymarket, and more across 15 integrated DeFi protocol providers.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/actions/jupiter-swap/swap &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "inputMint": "So11111111111111111111111111111111111111112",
    "outputMint": "EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v",
    "amount": "1000000000"
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Simulate before executing:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/send &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "type": "TRANSFER",
    "to": "recipient-address",
    "amount": "0.1",
    "dryRun": true
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The dry-run capability matters a lot for autonomous agents. Before committing a transaction, the agent can verify what would happen — simulating outcomes without on-chain consequences. For agents operating in production with real funds, this is the difference between "execute and hope" and "verify then execute."&lt;/p&gt;

&lt;p&gt;Every transaction goes through a 7-stage pipeline: validate → auth → policy → wait → execute → confirm. The policy stage is where guardrails live.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Policy Layer: Autonomy with Guardrails
&lt;/h2&gt;

&lt;p&gt;Here's the tension that makes wallet infrastructure for AI agents genuinely hard: you want the agent to be autonomous, but you don't want it to drain the wallet in one bad decision or one compromised session.&lt;/p&gt;

&lt;p&gt;WAIaaS resolves this with a policy engine that enforces constraints at the infrastructure level — not in the agent's code, where they can be bypassed, but in the transaction pipeline itself.&lt;/p&gt;

&lt;p&gt;There are 21 policy types organized around 4 security tiers:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;INSTANT&lt;/strong&gt;: Execute immediately, no notification&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;NOTIFY&lt;/strong&gt;: Execute immediately, send notification to owner&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;DELAY&lt;/strong&gt;: Queue the transaction for N seconds, then execute (cancellable window)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;APPROVAL&lt;/strong&gt;: Require explicit human approval before execution&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;A spending limit policy wires these tiers to dollar amounts:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "SPENDING_LIMIT",
    "rules": {
      "instant_max_usd": 100,
      "notify_max_usd": 500,
      "delay_max_usd": 2000,
      "delay_seconds": 900,
      "daily_limit_usd": 5000
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With this policy in place, an agent handling x402 micro-payments (say, $0.01 per API call) operates completely autonomously — those transactions are well under &lt;code&gt;instant_max_usd&lt;/code&gt;. A $300 transaction triggers a notification to the owner but still executes. A $1,500 transaction waits 15 minutes, giving the owner a window to cancel if something looks wrong. Anything over $2,000 requires explicit approval.&lt;/p&gt;

&lt;p&gt;The policy engine also enforces default-deny on token transfers and contract interactions. If &lt;code&gt;ALLOWED_TOKENS&lt;/code&gt; isn't configured, the agent can't transfer any tokens. If &lt;code&gt;CONTRACT_WHITELIST&lt;/code&gt; isn't configured, the agent can't call contracts. The default is locked down — you explicitly expand permissions rather than trying to block bad behaviors after the fact.&lt;/p&gt;

&lt;p&gt;For DeFi-specific risk management, there are policies like &lt;code&gt;LENDING_LTV_LIMIT&lt;/code&gt; (caps loan-to-value ratio in lending protocols), &lt;code&gt;PERP_MAX_LEVERAGE&lt;/code&gt; (maximum leverage on perpetual futures positions), and &lt;code&gt;PERP_MAX_POSITION_USD&lt;/code&gt; (maximum position size). An agent managing a treasury or yield strategy operates within these bounds automatically — the infrastructure enforces the risk parameters, not the agent's code.&lt;/p&gt;

&lt;p&gt;The x402 domain whitelist is particularly relevant here:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"domains"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"api.example.com"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"*.openai.com"&lt;/span&gt;&lt;span class="p"&gt;]}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;X402_ALLOWED_DOMAINS&lt;/code&gt; policy restricts which domains the agent can make x402 payments to. An agent authorized to pay for inference and data APIs can't suddenly start paying arbitrary addresses — only the domains you've explicitly approved.&lt;/p&gt;

&lt;h2&gt;
  
  
  Getting This Running
&lt;/h2&gt;

&lt;p&gt;The fastest path from zero to a working agent wallet is through the CLI:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;-g&lt;/span&gt; @waiaas/cli
waiaas init                        &lt;span class="c"&gt;# Create data directory + config.toml&lt;/span&gt;
waiaas start                       &lt;span class="c"&gt;# Start daemon (sets master password on first run)&lt;/span&gt;
waiaas quickset &lt;span class="nt"&gt;--mode&lt;/span&gt; mainnet     &lt;span class="c"&gt;# Create wallets + MCP sessions in one step&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After &lt;code&gt;quickset&lt;/code&gt;, you'll have wallet addresses, session tokens, and an MCP configuration you can paste directly into Claude Desktop. The &lt;code&gt;waiaas mcp setup --all&lt;/code&gt; command auto-registers everything with Claude.&lt;/p&gt;

&lt;p&gt;If you prefer Docker:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;docker run &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--name&lt;/span&gt; waiaas &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-p&lt;/span&gt; 127.0.0.1:3100:3100 &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-v&lt;/span&gt; waiaas-data:/data &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-e&lt;/span&gt; &lt;span class="nv"&gt;WAIAAS_AUTO_PROVISION&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nb"&gt;true&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  ghcr.io/minhoyoo-iotrust/waiaas:latest

docker &lt;span class="nb"&gt;exec &lt;/span&gt;waiaas &lt;span class="nb"&gt;cat&lt;/span&gt; /data/recovery.key
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;WAIAAS_AUTO_PROVISION=true&lt;/code&gt; flag generates a random master password on first start and writes it to &lt;code&gt;recovery.key&lt;/code&gt;. You can harden it later with &lt;code&gt;waiaas set-master&lt;/code&gt; once you've confirmed everything is running.&lt;/p&gt;

&lt;p&gt;For production deployments, Docker Secrets integration avoids environment variable exposure:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; secrets
&lt;span class="nb"&gt;echo&lt;/span&gt; &lt;span class="s2"&gt;"your-secure-password"&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; secrets/master_password.txt
&lt;span class="nb"&gt;chmod &lt;/span&gt;600 secrets/master_password.txt

docker compose &lt;span class="nt"&gt;-f&lt;/span&gt; docker-compose.yml &lt;span class="nt"&gt;-f&lt;/span&gt; docker-compose.secrets.yml up &lt;span class="nt"&gt;-d&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  The Agent Economy Isn't Hypothetical
&lt;/h2&gt;

&lt;p&gt;It's worth being direct about where this stands: x402 payments and autonomous agent wallets aren't speculative architecture. They work today. WAIaaS has 45 MCP tools covering wallet operations, token transfers, DeFi positions, NFT management, and x402 payments. It supports 18 networks across EVM and Solana. The TypeScript and Python SDKs exist, are documented, and have working code.&lt;/p&gt;

&lt;p&gt;What's still early is the supply side — the number of APIs that return 402 responses and accept x402 payments. That ecosystem is growing. But the agent-side infrastructure, the part that lets an agent receive a 402, execute a payment, and continue — that part is ready.&lt;/p&gt;

&lt;p&gt;ERC-8004 trustless agent reputation (exposed via WAIaaS's &lt;code&gt;erc8004-get-reputation&lt;/code&gt; and &lt;code&gt;erc8004-get-validation-status&lt;/code&gt; MCP tools) adds another dimension: agents that can prove their behavioral track record on-chain. When one agent is evaluating whether to transact with another agent — or when a human owner is deciding how much autonomy to grant — on-chain reputation becomes the trust primitive that makes multi-agent economic interactions possible without requiring human mediation for every handshake.&lt;/p&gt;

&lt;p&gt;The picture coming into focus: agents with wallets, operating under policy guardrails, paying for API calls inline via x402, and establishing trust through on-chain reputation. Not science fiction. Infrastructure you can deploy this afternoon.&lt;/p&gt;

&lt;h2&gt;
  
  
  What's Next
&lt;/h2&gt;

&lt;p&gt;The GitHub repository at &lt;a href="https://github.com/minhoyoo-iotrust/WAIaaS" rel="noopener noreferrer"&gt;https://github.com/minhoyoo-iotrust/WAIaaS&lt;/a&gt; has the full codebase, including the Docker Compose setup, CLI, and SDK packages. The OpenAPI spec is auto-generated and served at &lt;code&gt;/doc&lt;/code&gt; with an interactive Scalar UI at &lt;code&gt;/reference&lt;/code&gt; once your daemon is running — which is the fastest way to explore the full 39-route API surface.&lt;/p&gt;

&lt;p&gt;If you're building agent infrastructure and thinking seriously about how autonomous systems participate in economic activity, &lt;a href="https://waiaas.ai" rel="noopener noreferrer"&gt;https://waiaas.ai&lt;/a&gt; is worth bookmarking. The agent economy is going to need payment rails that work at machine speed, and the foundation for that is being built in the open right now.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>web3</category>
      <category>api</category>
      <category>payments</category>
    </item>
    <item>
      <title>Trustless Trading Bots: ERC-8004 Onchain Reputation for Automated DeFi</title>
      <dc:creator>Wallet Guy</dc:creator>
      <pubDate>Mon, 06 Jul 2026 11:08:29 +0000</pubDate>
      <link>https://dev.to/walletguy/trustless-trading-bots-erc-8004-onchain-reputation-for-automated-defi-472k</link>
      <guid>https://dev.to/walletguy/trustless-trading-bots-erc-8004-onchain-reputation-for-automated-defi-472k</guid>
      <description>&lt;h1&gt;
  
  
  Trustless Trading Bots: ERC-8004 Onchain Reputation for Automated DeFi
&lt;/h1&gt;

&lt;p&gt;Trustless trading bots that execute DeFi strategies autonomously sound great until you ask the hard question: how does anyone — a protocol, a counterparty, a smart contract — actually verify that your bot is what it claims to be? Reputation in DeFi has always been fragile, off-chain, and easy to fake. ERC-8004 changes that, and WAIaaS ships with native support for it alongside 15 integrated DeFi protocols — so you can build a bot that doesn't just trade, but proves itself onchain.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why Onchain Agent Reputation Actually Matters
&lt;/h2&gt;

&lt;p&gt;If you've built a DeFi trading bot before, you've dealt with the trust problem from the other direction: you're the one who has to trust the protocols, the oracles, the RPC endpoints. But as automated agents become more capable — executing multi-step strategies across Jupiter swaps, Aave lending positions, Hyperliquid perps, and Lido staking in a single session — the question flips. Protocols, DAOs, and other agents need a way to trust &lt;em&gt;your&lt;/em&gt; bot.&lt;/p&gt;

&lt;p&gt;ERC-8004 is a standard for onchain agent reputation and validation. Instead of your bot just asserting "I'm authorized," it can present cryptographically verifiable reputation data that lives on-chain. This matters for DeFi specifically because you're often interacting with smart contracts that could gate access, apply different fee tiers, or require proof of trustworthiness before allowing high-value operations. Without something like ERC-8004, your bot is a black box to everyone it interacts with.&lt;/p&gt;

&lt;p&gt;WAIaaS has built ERC-8004 support directly into its architecture — both as a DeFi action provider (&lt;code&gt;erc8004&lt;/code&gt; in the protocol list) and as MCP tools (&lt;code&gt;erc8004-get-agent-info&lt;/code&gt;, &lt;code&gt;erc8004-get-reputation&lt;/code&gt;, &lt;code&gt;erc8004-get-validation-status&lt;/code&gt;) that AI agents can call directly. Combined with 14 other protocol integrations and a policy engine that enforces rules before any transaction executes, it's the infrastructure layer for building bots that are both capable and verifiable.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Protocol Stack Your Bot Actually Needs
&lt;/h2&gt;

&lt;p&gt;Let's be concrete. A serious DeFi trading bot in 2026 isn't just doing spot swaps. It's managing positions across multiple layers: swapping on DEXes, lending/borrowing for leverage, staking idle assets, bridging between chains, and sometimes trading perps. WAIaaS integrates 15 DeFi protocol providers:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;EVM side:&lt;/strong&gt; Aave v3 (lending), Lido (liquid staking), 0x Swap, LI.FI (cross-chain bridging), Across (bridging), Pendle (yield tokenization), Polymarket (prediction markets)&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Solana side:&lt;/strong&gt; Jupiter Swap, Kamino (lending/vaults), Jito (liquid staking), Drift (perpetuals), D'CENT swap, XRPL DEX&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Cross-chain/meta:&lt;/strong&gt; Hyperliquid (perpetuals and spot), ERC-8004 (agent reputation)&lt;/p&gt;

&lt;p&gt;Instead of maintaining 15 separate SDKs, authentication flows, and error handling implementations, you make a single API call pattern. Here's what executing a Jupiter swap looks like:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/actions/jupiter-swap/swap &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "inputMint": "So11111111111111111111111111111111111111112",
    "outputMint": "EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v",
    "amount": "1000000000"
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's SOL → USDC on Jupiter. The same &lt;code&gt;Authorization&lt;/code&gt; header and the same request pattern works across every protocol. Your bot doesn't need to know how Jupiter constructs its versioned transactions under the hood — that complexity lives inside WAIaaS.&lt;/p&gt;

&lt;h2&gt;
  
  
  ERC-8004: Wiring in Onchain Reputation
&lt;/h2&gt;

&lt;p&gt;Here's where it gets interesting for trustless systems. The &lt;code&gt;erc8004&lt;/code&gt; provider in WAIaaS exposes three MCP tools that your bot can call:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;erc8004-get-agent-info&lt;/code&gt; — retrieve the onchain identity and metadata for an agent&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;erc8004-get-reputation&lt;/code&gt; — query the reputation score for an agent address&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;erc8004-get-validation-status&lt;/code&gt; — check whether an agent passes validation for a given context&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;These aren't just read operations for curiosity. In a production system, you'd wire &lt;code&gt;erc8004-get-validation-status&lt;/code&gt; into your bot's pre-trade logic. Before your bot interacts with another agent's positions, or before you allow an external agent to trigger actions on your wallet, you check its validation status first.&lt;/p&gt;

&lt;p&gt;WAIaaS also exposes this at the policy layer via the &lt;code&gt;REPUTATION_THRESHOLD&lt;/code&gt; policy type. You can set a minimum onchain reputation score that any agent must meet before transactions are allowed — enforced by the policy engine before execution, not as an afterthought in application code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "REPUTATION_THRESHOLD",
    "rules": {
      "min_reputation_score": 80
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is the default-deny philosophy applied to agent trust: unless an interacting agent meets your reputation threshold, the transaction doesn't happen. The policy engine enforces it at stage 3 of the 7-stage transaction pipeline, before execution ever reaches the protocol layer.&lt;/p&gt;

&lt;h2&gt;
  
  
  The 7-Stage Pipeline: Where Safety Lives
&lt;/h2&gt;

&lt;p&gt;Speaking of the pipeline — understanding it matters for bot builders because it's where all your safety guarantees actually live. Every transaction, whether it's a Jupiter swap or an Aave borrow, goes through these stages:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Validate&lt;/strong&gt; — schema and parameter validation&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Auth&lt;/strong&gt; — verify the session token&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Policy&lt;/strong&gt; — check all applicable policies (this is where REPUTATION_THRESHOLD, SPENDING_LIMIT, CONTRACT_WHITELIST, etc. all fire)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Wait&lt;/strong&gt; — enforce time delays if the DELAY tier was triggered&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Execute&lt;/strong&gt; — broadcast to the network&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Confirm&lt;/strong&gt; — wait for confirmation&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;The policy check at stage 3 is comprehensive. For a DeFi bot, the relevant policy types include:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;SPENDING_LIMIT&lt;/code&gt; — 4-tier security (INSTANT/NOTIFY/DELAY/APPROVAL) based on USD value&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;CONTRACT_WHITELIST&lt;/code&gt; — only listed contracts can be called (default-deny)&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;ALLOWED_TOKENS&lt;/code&gt; — only listed tokens can be transferred (default-deny)&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;ALLOWED_NETWORKS&lt;/code&gt; — restrict execution to specific chains&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;PERP_MAX_LEVERAGE&lt;/code&gt; — cap leverage on Hyperliquid or Drift positions&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;PERP_MAX_POSITION_USD&lt;/code&gt; — cap total position size&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;PERP_ALLOWED_MARKETS&lt;/code&gt; — whitelist which perp markets the bot can trade&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;LENDING_LTV_LIMIT&lt;/code&gt; — prevent over-leveraged borrows on Aave&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;LENDING_ASSET_WHITELIST&lt;/code&gt; — control which assets can be used as collateral&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;VENUE_WHITELIST&lt;/code&gt; — restrict which trading venues are accessible&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;ACTION_CATEGORY_LIMIT&lt;/code&gt; — cap activity within DeFi action categories&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;That's 11 policy types directly relevant to DeFi trading, out of 21 total. For a bot managing real funds, you'd typically layer several of these together. Here's a spending limit that creates meaningful safety tiers for an automated strategy:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "SPENDING_LIMIT",
    "rules": {
      "instant_max_usd": 100,
      "notify_max_usd": 500,
      "delay_max_usd": 2000,
      "delay_seconds": 900,
      "daily_limit_usd": 5000
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Transactions under $100 execute immediately. $100-$500 execute but trigger a notification to the owner. $500-$2000 get queued for 15 minutes, cancellable by the owner via WalletConnect. Above $2000, the bot needs explicit human approval before anything moves.&lt;/p&gt;

&lt;h2&gt;
  
  
  Simulate Before You Execute
&lt;/h2&gt;

&lt;p&gt;One of the most practical features for bot development is the dry-run API. Before you wire up a new strategy to live funds, you can simulate the full transaction — including policy checks — without broadcasting to the network:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/send &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "type": "TRANSFER",
    "to": "recipient-address",
    "amount": "0.1",
    "dryRun": true
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;dryRun: true&lt;/code&gt; flag runs the full pipeline except the execute and confirm stages. If your &lt;code&gt;CONTRACT_WHITELIST&lt;/code&gt; would block this transaction, you find out in simulation, not after a failed on-chain transaction. If the &lt;code&gt;SPENDING_LIMIT&lt;/code&gt; would route it to the DELAY tier instead of INSTANT, simulation tells you that too.&lt;/p&gt;

&lt;p&gt;This is table stakes for any serious bot development workflow — you should know exactly what the policy engine will do before you deploy.&lt;/p&gt;

&lt;h2&gt;
  
  
  Building the Bot: TypeScript SDK
&lt;/h2&gt;

&lt;p&gt;For production bots, the REST API is fine but the TypeScript SDK is cleaner. Here's a simplified example of a bot that checks its wallet state, executes a strategy, and polls for confirmation:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSClient&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSError&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@waiaas/sdk&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;WAIaaSClient&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="na"&gt;baseUrl&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;WAIAAS_BASE_URL&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;??&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;http://localhost:3100&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;sessionToken&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;WAIAAS_SESSION_TOKEN&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;

&lt;span class="c1"&gt;// Check balance before executing&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;balance&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getBalance&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`Balance: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt; &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;symbol&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt; (&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;chain&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;/&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;network&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;)`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="c1"&gt;// Execute the strategy&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;sendResult&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;sendToken&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="na"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;TRANSFER&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;to&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;recipient-address&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;amount&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;0.001&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`Transaction submitted: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;sendResult&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt; (status: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;sendResult&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;status&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;)`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="c1"&gt;// Poll for confirmation&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;POLL_TIMEOUT_MS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;60&lt;/span&gt;&lt;span class="nx"&gt;_000&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;startTime&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Date&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="k"&gt;while &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;Date&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="nx"&gt;startTime&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="nx"&gt;POLL_TIMEOUT_MS&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;tx&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getTransaction&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;sendResult&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;tx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;status&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;COMPLETED&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`Confirmed! Hash: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;tx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;txHash&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;tx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;status&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;FAILED&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;error&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`Failed: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;tx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;error&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;Promise&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;resolve&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="nf"&gt;setTimeout&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;resolve&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;1000&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Error handling is worth calling out explicitly — policy denials come back as structured errors, not generic HTTP 4xx responses:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;try&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;tx&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;sendToken&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="na"&gt;to&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;...&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;amount&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;1.0&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt; &lt;span class="p"&gt;});&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;catch &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;error&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;error&lt;/span&gt; &lt;span class="k"&gt;instanceof&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSError&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;error&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`API Error: [&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;error&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;code&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;] &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;error&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;message&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="c1"&gt;// error.code examples: INSUFFICIENT_BALANCE, POLICY_DENIED, TOKEN_EXPIRED&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;A &lt;code&gt;POLICY_DENIED&lt;/code&gt; error with &lt;code&gt;domain: "POLICY"&lt;/code&gt; tells you exactly what stopped the transaction. Your bot can branch on error codes — retry with a smaller amount, alert the operator, or fail gracefully — instead of parsing error message strings.&lt;/p&gt;

&lt;h2&gt;
  
  
  45 MCP Tools for AI-Native Bots
&lt;/h2&gt;

&lt;p&gt;If you're building an AI agent rather than a traditional algorithmic bot, the MCP integration gives Claude (or any MCP-compatible model) direct access to 45 tools covering wallet operations, transactions, DeFi positions, NFTs, and ERC-8004 reputation queries. The setup is minimal:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas mcp setup &lt;span class="nt"&gt;--all&lt;/span&gt;    &lt;span class="c"&gt;# Auto-register all wallets with Claude Desktop&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The tools include the full ERC-8004 surface (&lt;code&gt;erc8004-get-agent-info&lt;/code&gt;, &lt;code&gt;erc8004-get-reputation&lt;/code&gt;, &lt;code&gt;erc8004-get-validation-status&lt;/code&gt;), DeFi position queries (&lt;code&gt;get-defi-positions&lt;/code&gt;, &lt;code&gt;get-health-factor&lt;/code&gt;), and trading actions (&lt;code&gt;send-batch&lt;/code&gt;, &lt;code&gt;simulate-transaction&lt;/code&gt;, &lt;code&gt;x402-fetch&lt;/code&gt;). An AI agent can check its own reputation, verify counterparty agents, and execute multi-protocol strategies through the same tool interface.&lt;/p&gt;

&lt;h2&gt;
  
  
  Quick Start for DeFi Developers
&lt;/h2&gt;

&lt;p&gt;Here's the minimal path from zero to a running bot with policy guardrails:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;1. Start the daemon:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git clone https://github.com/minhoyoo-iotrust/WAIaaS.git
&lt;span class="nb"&gt;cd &lt;/span&gt;WAIaaS
docker compose up &lt;span class="nt"&gt;-d&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;2. Create a wallet and session:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/wallets &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"name": "trading-wallet", "chain": "solana", "environment": "mainnet"}'&lt;/span&gt;

curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/sessions &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"walletId": "&amp;lt;wallet-uuid&amp;gt;"}'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;3. Apply DeFi-specific policies (PERP_MAX_LEVERAGE, CONTRACT_WHITELIST, SPENDING_LIMIT)&lt;/strong&gt; using the policy API shown above.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;4. Simulate your first action&lt;/strong&gt; with &lt;code&gt;dryRun: true&lt;/code&gt; to verify policy behavior before using live funds.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;5. Install the SDK and connect your strategy:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; @waiaas/sdk
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The OpenAPI spec auto-generated at &lt;code&gt;/doc&lt;/code&gt; and interactive Scalar UI at &lt;code&gt;/reference&lt;/code&gt; give you the full endpoint reference while you're building.&lt;/p&gt;

&lt;h2&gt;
  
  
  What's Next
&lt;/h2&gt;

&lt;p&gt;The 15 protocol integrations, 21 policy types, and ERC-8004 reputation tools are all documented in the interactive API reference at &lt;code&gt;http://localhost:3100/reference&lt;/code&gt; once you're running. The GitHub repo has the full codebase, including the 683+ test files that cover the pipeline stages and policy engine — useful reading if you want to understand exactly how policy enforcement works before trusting it with real funds.&lt;/p&gt;

&lt;p&gt;Start building at &lt;a href="https://github.com/minhoyoo-iotrust/WAIaaS" rel="noopener noreferrer"&gt;github.com/minhoyoo-iotrust/WAIaaS&lt;/a&gt; and find protocol documentation, deployment guides, and SDK references at &lt;a href="https://waiaas.ai" rel="noopener noreferrer"&gt;waiaas.ai&lt;/a&gt;.&lt;/p&gt;

</description>
      <category>defi</category>
      <category>security</category>
      <category>ethereum</category>
      <category>ai</category>
    </item>
    <item>
      <title>Self-Updating Crypto Infrastructure: Watchtower + GHCR for AI Agent Wallets</title>
      <dc:creator>Wallet Guy</dc:creator>
      <pubDate>Sun, 05 Jul 2026 14:51:29 +0000</pubDate>
      <link>https://dev.to/walletguy/self-updating-crypto-infrastructure-watchtower-ghcr-for-ai-agent-wallets-5a4g</link>
      <guid>https://dev.to/walletguy/self-updating-crypto-infrastructure-watchtower-ghcr-for-ai-agent-wallets-5a4g</guid>
      <description>&lt;h1&gt;
  
  
  Self-Updating Crypto Infrastructure: Watchtower + GHCR for AI Agent Wallets
&lt;/h1&gt;

&lt;p&gt;Self-hosted wallet infrastructure for AI agents sounds like a weekend project that ends in tears — until you realize one Docker command is genuinely all it takes to get started. But getting it &lt;em&gt;running&lt;/em&gt; is only half the battle. The harder question is: how do you keep it &lt;em&gt;updated&lt;/em&gt; without babysitting a server? That's where Watchtower and GitHub Container Registry (GHCR) come in, and it's a combination worth understanding if you care about running your own infrastructure.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why Self-Hosting Your AI Agent's Wallet Actually Matters
&lt;/h2&gt;

&lt;p&gt;Would you trust a third party with your AI agent's private keys?&lt;/p&gt;

&lt;p&gt;That's not a rhetorical scare tactic — it's a genuine architectural question that comes up the moment you start building AI agents that need to move money. When you hand wallet custody to a hosted service, you're also handing over your transaction history, your rate limits, your uptime dependency, and in the worst case, your keys themselves.&lt;/p&gt;

&lt;p&gt;The self-hosted philosophy here is familiar to anyone who runs their own email server, Nextcloud instance, or Home Assistant setup: you trade some operational overhead for complete sovereignty. Your keys live on your hardware. Your transaction data doesn't leave your network. You set the rules.&lt;/p&gt;

&lt;p&gt;What makes WAIaaS compelling for this crowd specifically is that it isn't just a wallet — it's a full Wallet-as-a-Service daemon that an AI agent can call via REST API or MCP tools. The agent gets a session token. The session token has policies. The policies define what the agent can and cannot do with your funds. All of that runs on your server, behind your firewall, without any third party in the loop.&lt;/p&gt;

&lt;p&gt;But let's talk about the part that usually gets skipped in self-hosting guides: keeping the thing updated.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Update Problem for Self-Hosted Services
&lt;/h2&gt;

&lt;p&gt;Here's how update management usually goes for self-hosted projects:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;You deploy version X.&lt;/li&gt;
&lt;li&gt;Version X+1 comes out with a security fix.&lt;/li&gt;
&lt;li&gt;You find out three weeks later from a forum post.&lt;/li&gt;
&lt;li&gt;You SSH in, pull the new image, restart the service.&lt;/li&gt;
&lt;li&gt;Repeat forever.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;For a homelab running Jellyfin, this is mildly annoying. For infrastructure that AI agents use to sign and broadcast transactions, stale software is a genuine risk. Security patches, bug fixes, and new protocol support all matter here.&lt;/p&gt;

&lt;p&gt;WAIaaS publishes its Docker image to GHCR at &lt;code&gt;ghcr.io/minhoyoo-iotrust/waiaas:latest&lt;/code&gt;. The &lt;code&gt;:latest&lt;/code&gt; tag is the conventional signal that you want the most current stable build. Watchtower is the conventional tool for polling that tag and rolling updates automatically.&lt;/p&gt;

&lt;p&gt;Together, they solve the update problem without requiring you to log into your server.&lt;/p&gt;

&lt;h2&gt;
  
  
  What WAIaaS Actually Runs
&lt;/h2&gt;

&lt;p&gt;Before getting into the update mechanics, it helps to understand what you're deploying.&lt;/p&gt;

&lt;p&gt;WAIaaS is a 15-package monorepo that ships as two Docker images: the main daemon and a push-relay service. The daemon is the piece most people care about — it's the REST API server that AI agents talk to.&lt;/p&gt;

&lt;p&gt;That API has 39 route modules covering wallets, transactions, DeFi actions, NFTs, sessions, policies, and more. It supports 18 networks across EVM and Solana chain types. It has 15 DeFi protocol integrations including Jupiter, Aave v3, Lido, Jito, Hyperliquid, Polymarket, and others.&lt;/p&gt;

&lt;p&gt;The transaction pipeline has 7 stages — validate, auth, policy, wait, execute, confirm — and a policy engine with 21 policy types and 4 security tiers (INSTANT, NOTIFY, DELAY, APPROVAL). Default-deny enforcement means if you haven't explicitly whitelisted a token or contract, the transaction gets blocked.&lt;/p&gt;

&lt;p&gt;For AI agent integration, there are 45 MCP tools covering wallet operations, transfers, DeFi positions, NFTs, and x402 payments. The CLI has 20 commands for everything from &lt;code&gt;quickstart&lt;/code&gt; to &lt;code&gt;backup create&lt;/code&gt; to &lt;code&gt;mcp setup&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;This is not a toy. Keeping it updated matters.&lt;/p&gt;

&lt;h2&gt;
  
  
  Getting It Running: One Docker Command
&lt;/h2&gt;

&lt;p&gt;The fastest path to a running instance:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;docker run &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--name&lt;/span&gt; waiaas &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-p&lt;/span&gt; 127.0.0.1:3100:3100 &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-v&lt;/span&gt; waiaas-data:/data &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-e&lt;/span&gt; &lt;span class="nv"&gt;WAIAAS_AUTO_PROVISION&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nb"&gt;true&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  ghcr.io/minhoyoo-iotrust/waiaas:latest

&lt;span class="c"&gt;# Retrieve auto-generated master password&lt;/span&gt;
docker &lt;span class="nb"&gt;exec &lt;/span&gt;waiaas &lt;span class="nb"&gt;cat&lt;/span&gt; /data/recovery.key
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;WAIAAS_AUTO_PROVISION=true&lt;/code&gt; flag tells the entrypoint to generate a master password on first start and write it to &lt;code&gt;/data/recovery.key&lt;/code&gt;. You retrieve it once, store it somewhere safe, and the daemon is ready.&lt;/p&gt;

&lt;p&gt;The port binding &lt;code&gt;127.0.0.1:3100:3100&lt;/code&gt; is intentional — it keeps the API localhost-only by default, so you're not accidentally exposing wallet infrastructure to the internet.&lt;/p&gt;

&lt;p&gt;For anything beyond a quick test, Docker Compose gives you a cleaner setup:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;services&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;daemon&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;image&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;ghcr.io/minhoyoo-iotrust/waiaas:latest&lt;/span&gt;
    &lt;span class="na"&gt;container_name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;waiaas-daemon&lt;/span&gt;
    &lt;span class="na"&gt;ports&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;127.0.0.1:3100:3100"&lt;/span&gt;
    &lt;span class="na"&gt;volumes&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;waiaas-data:/data&lt;/span&gt;
    &lt;span class="na"&gt;environment&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;WAIAAS_DATA_DIR=/data&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;WAIAAS_DAEMON_HOSTNAME=0.0.0.0&lt;/span&gt;
    &lt;span class="na"&gt;env_file&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;.env&lt;/span&gt;
        &lt;span class="na"&gt;required&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;
    &lt;span class="na"&gt;restart&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;unless-stopped&lt;/span&gt;
    &lt;span class="na"&gt;healthcheck&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="na"&gt;test&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;CMD"&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;curl"&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;-f"&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;http://localhost:3100/health"&lt;/span&gt;&lt;span class="pi"&gt;]&lt;/span&gt;
      &lt;span class="na"&gt;interval&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;30s&lt;/span&gt;
      &lt;span class="na"&gt;timeout&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;5s&lt;/span&gt;
      &lt;span class="na"&gt;start_period&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;10s&lt;/span&gt;
      &lt;span class="na"&gt;retries&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;3&lt;/span&gt;

&lt;span class="na"&gt;volumes&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;waiaas-data&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;driver&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;local&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;A few things worth noting in this compose file:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;restart: unless-stopped&lt;/code&gt; means the daemon survives reboots.&lt;/li&gt;
&lt;li&gt;The healthcheck polls &lt;code&gt;/health&lt;/code&gt; every 30 seconds, so you'll know if something goes wrong.&lt;/li&gt;
&lt;li&gt;Data lives in a named volume, so &lt;code&gt;docker compose down&lt;/code&gt; doesn't wipe your wallets. Only &lt;code&gt;docker compose down -v&lt;/code&gt; does.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Production Secrets: Not Just Environment Variables
&lt;/h2&gt;

&lt;p&gt;If you're running this seriously, hardcoded environment variables in compose files aren't the right approach for sensitive values. WAIaaS ships with a Docker Secrets overlay pattern via &lt;code&gt;docker-compose.secrets.yml&lt;/code&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Create secret files&lt;/span&gt;
&lt;span class="nb"&gt;mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; secrets
&lt;span class="nb"&gt;echo&lt;/span&gt; &lt;span class="s2"&gt;"your-secure-password"&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; secrets/master_password.txt
&lt;span class="nb"&gt;chmod &lt;/span&gt;600 secrets/master_password.txt

&lt;span class="c"&gt;# Deploy with secrets overlay&lt;/span&gt;
docker compose &lt;span class="nt"&gt;-f&lt;/span&gt; docker-compose.yml &lt;span class="nt"&gt;-f&lt;/span&gt; docker-compose.secrets.yml up &lt;span class="nt"&gt;-d&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Secret files are mounted into the container at runtime rather than baked into environment variables that might show up in &lt;code&gt;docker inspect&lt;/code&gt; or process listings. This is the right approach for production deployments, especially on shared hardware.&lt;/p&gt;

&lt;h2&gt;
  
  
  Adding Watchtower for Automatic Updates
&lt;/h2&gt;

&lt;p&gt;Watchtower is a container that watches your other containers and restarts them when their upstream image is updated. It works by periodically checking the registry for newer digests matching the tag you're tracking.&lt;/p&gt;

&lt;p&gt;Adding it to your compose setup is straightforward — here's the concept in a standalone docker run to keep things clear:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;docker run &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--name&lt;/span&gt; watchtower &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-v&lt;/span&gt; /var/run/docker.sock:/var/run/docker.sock &lt;span class="se"&gt;\&lt;/span&gt;
  containrrr/watchtower &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--interval&lt;/span&gt; 86400 &lt;span class="se"&gt;\&lt;/span&gt;
  waiaas-daemon
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This tells Watchtower to check once per day (&lt;code&gt;--interval 86400&lt;/code&gt; seconds) and only watch the &lt;code&gt;waiaas-daemon&lt;/code&gt; container. If a new image is published to &lt;code&gt;ghcr.io/minhoyoo-iotrust/waiaas:latest&lt;/code&gt;, Watchtower pulls it, stops the old container, and starts a new one with the same configuration.&lt;/p&gt;

&lt;p&gt;Because the wallet data lives in a named volume (&lt;code&gt;waiaas-data:/data&lt;/code&gt;), it persists across container restarts. The new container picks up exactly where the old one left off.&lt;/p&gt;

&lt;p&gt;A few practical notes for self-hosters:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Schedule updates during low-traffic windows.&lt;/strong&gt; If your AI agents are actively trading, a restart in the middle of a transaction pipeline isn't ideal. Watchtower supports cron-style scheduling with &lt;code&gt;--schedule&lt;/code&gt; if you want updates to happen at 3am instead of randomly throughout the day.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Consider update notifications.&lt;/strong&gt; Watchtower can post to Slack, email, or other channels when it performs an update. For infrastructure you care about, knowing when an update happened is useful for debugging if something changes behavior.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Test before enabling auto-update in production.&lt;/strong&gt; Run a staging instance that auto-updates, verify it works, then roll to production. Named volumes make this easy because staging and production can share nothing except the image.&lt;/p&gt;

&lt;h2&gt;
  
  
  The CLI Path: More Control, Less Magic
&lt;/h2&gt;

&lt;p&gt;If automatic updates feel like too much magic for your taste, the CLI gives you explicit control:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;-g&lt;/span&gt; @waiaas/cli
waiaas init
waiaas start
waiaas update
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;waiaas update&lt;/code&gt; command is one of the 20 CLI commands built into the WAIaaS CLI. It's the manual equivalent of what Watchtower does automatically — pull the latest image, restart the daemon. You run it when you want to, not on a schedule.&lt;/p&gt;

&lt;p&gt;This is the right approach if you're running WAIaaS on hardware where unattended restarts could cause problems, or if you want to read changelogs before updating.&lt;/p&gt;

&lt;h2&gt;
  
  
  Setting Up Your First Wallet and Agent Session
&lt;/h2&gt;

&lt;p&gt;Once the daemon is running, the quickstart flow is three more commands:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas init                    &lt;span class="c"&gt;# Create data directory + config.toml&lt;/span&gt;
waiaas start                   &lt;span class="c"&gt;# Start daemon (sets master password on first run)&lt;/span&gt;
waiaas quickset &lt;span class="nt"&gt;--mode&lt;/span&gt; mainnet &lt;span class="c"&gt;# Create wallets + MCP sessions in one step&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;quickset&lt;/code&gt; creates wallets and sessions, then prints the MCP configuration JSON you need to paste into Claude Desktop (or whatever AI agent framework you're using). If you want to skip copy-pasting:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas mcp setup &lt;span class="nt"&gt;--all&lt;/span&gt;   &lt;span class="c"&gt;# Auto-register all wallets with Claude Desktop&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After that, your AI agent has a session token, and you control what it can do via policies. For example, setting a spending limit:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "SPENDING_LIMIT",
    "rules": {
      "instant_max_usd": 100,
      "notify_max_usd": 500,
      "delay_max_usd": 2000,
      "delay_seconds": 900,
      "daily_limit_usd": 5000
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This creates a four-tier policy: under $100 executes immediately, $100-500 sends you a notification, $500-2000 queues for 15 minutes (cancellable), and over $2000 requires your explicit approval. The agent can't override these — they're enforced server-side in the transaction pipeline before any signing happens.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Self-Hosting Philosophy in Practice
&lt;/h2&gt;

&lt;p&gt;Running your own wallet infrastructure is the crypto equivalent of running your own email server — the comparison gets made a lot because it's accurate. Both give you control over sensitive data. Both require you to think about uptime, updates, and backups. Both are more practical than they used to be.&lt;/p&gt;

&lt;p&gt;The backup story matters here too. The CLI includes &lt;code&gt;backup create&lt;/code&gt;, &lt;code&gt;backup list&lt;/code&gt;, &lt;code&gt;backup inspect&lt;/code&gt;, and &lt;code&gt;restore&lt;/code&gt; commands. Your wallet data, session configuration, and policies are all in the named volume. Back it up. The &lt;code&gt;waiaas backup create&lt;/code&gt; command exists precisely so you don't have to figure out the right &lt;code&gt;tar&lt;/code&gt; incantation to grab the right files.&lt;/p&gt;

&lt;p&gt;For the privacy-conscious: all of this runs on your hardware, on your network. The transaction data that flows through your WAIaaS instance — which agents are doing what, when, to which addresses — stays local. If you're building agents that handle sensitive financial operations, that's not a minor consideration.&lt;/p&gt;

&lt;p&gt;The three-layer security model (session auth → time delay and approval → monitoring and kill switch) works because all three layers run locally. WalletConnect integration lets you approve transactions from your phone. The kill switch is yours to pull, not a hosted service's.&lt;/p&gt;

&lt;h2&gt;
  
  
  Quick Start Summary
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Deploy&lt;/strong&gt;: &lt;code&gt;docker compose up -d&lt;/code&gt; from the cloned repo, or &lt;code&gt;docker run&lt;/code&gt; with the image from GHCR&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Auto-provision&lt;/strong&gt;: Set &lt;code&gt;WAIAAS_AUTO_PROVISION=true&lt;/code&gt;, retrieve the master password from &lt;code&gt;/data/recovery.key&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Add Watchtower&lt;/strong&gt;: Point it at &lt;code&gt;waiaas-daemon&lt;/code&gt; with a daily check interval&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Create wallets and sessions&lt;/strong&gt;: &lt;code&gt;waiaas quickset --mode mainnet&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Set policies&lt;/strong&gt;: Define spending limits and whitelists via the REST API or Admin UI before handing session tokens to agents&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;The OpenAPI spec and interactive docs are available at &lt;code&gt;http://127.0.0.1:3100/doc&lt;/code&gt; and &lt;code&gt;http://127.0.0.1:3100/reference&lt;/code&gt; once you're running.&lt;/p&gt;

&lt;h2&gt;
  
  
  What's Next
&lt;/h2&gt;

&lt;p&gt;The infrastructure side of self-hosting WAIaaS is genuinely approachable — the harder and more interesting questions are around policy design (which of the 21 policy types you need, and how tight to set the tiers) and agent integration (MCP vs. SDK vs. direct REST). Both are worth spending time on before your agents start moving real funds. The &lt;a href="https://github.com/minhoyoo-iotrust/WAIaaS" rel="noopener noreferrer"&gt;GitHub repository&lt;/a&gt; has the full source and documentation, and &lt;a href="https://waiaas.ai" rel="noopener noreferrer"&gt;waiaas.ai&lt;/a&gt; covers the broader architecture. Start with &lt;code&gt;WAIAAS_AUTO_PROVISION=true&lt;/code&gt; on a testnet wallet, run a few transactions through the pipeline, watch the logs — you'll get a feel for how the pieces fit together before anything is at stake.&lt;/p&gt;

</description>
      <category>docker</category>
      <category>selfhosted</category>
      <category>devops</category>
      <category>security</category>
    </item>
    <item>
      <title>21 Policy Types for Self-Hosted Crypto Wallets: Complete Risk Management</title>
      <dc:creator>Wallet Guy</dc:creator>
      <pubDate>Sat, 04 Jul 2026 14:44:38 +0000</pubDate>
      <link>https://dev.to/walletguy/21-policy-types-for-self-hosted-crypto-wallets-complete-risk-management-49n</link>
      <guid>https://dev.to/walletguy/21-policy-types-for-self-hosted-crypto-wallets-complete-risk-management-49n</guid>
      <description>&lt;h1&gt;
  
  
  21 Policy Types for Self-Hosted Crypto Wallets: Complete Risk Management
&lt;/h1&gt;

&lt;p&gt;Would you trust a third party with your AI agent's private keys? If you're building autonomous agents that move real money, the question of &lt;em&gt;who controls the wallet&lt;/em&gt; matters as much as the policy rules protecting it. WAIaaS is an open-source, self-hosted Wallet-as-a-Service that lets you run your own wallet infrastructure — and back it with a policy engine covering 21 distinct risk controls, all enforced locally on your own server.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why Risk Management for AI Agents Is Different
&lt;/h2&gt;

&lt;p&gt;Traditional wallet security assumes a human is making every decision. A human checks the recipient address. A human notices when a transaction looks wrong. A human stops before clicking send on a $10,000 transfer at 3 AM.&lt;/p&gt;

&lt;p&gt;AI agents don't do any of that.&lt;/p&gt;

&lt;p&gt;When you give an autonomous agent a session token, you're handing it the ability to sign and broadcast transactions without any of those human checkpoints. That's the whole point — but it's also the risk. An agent following bad instructions, a compromised session token, or a misconfigured DeFi strategy can drain funds faster than any human operator can react. The policy engine isn't a nice-to-have. It's the layer between "agent does something clever" and "agent does something catastrophic."&lt;/p&gt;

&lt;p&gt;The self-hosted angle matters here too. When you run WAIaaS on your own server, your private keys never leave your infrastructure. The policy engine enforcing your rules runs on your machine. No hosted service is making decisions about your transactions, rate-limiting your agent's API calls, or holding your keys in a multi-tenant environment. Your server, your rules, full stop.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Default-Deny Foundation
&lt;/h2&gt;

&lt;p&gt;Before diving into the 21 policy types, it's worth understanding the foundational principle: &lt;strong&gt;default-deny&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;If you don't configure an &lt;code&gt;ALLOWED_TOKENS&lt;/code&gt; policy, token transfers are blocked. If you don't configure a &lt;code&gt;CONTRACT_WHITELIST&lt;/code&gt;, contract calls are blocked. The absence of a permission is itself a denial. This is the opposite of most wallet setups where everything is allowed until you explicitly restrict it.&lt;/p&gt;

&lt;p&gt;This matters for agents specifically because agents &lt;em&gt;will&lt;/em&gt; try things you didn't anticipate. A default-allow system means your agent can do anything until you catch and block it. A default-deny system means your agent can only do what you've explicitly permitted.&lt;/p&gt;

&lt;h2&gt;
  
  
  The 4 Security Tiers
&lt;/h2&gt;

&lt;p&gt;Every transaction WAIaaS processes gets assigned to one of four security tiers before execution:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;INSTANT&lt;/strong&gt; — Execute immediately, no notification&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;NOTIFY&lt;/strong&gt; — Execute immediately, but send you a notification&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;DELAY&lt;/strong&gt; — Queue the transaction for a configurable number of seconds, then execute (you can cancel during this window)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;APPROVAL&lt;/strong&gt; — Block until you explicitly approve via WalletConnect, Telegram, or push notification&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The &lt;code&gt;SPENDING_LIMIT&lt;/code&gt; policy is what maps transaction amounts to these tiers. Here's a practical example — a policy that lets your agent handle small routine payments instantly, notifies you on medium transactions, delays large ones (giving you a cancellation window), and requires your explicit sign-off on anything significant:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://localhost:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s1"&gt;'Content-Type: application/json'&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s1"&gt;'X-Master-Password: &amp;lt;password&amp;gt;'&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "SPENDING_LIMIT",
    "rules": {
      "instant_max_usd": 10,
      "notify_max_usd": 100,
      "delay_max_usd": 1000,
      "delay_seconds": 300,
      "daily_limit_usd": 500,
      "monthly_limit_usd": 5000
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With this config: anything under $10 executes immediately, $10–$100 executes with a notification, $100–$1,000 gets queued for 5 minutes before executing, and anything over $1,000 waits for your manual approval. The daily cap of $500 and monthly cap of $5,000 add an aggregate safety net on top.&lt;/p&gt;

&lt;h2&gt;
  
  
  All 21 Policy Types
&lt;/h2&gt;

&lt;p&gt;Here's what the full policy library covers:&lt;/p&gt;

&lt;h3&gt;
  
  
  Transfer Controls
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;SPENDING_LIMIT&lt;/code&gt;&lt;/strong&gt; — The core 4-tier security policy described above. Maps USD amounts to INSTANT/NOTIFY/DELAY/APPROVAL tiers with daily and monthly aggregate limits.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;WHITELIST&lt;/code&gt;&lt;/strong&gt; — Restricts which recipient addresses your agent can send funds to. If an address isn't on the list, the transaction is blocked:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"allowed_addresses"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"&amp;lt;address1&amp;gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"&amp;lt;address2&amp;gt;"&lt;/span&gt;&lt;span class="p"&gt;]}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;ALLOWED_TOKENS&lt;/code&gt;&lt;/strong&gt; — Default-deny whitelist of which tokens your agent can transfer. Your agent can only move tokens explicitly listed here:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"tokens"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[{&lt;/span&gt;&lt;span class="nl"&gt;"address"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"symbol"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"USDC"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"chain"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"solana"&lt;/span&gt;&lt;span class="p"&gt;}]}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;RATE_LIMIT&lt;/code&gt;&lt;/strong&gt; — Caps the number of transactions your agent can submit per period:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"maxTransactions"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;10&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"period"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"hourly"&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;TIME_RESTRICTION&lt;/code&gt;&lt;/strong&gt; — Limits when transactions can execute. Useful if your agent should only operate during business hours:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"allowedHours"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"start"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;9&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"end"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;17&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"timezone"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"UTC"&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;ALLOWED_NETWORKS&lt;/code&gt;&lt;/strong&gt; — Restricts which chains your agent can transact on:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"networks"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[{&lt;/span&gt;&lt;span class="nl"&gt;"network"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"ethereum-mainnet"&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"network"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"solana-mainnet"&lt;/span&gt;&lt;span class="p"&gt;}]}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Contract Interaction Controls
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;CONTRACT_WHITELIST&lt;/code&gt;&lt;/strong&gt; — Default-deny whitelist of smart contracts your agent can call. If the contract address isn't listed, the call is blocked:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"contracts"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[{&lt;/span&gt;&lt;span class="nl"&gt;"address"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"JUP6LkbZbjS1jKKwapdHNy74zcZ3tLUZoi5QNyVTaV4"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Jupiter"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"chain"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"solana"&lt;/span&gt;&lt;span class="p"&gt;}]}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;METHOD_WHITELIST&lt;/code&gt;&lt;/strong&gt; — Restricts which function selectors (4-byte method IDs) the agent can call on contracts. Useful when you want to allow a contract but only specific functions on it.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;APPROVED_SPENDERS&lt;/code&gt;&lt;/strong&gt; — Default-deny whitelist controlling which addresses your agent can grant token approval to:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"spenders"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[{&lt;/span&gt;&lt;span class="nl"&gt;"address"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"0xDEF1..."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Uniswap Router"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"maxAmount"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"1000000000"&lt;/span&gt;&lt;span class="p"&gt;}]}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;APPROVE_AMOUNT_LIMIT&lt;/code&gt;&lt;/strong&gt; — Sets a cap on approval amounts and can block unlimited approvals (the &lt;code&gt;approve(MAX_UINT256)&lt;/code&gt; pattern that's common but risky).&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;APPROVE_TIER_OVERRIDE&lt;/code&gt;&lt;/strong&gt; — Forces approval transactions into a specific security tier regardless of amount. You might want all &lt;code&gt;approve()&lt;/code&gt; calls to require human sign-off even if the amount would normally be INSTANT.&lt;/p&gt;

&lt;h3&gt;
  
  
  DeFi-Specific Controls
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;LENDING_LTV_LIMIT&lt;/code&gt;&lt;/strong&gt; — Caps the loan-to-value ratio your agent can take on in lending protocols like Aave. Prevents your agent from over-leveraging borrowed positions.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;LENDING_ASSET_WHITELIST&lt;/code&gt;&lt;/strong&gt; — Restricts which assets your agent can supply or borrow in lending protocols.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;PERP_MAX_LEVERAGE&lt;/code&gt;&lt;/strong&gt; — Sets the maximum leverage multiplier for perpetual futures positions on protocols like Hyperliquid.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;PERP_MAX_POSITION_USD&lt;/code&gt;&lt;/strong&gt; — Caps the total USD size of any single perpetual position.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;PERP_ALLOWED_MARKETS&lt;/code&gt;&lt;/strong&gt; — Restricts which perpetual futures markets your agent can trade.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;VENUE_WHITELIST&lt;/code&gt;&lt;/strong&gt; — Controls which trading venues or DEXes your agent can route through.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;ACTION_CATEGORY_LIMIT&lt;/code&gt;&lt;/strong&gt; — Applies aggregate limits across DeFi action categories (lending, staking, trading, etc.).&lt;/p&gt;

&lt;h3&gt;
  
  
  Emerging Protocol Controls
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;X402_ALLOWED_DOMAINS&lt;/code&gt;&lt;/strong&gt; — WAIaaS supports the x402 HTTP payment protocol, where AI agents automatically pay for API calls. This policy whitelists which domains your agent can make automatic payments to:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"domains"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"api.example.com"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"*.openai.com"&lt;/span&gt;&lt;span class="p"&gt;]}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;REPUTATION_THRESHOLD&lt;/code&gt;&lt;/strong&gt; — Sets a minimum ERC-8004 onchain reputation score required for counterparties in agent-to-agent interactions.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;ERC8128_ALLOWED_DOMAINS&lt;/code&gt;&lt;/strong&gt; — Restricts which domains your agent can sign HTTP requests for under the ERC-8128 protocol.&lt;/p&gt;

&lt;h2&gt;
  
  
  Approving a Transaction as the Owner
&lt;/h2&gt;

&lt;p&gt;When a transaction hits the APPROVAL tier, your agent's execution is paused. The transaction waits until you act on it. Once you've reviewed and decided to proceed, approving looks like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/&amp;lt;tx-id&amp;gt;/approve &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Owner-Signature: &amp;lt;ed25519-or-secp256k1-signature&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Owner-Message: &amp;lt;signed-message&amp;gt;"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;ownerAuth&lt;/code&gt; layer uses your own keypair — the same address you used when setting up owner authentication. Nothing about this approval touches a third-party service. The signature verification happens on your server.&lt;/p&gt;

&lt;h2&gt;
  
  
  Testing Before You Commit
&lt;/h2&gt;

&lt;p&gt;Before you deploy a policy setup to a live agent, you can simulate transactions to see exactly how they'd be handled. The &lt;code&gt;dryRun&lt;/code&gt; flag runs the full policy evaluation pipeline without broadcasting anything:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/send &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "type": "TRANSFER",
    "to": "recipient-address",
    "amount": "0.1",
    "dryRun": true
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is how you validate that your &lt;code&gt;SPENDING_LIMIT&lt;/code&gt; thresholds work the way you intended, that your &lt;code&gt;WHITELIST&lt;/code&gt; covers the right addresses, and that your &lt;code&gt;ALLOWED_TOKENS&lt;/code&gt; list includes everything your agent legitimately needs — before any real funds are at risk.&lt;/p&gt;

&lt;h2&gt;
  
  
  What a Policy Denial Looks Like
&lt;/h2&gt;

&lt;p&gt;When a transaction is blocked by a policy, the API returns a structured error rather than silently failing. Your agent (or your monitoring) gets something like:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"error"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"code"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"POLICY_DENIED"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"message"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Transaction denied by SPENDING_LIMIT policy"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"domain"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"POLICY"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"retryable"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;retryable: false&lt;/code&gt; flag tells the agent not to keep hammering the endpoint. The error code tells you exactly which policy triggered the block, so you can audit your configuration.&lt;/p&gt;

&lt;h2&gt;
  
  
  Getting It Running
&lt;/h2&gt;

&lt;p&gt;The fastest path from zero to a self-hosted WAIaaS instance with policies configured:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 1: Start the daemon&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git clone https://github.com/minhoyoo-iotrust/WAIaaS.git
&lt;span class="nb"&gt;cd &lt;/span&gt;WAIaaS
docker compose up &lt;span class="nt"&gt;-d&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The Docker image is &lt;code&gt;ghcr.io/minhoyoo-iotrust/waiaas:latest&lt;/code&gt;, and it binds to &lt;code&gt;127.0.0.1:3100&lt;/code&gt; by default — local only, not exposed to the network.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 2: Initialize and create a wallet&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;-g&lt;/span&gt; @waiaas/cli
waiaas init
waiaas start
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Or use &lt;code&gt;waiaas quickset --mode mainnet&lt;/code&gt; to create wallets and sessions in one step.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 3: Create your spending policy&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "SPENDING_LIMIT",
    "rules": {
      "instant_max_usd": 100,
      "notify_max_usd": 500,
      "delay_max_usd": 2000,
      "delay_seconds": 900,
      "daily_limit_usd": 5000
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 4: Add token and contract whitelists&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Layer &lt;code&gt;ALLOWED_TOKENS&lt;/code&gt; and &lt;code&gt;CONTRACT_WHITELIST&lt;/code&gt; on top of your spending limit. Remember: without these, token transfers and contract calls are blocked by default.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 5: Create a session for your agent&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/sessions &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"walletId": "&amp;lt;wallet-uuid&amp;gt;"}'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Your agent gets a &lt;code&gt;wai_sess_...&lt;/code&gt; token scoped to that wallet and governed by every policy you've configured.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Philosophy Behind Self-Hosting This
&lt;/h2&gt;

&lt;p&gt;Running WAIaaS is philosophically similar to running your own email server. It's more setup than using a hosted service. But you get things a hosted service structurally cannot give you: your private keys live on your hardware, your policy engine enforces rules without calling home, and your agent's transaction history stays on your infrastructure.&lt;/p&gt;

&lt;p&gt;The 21 policy types aren't about making things complicated. They're about giving you the specific controls you actually need — whether that's a simple spending cap for a personal agent or a layered DeFi risk framework for something managing real capital. Start with &lt;code&gt;SPENDING_LIMIT&lt;/code&gt; and &lt;code&gt;ALLOWED_TOKENS&lt;/code&gt;. Add the DeFi controls when you're running lending or futures strategies. The rest are there when you need them.&lt;/p&gt;

&lt;h2&gt;
  
  
  What's Next
&lt;/h2&gt;

&lt;p&gt;The interactive API reference at &lt;code&gt;http://127.0.0.1:3100/reference&lt;/code&gt; documents every policy type with request/response schemas you can try directly in the browser. The admin UI at &lt;code&gt;/admin&lt;/code&gt; includes a policy editor for managing policies without writing curl commands. If you're wiring this up to Claude or another MCP-compatible agent, the 45 MCP tools include &lt;code&gt;get-policies&lt;/code&gt; so your agent can introspect its own policy configuration at runtime.&lt;/p&gt;

&lt;p&gt;Grab the source, open an issue, or star the project on GitHub:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;GitHub&lt;/strong&gt;: &lt;a href="https://github.com/minhoyoo-iotrust/WAIaaS" rel="noopener noreferrer"&gt;https://github.com/minhoyoo-iotrust/WAIaaS&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Official site&lt;/strong&gt;: &lt;a href="https://waiaas.ai" rel="noopener noreferrer"&gt;https://waiaas.ai&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>selfhosted</category>
      <category>security</category>
      <category>opensource</category>
      <category>web3</category>
    </item>
    <item>
      <title>WalletConnect in Claude Desktop: Mobile Approval for AI Agent Transactions</title>
      <dc:creator>Wallet Guy</dc:creator>
      <pubDate>Sat, 04 Jul 2026 09:03:36 +0000</pubDate>
      <link>https://dev.to/walletguy/walletconnect-in-claude-desktop-mobile-approval-for-ai-agent-transactions-27ho</link>
      <guid>https://dev.to/walletguy/walletconnect-in-claude-desktop-mobile-approval-for-ai-agent-transactions-27ho</guid>
      <description>&lt;h1&gt;
  
  
  WalletConnect in Claude Desktop: Mobile Approval for AI Agent Transactions
&lt;/h1&gt;

&lt;p&gt;WalletConnect integration in WAIaaS means your Claude Desktop agent doesn't just send transactions — it can pause and ask you to approve them from your phone. If you've been exploring MCP tools that let Claude interact with blockchains, this is the piece that closes the loop: an AI agent that executes onchain actions, governed by policies you set, with a human-in-the-loop safety net when the stakes are high enough to warrant one.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why Human Approval Still Matters for Autonomous Agents
&lt;/h2&gt;

&lt;p&gt;Giving an AI agent a wallet is straightforward. Trusting it completely with that wallet is a different question. Most developers building onchain agents eventually hit the same wall: they want the agent to move fast on small, routine transactions, but they want a human checkpoint before anything significant happens.&lt;/p&gt;

&lt;p&gt;WAIaaS approaches this with a 4-tier security model — INSTANT, NOTIFY, DELAY, and APPROVAL — built directly into its policy engine. The APPROVAL tier is where WalletConnect comes in. When a transaction exceeds your configured threshold, the daemon holds it in a pending state and fires an approval request to the wallet owner's mobile device. You tap approve or reject. The agent waits. Nothing moves without your sign-off.&lt;/p&gt;

&lt;p&gt;That's not a workaround. That's the intended architecture.&lt;/p&gt;

&lt;h2&gt;
  
  
  WAIaaS as an MCP Server
&lt;/h2&gt;

&lt;p&gt;Before getting into WalletConnect mechanics, it helps to understand how WAIaaS fits into your Claude Desktop setup. WAIaaS is, among other things, an MCP server exposing 45 tools across wallet, transaction, DeFi, NFT, and x402 categories. From Claude's perspective, it's just another entry in &lt;code&gt;claude_desktop_config.json&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Add this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"mcpServers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"waiaas"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"command"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"npx"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"args"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"-y"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"@waiaas/mcp"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"env"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_BASE_URL"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:3100"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_SESSION_TOKEN"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"wai_sess_&amp;lt;your-token&amp;gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_DATA_DIR"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"~/.waiaas"&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Restart Claude Desktop. Claude now has access to 45 MCP tools including &lt;code&gt;wc-connect&lt;/code&gt;, &lt;code&gt;wc-disconnect&lt;/code&gt;, &lt;code&gt;wc-status&lt;/code&gt;, &lt;code&gt;get-balance&lt;/code&gt;, &lt;code&gt;send-token&lt;/code&gt;, &lt;code&gt;get-defi-positions&lt;/code&gt;, &lt;code&gt;simulate-transaction&lt;/code&gt;, and more. The WalletConnect tools are included in that set — they're not an add-on, they're part of the core MCP surface.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Three-Layer Security Model
&lt;/h2&gt;

&lt;p&gt;Understanding where WalletConnect fits requires a quick look at how WAIaaS structures security:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Layer 1 — Session auth:&lt;/strong&gt; The AI agent authenticates with a session token (JWT HS256). This controls what the agent is allowed to request in the first place. Sessions have configurable TTL, max renewals, and absolute lifetimes.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Layer 2 — Policy engine + time delay + approval:&lt;/strong&gt; Every transaction runs through a 7-stage pipeline. Stage 3 is policy evaluation. If the policy engine assigns the APPROVAL tier to a transaction, it goes into a pending state. Stage 4 is the wait stage — the daemon holds the transaction until either the delay expires or the owner approves. This is where WalletConnect operates.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Layer 3 — Monitoring + kill switch:&lt;/strong&gt; Incoming transaction monitoring with real-time notifications, and the ability to disconnect or revoke at any time.&lt;/p&gt;

&lt;p&gt;WalletConnect is the mechanism that connects Layer 2's approval gate to the wallet owner's mobile device. The owner connects their wallet via WalletConnect, and from that point forward, APPROVAL-tier transactions surface as signing requests on their phone.&lt;/p&gt;

&lt;h2&gt;
  
  
  Setting Up the Spending Limit Policy
&lt;/h2&gt;

&lt;p&gt;The APPROVAL tier isn't triggered automatically on every transaction — you configure it through a &lt;code&gt;SPENDING_LIMIT&lt;/code&gt; policy. Here's what a typical configuration looks like:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "SPENDING_LIMIT",
    "rules": {
      "instant_max_usd": 100,
      "notify_max_usd": 500,
      "delay_max_usd": 2000,
      "delay_seconds": 900,
      "daily_limit_usd": 5000
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With these rules:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Transactions under $100 → INSTANT (execute immediately, no notification)&lt;/li&gt;
&lt;li&gt;$100–$500 → NOTIFY (execute, but send you a notification)&lt;/li&gt;
&lt;li&gt;$500–$2,000 → DELAY (queue for 900 seconds, cancellable window)&lt;/li&gt;
&lt;li&gt;Over $2,000 → APPROVAL (hard stop, requires WalletConnect approval)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The policy engine enforces default-deny on top of this. Transactions to unwhitelisted tokens are blocked regardless of amount, unless you've explicitly configured &lt;code&gt;ALLOWED_TOKENS&lt;/code&gt;. This means a misconfigured agent can't accidentally drain a wallet into an unknown contract.&lt;/p&gt;

&lt;h2&gt;
  
  
  What the Agent Sees When a Transaction Needs Approval
&lt;/h2&gt;

&lt;p&gt;From Claude's perspective, when it calls &lt;code&gt;send_token&lt;/code&gt; and the transaction hits the APPROVAL tier, the tool returns a response indicating the transaction is pending owner approval. The transaction ID is available. Claude can poll &lt;code&gt;get_transaction&lt;/code&gt; to check status, or simply inform the user that approval is needed.&lt;/p&gt;

&lt;p&gt;On the owner's side, the WalletConnect request arrives on their phone as a standard wallet signing request — the same UX they'd see for any dApp interaction. They review the transaction details and approve or reject.&lt;/p&gt;

&lt;p&gt;You can also approve directly via the REST API using ownerAuth if you're not using WalletConnect:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/&amp;lt;tx-id&amp;gt;/approve &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Owner-Signature: &amp;lt;ed25519-or-secp256k1-signature&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Owner-Message: &amp;lt;signed-message&amp;gt;"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The ownerAuth uses either ed25519 (Solana, Sign In With Solana) or secp256k1 (EVM, Sign In With Ethereum) — matching whichever chain the wallet is on.&lt;/p&gt;

&lt;h2&gt;
  
  
  Dry-Run Before the Agent Commits
&lt;/h2&gt;

&lt;p&gt;One practical technique when building agent workflows: use the dry-run flag before sending real transactions. This lets Claude (or your code) simulate a transaction and see what the policy engine would decide — without actually executing anything.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/send &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "type": "TRANSFER",
    "to": "recipient-address",
    "amount": "0.1",
    "dryRun": true
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The MCP tool list also includes &lt;code&gt;simulate-transaction&lt;/code&gt; for the same purpose. In an agent workflow, you might instruct Claude to always simulate first and report the policy outcome before asking the user whether to proceed. This surfaces APPROVAL requirements before the user is surprised by a pending transaction.&lt;/p&gt;

&lt;h2&gt;
  
  
  Multi-Wallet Setup: Separate Policies Per Agent
&lt;/h2&gt;

&lt;p&gt;If you're running multiple agents — say, a trading agent and a slower, more conservative treasury agent — you can configure separate wallets with separate policies and expose them as separate MCP servers:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"mcpServers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"waiaas-trading"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"command"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"npx"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"args"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"-y"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"@waiaas/mcp"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"env"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_BASE_URL"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:3100"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_AGENT_ID"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"019c47d6-51ef-7f43-a76b-d50e875d95f4"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_AGENT_NAME"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"trading-agent"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_DATA_DIR"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"~/.waiaas"&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"waiaas-solana"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"command"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"npx"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"args"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"-y"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"@waiaas/mcp"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"env"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_BASE_URL"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:3100"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_AGENT_ID"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"019c4cd2-86e8-758f-a61e-9c560307c788"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_AGENT_NAME"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"solana-wallet"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_DATA_DIR"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"~/.waiaas"&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Each wallet gets its own spending policy. The trading wallet might have a higher INSTANT threshold. The treasury wallet might require APPROVAL for anything over $50. WalletConnect connections and approval flows are per-wallet — you're not sharing a single approval channel across all agents.&lt;/p&gt;

&lt;h2&gt;
  
  
  Quick Start: From Zero to Approval Flow
&lt;/h2&gt;

&lt;p&gt;Here's the minimal path to having WalletConnect-gated approval working in Claude Desktop:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 1 — Install and start WAIaaS:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;-g&lt;/span&gt; @waiaas/cli
waiaas init
waiaas start
waiaas quickset &lt;span class="nt"&gt;--mode&lt;/span&gt; mainnet
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;quickset&lt;/code&gt; creates wallets and MCP sessions in one step. It prints the MCP config JSON you'll need for the next step.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 2 — Add to Claude Desktop config:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Paste the output from &lt;code&gt;quickset&lt;/code&gt; into:&lt;br&gt;
&lt;code&gt;~/Library/Application Support/Claude/claude_desktop_config.json&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Or auto-register all wallets:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas mcp setup &lt;span class="nt"&gt;--all&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 3 — Create a spending limit policy with APPROVAL tier:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Use the &lt;code&gt;SPENDING_LIMIT&lt;/code&gt; policy example above. Set &lt;code&gt;delay_max_usd&lt;/code&gt; to whatever threshold makes sense for your use case. Anything above that will require explicit approval.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 4 — Connect WalletConnect via Claude:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;In Claude Desktop, ask: &lt;em&gt;"Connect my wallet via WalletConnect."&lt;/em&gt; Claude calls the &lt;code&gt;wc-connect&lt;/code&gt; MCP tool. Scan the QR code with your mobile wallet app.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 5 — Test the flow:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Ask Claude to simulate a large transfer using the &lt;code&gt;simulate-transaction&lt;/code&gt; tool. Confirm the policy would trigger APPROVAL. Then try a real transaction above your threshold and watch the mobile approval request arrive.&lt;/p&gt;

&lt;h2&gt;
  
  
  Beyond Approval: What Claude Can Do With 45 MCP Tools
&lt;/h2&gt;

&lt;p&gt;The WalletConnect approval flow is one piece of a larger capability surface. With WAIaaS's 45 MCP tools connected, Claude can:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Check wallet balance and token holdings&lt;/li&gt;
&lt;li&gt;Send native tokens or ERC-20/SPL tokens&lt;/li&gt;
&lt;li&gt;Execute DeFi actions across 15 integrated protocols (swap on Jupiter, lend on Aave, stake via Lido or Jito, trade perps on Hyperliquid)&lt;/li&gt;
&lt;li&gt;Query DeFi positions and health factors&lt;/li&gt;
&lt;li&gt;Browse and transfer NFTs (ERC-721, ERC-1155, Metaplex)&lt;/li&gt;
&lt;li&gt;Monitor incoming transactions&lt;/li&gt;
&lt;li&gt;Make x402 HTTP payments automatically when an API returns a 402 response&lt;/li&gt;
&lt;li&gt;Sign messages and build UserOps for Account Abstraction flows&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The WalletConnect tools (&lt;code&gt;wc-connect&lt;/code&gt;, &lt;code&gt;wc-disconnect&lt;/code&gt;, &lt;code&gt;wc-status&lt;/code&gt;) are the bridge that keeps you in the loop for the high-stakes subset of those actions. Everything else can run autonomously within the policy guardrails you've defined.&lt;/p&gt;

&lt;h2&gt;
  
  
  What's Next
&lt;/h2&gt;

&lt;p&gt;The full list of 21 policy types — including DeFi-specific controls like &lt;code&gt;LENDING_LTV_LIMIT&lt;/code&gt;, &lt;code&gt;PERP_MAX_LEVERAGE&lt;/code&gt;, and &lt;code&gt;VENUE_WHITELIST&lt;/code&gt; — is documented in the OpenAPI reference at &lt;code&gt;http://127.0.0.1:3100/reference&lt;/code&gt; once your daemon is running. For teams deploying WAIaaS in production, the Docker Secrets overlay and auto-provision flow handle credential management without storing passwords in environment variables.&lt;/p&gt;

&lt;p&gt;If you're building agents that need to interact with blockchains and you want a clear approval boundary between "the agent decides" and "I decide," WAIaaS's WalletConnect integration through MCP is worth an afternoon of exploration.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;GitHub: &lt;a href="https://github.com/minhoyoo-iotrust/WAIaaS" rel="noopener noreferrer"&gt;https://github.com/minhoyoo-iotrust/WAIaaS&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Official site: &lt;a href="https://waiaas.ai" rel="noopener noreferrer"&gt;https://waiaas.ai&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>ai</category>
      <category>web3</category>
      <category>security</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>The Wallet Infrastructure Layer: Why AI Agents Can't Use Traditional Finance</title>
      <dc:creator>Wallet Guy</dc:creator>
      <pubDate>Fri, 03 Jul 2026 15:21:57 +0000</pubDate>
      <link>https://dev.to/walletguy/the-wallet-infrastructure-layer-why-ai-agents-cant-use-traditional-finance-19j4</link>
      <guid>https://dev.to/walletguy/the-wallet-infrastructure-layer-why-ai-agents-cant-use-traditional-finance-19j4</guid>
      <description>&lt;h1&gt;
  
  
  The Wallet Infrastructure Layer: Why AI Agents Can't Use Traditional Finance
&lt;/h1&gt;

&lt;p&gt;AI agents will need to pay for compute, data, and API calls — and the infrastructure to let them do that autonomously doesn't exist in traditional finance. Banks require humans. Custodied accounts require human approval loops. Credit cards require a person on the other end. The moment you ask an AI agent to handle money independently, you run into a wall that the existing financial system was never designed to climb over.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Real Problem
&lt;/h2&gt;

&lt;p&gt;Think about what an AI agent actually needs to participate in an economy. It needs to hold funds. It needs to send payments without waiting for a human to click "approve." It needs to interact with DeFi protocols, pay API providers, and manage multiple chains — all while staying within the limits its operator set.&lt;/p&gt;

&lt;p&gt;Traditional finance infrastructure is built around a core assumption: a human is always in the loop. Every transaction gets reviewed. Every account is tied to a legal identity. Every authorization requires a signature from a person who can be held accountable. That's sensible design for human users. For autonomous agents, it's a complete mismatch.&lt;/p&gt;

&lt;p&gt;The stakes are real. As AI agents are increasingly asked to do economically meaningful work — managing portfolios, executing trades, paying for API access, distributing funds — the infrastructure layer they run on determines how much autonomy they actually have. Give them a custodied wallet managed by a human operator, and you've just created a bottleneck. Every transaction becomes a support ticket. Every edge case stops the agent cold.&lt;/p&gt;

&lt;p&gt;What agents need is wallet infrastructure designed from the start for autonomous operation: programmable spending controls, multiple security tiers, and the ability to execute transactions without a human in the critical path for routine operations.&lt;/p&gt;

&lt;h2&gt;
  
  
  What "Autonomous Wallet Infrastructure" Actually Means
&lt;/h2&gt;

&lt;p&gt;WAIaaS (Wallet-as-a-Service for AI agents) is an open-source, self-hosted system built specifically for this problem. It exists today. You can run it with Docker in under five minutes. The architecture is worth understanding because it reflects a genuinely different set of assumptions about who (or what) is holding the wallet.&lt;/p&gt;

&lt;p&gt;The core separation is this: the &lt;strong&gt;owner&lt;/strong&gt; of the funds is a human. The &lt;strong&gt;operator&lt;/strong&gt; of the wallet is an AI agent. WAIaaS keeps these roles clearly distinct through three authentication layers.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;masterAuth&lt;/strong&gt; (Argon2id) is the system administrator — the human who creates wallets, configures policies, and manages sessions. &lt;strong&gt;ownerAuth&lt;/strong&gt; (SIWS/SIWE) is the fund owner — a human who can approve high-value transactions or invoke a kill switch if something goes wrong. &lt;strong&gt;sessionAuth&lt;/strong&gt; (JWT HS256) is what the AI agent uses — a scoped token that grants the agent the ability to execute transactions within pre-approved limits.&lt;/p&gt;

&lt;p&gt;This three-layer design means an agent can run independently for routine operations, while humans retain hard controls over anything beyond defined thresholds.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Policy Engine: Where Rules Replace Humans
&lt;/h2&gt;

&lt;p&gt;The reason autonomous operation is safe in WAIaaS is the policy engine. It has 21 policy types and four security tiers. Before a transaction executes, it runs through a 7-stage pipeline that includes validation, authentication, policy evaluation, and confirmation.&lt;/p&gt;

&lt;p&gt;The four tiers are:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;INSTANT&lt;/strong&gt; — Execute immediately, no notification&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;NOTIFY&lt;/strong&gt; — Execute immediately, send the owner a notification&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;DELAY&lt;/strong&gt; — Queue for a configurable number of seconds, then execute (cancellable)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;APPROVAL&lt;/strong&gt; — Require explicit human approval via WalletConnect, Telegram, or push notification&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;A &lt;code&gt;SPENDING_LIMIT&lt;/code&gt; policy ties transaction size to these tiers automatically:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "SPENDING_LIMIT",
    "rules": {
      "instant_max_usd": 100,
      "notify_max_usd": 500,
      "delay_max_usd": 2000,
      "delay_seconds": 900,
      "daily_limit_usd": 5000
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With this config, an agent paying a $12 API invoice executes immediately. A $300 transfer sends a notification but still goes through. A $1,500 transaction queues for 15 minutes, giving the owner time to cancel if something looks wrong. Anything over $2,000 requires explicit human approval. The agent doesn't stop — it just escalates correctly based on stakes.&lt;/p&gt;

&lt;p&gt;Beyond spending limits, you can lock down which tokens an agent can move (&lt;code&gt;ALLOWED_TOKENS&lt;/code&gt;), which contracts it can call (&lt;code&gt;CONTRACT_WHITELIST&lt;/code&gt;), which networks it can operate on (&lt;code&gt;ALLOWED_NETWORKS&lt;/code&gt;), and even which trading venues it can use (&lt;code&gt;VENUE_WHITELIST&lt;/code&gt;). The policy system enforces default-deny on these dimensions: if &lt;code&gt;ALLOWED_TOKENS&lt;/code&gt; is configured and a token isn't on the list, the transaction is blocked, period.&lt;/p&gt;

&lt;p&gt;For DeFi operations specifically, there are policies for maximum leverage on perpetual futures (&lt;code&gt;PERP_MAX_LEVERAGE&lt;/code&gt;), loan-to-value limits for lending protocols (&lt;code&gt;LENDING_LTV_LIMIT&lt;/code&gt;), and position size caps (&lt;code&gt;PERP_MAX_POSITION_USD&lt;/code&gt;). An agent running a trading strategy genuinely can't exceed the risk parameters its operator set — not through a bug, not through a misunderstanding.&lt;/p&gt;

&lt;h2&gt;
  
  
  x402: Machines That Pay for What They Use
&lt;/h2&gt;

&lt;p&gt;One of the most forward-looking pieces of WAIaaS is its support for the x402 HTTP payment protocol. The idea is straightforward: when an AI agent makes an HTTP request to a paid API, the server returns a &lt;code&gt;402 Payment Required&lt;/code&gt; response. The agent automatically handles the payment and retries the request. No human approval. No credit card. No invoice cycle.&lt;/p&gt;

&lt;p&gt;WAIaaS exposes this through both the REST API and the TypeScript SDK:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSClient&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@waiaas/sdk&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;WAIaaSClient&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="na"&gt;baseUrl&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;http://127.0.0.1:3100&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;sessionToken&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;WAIAAS_SESSION_TOKEN&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;

&lt;span class="c1"&gt;// This automatically handles 402 Payment Required responses&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;response&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;x402Fetch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;https://api.example.com/data&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The agent calls &lt;code&gt;x402Fetch&lt;/code&gt; instead of a plain HTTP fetch. If the server charges for access, the payment happens in the background. The &lt;code&gt;X402_ALLOWED_DOMAINS&lt;/code&gt; policy type controls which endpoints the agent is permitted to pay automatically — so an agent can't be redirected into paying arbitrary addresses.&lt;/p&gt;

&lt;p&gt;This is what autonomous economic participation looks like in practice. An agent that needs data pays for data. An agent that needs compute pays for compute. The whole cycle happens without a human approving each transaction, but within a policy envelope that keeps it safe.&lt;/p&gt;

&lt;h2&gt;
  
  
  Connecting an Agent: The MCP Path
&lt;/h2&gt;

&lt;p&gt;The most common way to connect a capable AI agent like Claude to WAIaaS today is through the Model Context Protocol. WAIaaS provides 45 MCP tools covering wallet operations, transactions, DeFi, NFTs, and x402 payments.&lt;/p&gt;

&lt;p&gt;Setup is a single CLI command:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas mcp setup &lt;span class="nt"&gt;--all&lt;/span&gt;    &lt;span class="c"&gt;# Auto-register all wallets with Claude Desktop&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Or you can configure it manually in &lt;code&gt;claude_desktop_config.json&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"mcpServers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"waiaas"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"command"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"npx"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"args"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"-y"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"@waiaas/mcp"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"env"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_BASE_URL"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:3100"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_SESSION_TOKEN"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"wai_sess_&amp;lt;your-token&amp;gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_DATA_DIR"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"~/.waiaas"&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After that, Claude can check balances, send tokens, query DeFi positions across 15 integrated protocols, trade on Hyperliquid, swap on Jupiter, and pay x402-gated APIs — all through natural language. The agent doesn't need to know the underlying mechanics. It just calls tools.&lt;/p&gt;

&lt;p&gt;If you're running multiple specialized agents — a trading agent, a data-fetching agent, a treasury management agent — you can give each one its own MCP server entry pointing at a different session token with different policy constraints. One agent can't touch the funds or the policy envelope of another.&lt;/p&gt;

&lt;h2&gt;
  
  
  The DeFi Layer: 15 Protocols, One Interface
&lt;/h2&gt;

&lt;p&gt;For agents that need to do more than move money around, WAIaaS integrates 15 DeFi protocol providers: Aave v3, Across, D'CENT Swap, Drift, ERC-8004, Hyperliquid, Jito staking, Jupiter Swap, Kamino, Lido staking, LI.FI, Pendle, Polymarket, XRPL DEX, and 0x Swap.&lt;/p&gt;

&lt;p&gt;An agent executing a Jupiter swap on Solana looks like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/actions/jupiter-swap/swap &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "inputMint": "So11111111111111111111111111111111111111112",
    "outputMint": "EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v",
    "amount": "1000000000"
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's an agent swapping SOL for USDC. The transaction runs through the full 7-stage pipeline — validated, policy-checked, executed, confirmed. If the agent's policy doesn't permit this token pair, the request fails with a clear &lt;code&gt;POLICY_DENIED&lt;/code&gt; error rather than silently doing something unintended:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"error"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"code"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"POLICY_DENIED"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"message"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Transaction denied by SPENDING_LIMIT policy"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"domain"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"POLICY"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"retryable"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Agents operating in financial markets also need to know what's about to happen before it happens. WAIaaS has a dry-run mode that simulates a transaction without executing it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/send &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "type": "TRANSFER",
    "to": "recipient-address",
    "amount": "0.1",
    "dryRun": true
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;An agent can check whether a transaction would pass policy, estimate gas, and verify the outcome before committing. For autonomous systems operating at speed, that's a meaningful safety check.&lt;/p&gt;

&lt;h2&gt;
  
  
  Getting Running in Five Minutes
&lt;/h2&gt;

&lt;p&gt;If you want to see this working today rather than just reading about it, the path is short:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 1: Start the daemon&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git clone https://github.com/minhoyoo-iotrust/WAIaaS.git
&lt;span class="nb"&gt;cd &lt;/span&gt;WAIaaS
docker compose up &lt;span class="nt"&gt;-d&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 2: Initialize with auto-provision&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;-g&lt;/span&gt; @waiaas/cli
waiaas init &lt;span class="nt"&gt;--auto-provision&lt;/span&gt;
waiaas start
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 3: Create wallets and sessions&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas quickset &lt;span class="nt"&gt;--mode&lt;/span&gt; mainnet
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 4: Connect to Claude Desktop&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas mcp setup &lt;span class="nt"&gt;--all&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 5: Set your policies&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Use the Admin Web UI at &lt;code&gt;/admin&lt;/code&gt; or the REST API to configure spending limits, token whitelists, and network restrictions before putting real funds in.&lt;/p&gt;

&lt;p&gt;The Docker image is &lt;code&gt;ghcr.io/minhoyoo-iotrust/waiaas:latest&lt;/code&gt;, bound to &lt;code&gt;127.0.0.1:3100&lt;/code&gt; by default. For production deployments, there's a secrets overlay via &lt;code&gt;docker-compose.secrets.yml&lt;/code&gt; that keeps credentials out of environment variables and in Docker Secrets instead.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Infrastructure Question Is Already Here
&lt;/h2&gt;

&lt;p&gt;It's tempting to frame autonomous agent finance as a future problem — something to solve when AI systems become capable enough to need it. But the infrastructure question is already here. AI agents are being deployed into workflows that involve real money today. The question isn't whether agents will need wallet infrastructure. It's whether that infrastructure will be purpose-built for autonomous operation, or whether builders will keep improvising around tools designed for humans.&lt;/p&gt;

&lt;p&gt;The gap between "an agent that can talk about finance" and "an agent that can autonomously manage funds within defined constraints" is exactly the gap that purpose-built wallet infrastructure fills. The policy engine, the three-tier authentication model, x402 support, and the 15 DeFi protocol integrations exist because those requirements are real, not theoretical.&lt;/p&gt;

&lt;p&gt;If you're building systems where AI agents need to handle money — even small amounts, even for simple API payments — it's worth understanding what the infrastructure layer actually needs to look like.&lt;/p&gt;

&lt;h2&gt;
  
  
  What's Next
&lt;/h2&gt;

&lt;p&gt;The best starting point is the GitHub repository, where you'll find the full codebase, Docker setup instructions, and the CLI quickstart: &lt;a href="https://github.com/minhoyoo-iotrust/WAIaaS" rel="noopener noreferrer"&gt;https://github.com/minhoyoo-iotrust/WAIaaS&lt;/a&gt;. For a broader overview of what WAIaaS supports and the roadmap, the official site at &lt;a href="https://waiaas.ai" rel="noopener noreferrer"&gt;https://waiaas.ai&lt;/a&gt; has the current documentation. The interactive API reference is available at &lt;code&gt;/reference&lt;/code&gt; once you have a daemon running — it's the fastest way to understand what's actually available before writing any code.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>web3</category>
      <category>architecture</category>
      <category>opensource</category>
    </item>
    <item>
      <title>Lock Down Your DeFi Bot: VENUE_WHITELIST Policy for 15-Protocol Trading</title>
      <dc:creator>Wallet Guy</dc:creator>
      <pubDate>Fri, 03 Jul 2026 09:38:50 +0000</pubDate>
      <link>https://dev.to/walletguy/lock-down-your-defi-bot-venuewhitelist-policy-for-15-protocol-trading-3meo</link>
      <guid>https://dev.to/walletguy/lock-down-your-defi-bot-venuewhitelist-policy-for-15-protocol-trading-3meo</guid>
      <description>&lt;h1&gt;
  
  
  Lock Down Your DeFi Bot: VENUE_WHITELIST Policy for 15-Protocol Trading
&lt;/h1&gt;

&lt;p&gt;DeFi trading bots live and die by two things: execution speed and risk controls. You've spent weeks tuning your arbitrage logic, backtesting entry conditions, and optimizing gas — but if your bot's wallet can call any contract on any protocol it wants, one compromised session token or a single logic bug is all it takes to drain everything. The VENUE_WHITELIST policy in WAIaaS gives your bot exactly the protocols it needs and nothing more.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why Protocol Whitelisting Matters for Automated Trading
&lt;/h2&gt;

&lt;p&gt;When you're running an automated strategy, the attack surface isn't just external threats — it's your own code. A malformed output from a price oracle, an unexpected edge case in your routing logic, a dependency that starts returning bad data: any of these can produce a transaction your bot didn't intend to send. Without hard constraints on which protocols your bot can interact with, a bug becomes a catastrophic loss event.&lt;/p&gt;

&lt;p&gt;Beyond bugs, there's the session model to think about. WAIaaS issues session tokens (&lt;code&gt;wai_sess_...&lt;/code&gt;) that your bot uses for all wallet operations. If that token leaks — through logs, environment variable exposure, or a compromised deployment — you want the blast radius to be exactly zero outside your approved venue list. Policy enforcement happens server-side in the daemon's transaction pipeline, before any transaction hits the chain. Your bot can't bypass it, and neither can an attacker holding a stolen session token.&lt;/p&gt;

&lt;h2&gt;
  
  
  What You're Working With
&lt;/h2&gt;

&lt;p&gt;WAIaaS integrates 15 DeFi protocol providers: aave-v3, across, dcent-swap, drift, erc8004, hyperliquid, jito-staking, jupiter-swap, kamino, lido-staking, lifi, pendle, polymarket, xrpl-dex, and zerox-swap. That's a broad surface area for a trading bot to operate across — perpetual futures on Hyperliquid, spot swaps on Jupiter, cross-chain bridges via LI.FI and Across, lending positions on Aave and Kamino, prediction markets on Polymarket.&lt;/p&gt;

&lt;p&gt;The wallet infrastructure is built around a 7-stage transaction pipeline: validate → auth → policy → wait → execute → confirm. The policy stage is where VENUE_WHITELIST lives. Every DeFi action your bot attempts gets checked against the policy before it moves to execution. This isn't an application-layer check you can accidentally skip — it's baked into the pipeline.&lt;/p&gt;

&lt;p&gt;The policy engine has 21 policy types total, and VENUE_WHITELIST is specifically designed for this use case: restricting which trading venues and DeFi protocols a wallet session can interact with.&lt;/p&gt;

&lt;h2&gt;
  
  
  Setting Up VENUE_WHITELIST for Your Strategy
&lt;/h2&gt;

&lt;p&gt;Let's say you're running a SOL/USDC arbitrage strategy that operates across Jupiter (Solana DEX) and hedges exposure using perpetual futures on Drift. You want your bot to have access to exactly those two protocols — nothing else.&lt;/p&gt;

&lt;p&gt;First, create your wallet and a session for the bot:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Create the trading wallet&lt;/span&gt;
curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/wallets &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"name": "arb-bot-wallet", "chain": "solana", "environment": "mainnet"}'&lt;/span&gt;

&lt;span class="c"&gt;# Create a session token for the bot process&lt;/span&gt;
curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/sessions &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"walletId": "&amp;lt;wallet-uuid&amp;gt;"}'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now lock down the venue list with a VENUE_WHITELIST policy:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "VENUE_WHITELIST",
    "rules": {
      "venues": ["jupiter-swap", "drift"]
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's it. Your bot's session token can now execute Jupiter swaps and Drift perp operations. Any attempt to call aave-v3, lifi, hyperliquid, or any other provider will be rejected at the policy stage with a &lt;code&gt;POLICY_DENIED&lt;/code&gt; error before it ever touches a signing key.&lt;/p&gt;

&lt;h2&gt;
  
  
  Layering Policies for a Full Risk Stack
&lt;/h2&gt;

&lt;p&gt;VENUE_WHITELIST answers &lt;em&gt;where&lt;/em&gt; your bot can trade. You probably also want to control &lt;em&gt;how much&lt;/em&gt; it can trade and &lt;em&gt;what tokens&lt;/em&gt; it can move. The policy engine is additive — stack multiple policies on the same wallet.&lt;/p&gt;

&lt;p&gt;Add a spending limit to cap the damage from any single runaway transaction:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "SPENDING_LIMIT",
    "rules": {
      "instant_max_usd": 500,
      "notify_max_usd": 2000,
      "delay_max_usd": 10000,
      "delay_seconds": 300,
      "daily_limit_usd": 50000
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The 4-tier security model assigns each transaction to INSTANT (execute immediately), NOTIFY (execute + alert you), DELAY (queue for 5 minutes, cancellable), or APPROVAL (requires your explicit sign-off via WalletConnect or Telegram). For an automated bot, you want most normal-sized trades hitting INSTANT, with larger position adjustments triggering a notification so you know they're happening, and anything anomalously large getting queued for you to review.&lt;/p&gt;

&lt;p&gt;Add a token whitelist to prevent the bot from interacting with unknown tokens:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "ALLOWED_TOKENS",
    "rules": {
      "tokens": [
        {
          "address": "So11111111111111111111111111111111111111112",
          "symbol": "SOL",
          "chain": "solana"
        },
        {
          "address": "EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v",
          "symbol": "USDC",
          "chain": "solana"
        }
      ]
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;ALLOWED_TOKENS is default-deny: if the token isn't on the list, the transaction is blocked. Your bot physically cannot be tricked into buying a honeypot token or moving an asset you didn't pre-approve.&lt;/p&gt;

&lt;p&gt;For perpetuals trading on Drift, you can also cap leverage and restrict which markets the bot can open positions in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "PERP_MAX_LEVERAGE",
    "rules": {
      "max_leverage": 5
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And if you want to go further, PERP_ALLOWED_MARKETS lets you restrict which perpetual markets the bot can trade. No accidental position opened on an illiquid altcoin market because of a bug in your market selection logic.&lt;/p&gt;

&lt;h2&gt;
  
  
  Executing Trades from Your Bot
&lt;/h2&gt;

&lt;p&gt;Once policies are in place, your bot uses the session token for all operations. Here's what a Jupiter swap looks like from code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSClient&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@waiaas/sdk&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;WAIaaSClient&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="na"&gt;baseUrl&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;WAIAAS_BASE_URL&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;??&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;http://localhost:3100&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;sessionToken&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;WAIAAS_SESSION_TOKEN&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;

&lt;span class="c1"&gt;// This will be blocked if jupiter-swap isn't in VENUE_WHITELIST&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;swapResult&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;executeAction&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;jupiter-swap&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;swap&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="na"&gt;inputMint&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;So11111111111111111111111111111111111111112&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;outputMint&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;amount&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;1000000000&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Or directly via the REST API:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/actions/jupiter-swap/swap &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "inputMint": "So11111111111111111111111111111111111111112",
    "outputMint": "EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v",
    "amount": "1000000000"
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If your bot tries to call a venue that's not on the whitelist, it gets back a clean error response:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"error"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"code"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"POLICY_DENIED"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"message"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Transaction denied by VENUE_WHITELIST policy"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"domain"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"POLICY"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"retryable"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Your bot can catch that error and log it as an anomaly — an attempted call to an unauthorized venue is worth knowing about, whether it came from a bug or something worse.&lt;/p&gt;

&lt;h2&gt;
  
  
  Gas Conditional Execution
&lt;/h2&gt;

&lt;p&gt;One more tool worth knowing about for trading automation: gas conditional execution. WAIaaS supports executing transactions only when gas price meets a threshold you define. For EVM-based strategies, this means your bot doesn't waste gas on trades that become unprofitable because of network congestion — the transaction simply waits until gas comes down to your acceptable range, then executes automatically.&lt;/p&gt;

&lt;p&gt;This is handled in the transaction pipeline before the execute stage, so the policy and signing infrastructure still applies. You're not bypassing any of the security controls to get gas optimization.&lt;/p&gt;

&lt;h2&gt;
  
  
  Dry-Run Before You Deploy
&lt;/h2&gt;

&lt;p&gt;Before you go live with a new strategy, use the dry-run API to simulate transactions through the full pipeline — including policy checks — without actually executing them:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/send &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "type": "TRANSFER",
    "to": "recipient-address",
    "amount": "0.1",
    "dryRun": true
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Use this to verify your policy stack is configured correctly before connecting your bot to production capital. A dry-run that comes back with &lt;code&gt;POLICY_DENIED&lt;/code&gt; is much better than discovering the misconfiguration after a live trade goes wrong.&lt;/p&gt;

&lt;h2&gt;
  
  
  Quick Start: Trading Bot with VENUE_WHITELIST
&lt;/h2&gt;

&lt;p&gt;Here's the minimal path from zero to a locked-down trading wallet:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 1: Install the CLI and start the daemon&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;-g&lt;/span&gt; @waiaas/cli
waiaas init
waiaas start
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 2: Create a wallet and session for your bot&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/wallets &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"name": "trading-bot", "chain": "solana", "environment": "mainnet"}'&lt;/span&gt;

curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/sessions &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"walletId": "&amp;lt;wallet-uuid&amp;gt;"}'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 3: Apply your policy stack&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Apply VENUE_WHITELIST, SPENDING_LIMIT, ALLOWED_TOKENS, and any perp-specific policies using the examples above. Order doesn't matter — all active policies are evaluated for every transaction.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 4: Verify with a dry-run&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Use &lt;code&gt;"dryRun": true&lt;/code&gt; to confirm your policy configuration is correct before funding the wallet.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 5: Deploy your bot with the session token&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nv"&gt;WAIAAS_SESSION_TOKEN&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;wai_sess_&amp;lt;your-token&amp;gt; &lt;span class="nv"&gt;WAIAAS_BASE_URL&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;http://127.0.0.1:3100 node your-bot.js
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  What's Next
&lt;/h2&gt;

&lt;p&gt;WAIaaS is open-source and self-hosted — the code is at &lt;a href="https://github.com/minhoyoo-iotrust/WAIaaS" rel="noopener noreferrer"&gt;https://github.com/minhoyoo-iotrust/WAIaaS&lt;/a&gt; and the full documentation is at &lt;a href="https://waiaas.ai" rel="noopener noreferrer"&gt;https://waiaas.ai&lt;/a&gt;. The full list of 21 policy types, all 15 DeFi protocol providers, and the OpenAPI reference at &lt;code&gt;/reference&lt;/code&gt; are good places to start if you're designing a more complex strategy. For production deployments, the Docker setup with Docker Secrets support gives you a clean way to keep your master password out of environment variables entirely.&lt;/p&gt;

</description>
      <category>defi</category>
      <category>security</category>
      <category>api</category>
      <category>blockchain</category>
    </item>
    <item>
      <title>683 Test Files Later: How We Validate AI Agent Wallet Infrastructure</title>
      <dc:creator>Wallet Guy</dc:creator>
      <pubDate>Thu, 02 Jul 2026 09:38:24 +0000</pubDate>
      <link>https://dev.to/walletguy/683-test-files-later-how-we-validate-ai-agent-wallet-infrastructure-1nn1</link>
      <guid>https://dev.to/walletguy/683-test-files-later-how-we-validate-ai-agent-wallet-infrastructure-1nn1</guid>
      <description>&lt;p&gt;683 Test Files Later: How We Validate AI Agent Wallet Infrastructure&lt;/p&gt;

&lt;p&gt;Your AI agent can browse the web, write code, and manage files — but can it actually touch money? That's the gap WAIaaS was built to close: a self-hosted, open-source Wallet-as-a-Service that gives your AI agent a real blockchain wallet, a policy engine, and a transaction pipeline it can use autonomously. And before any of that ships to production, it has to pass more than 683 test files.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why Test Coverage Matters for Wallet Infrastructure
&lt;/h2&gt;

&lt;p&gt;When your agent sends an email, a bug means a bad email. When your agent sends 0.1 ETH to the wrong address, a bug means lost funds. The stakes are categorically different.&lt;/p&gt;

&lt;p&gt;This isn't about chasing a coverage number. It's about the fact that wallet infrastructure for AI agents sits at the intersection of two unforgiving domains: financial transactions (irreversible, high-stakes) and autonomous software (runs without human review). If you're building an agent on top of a wallet layer, you need to know that layer has been beaten up extensively before you trust it with real assets.&lt;/p&gt;

&lt;p&gt;Here's a practical look at what WAIaaS actually tests, and more importantly, what that means for you as a developer building on top of it.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Architecture Under Test
&lt;/h2&gt;

&lt;p&gt;WAIaaS is a 15-package monorepo. Each package has its own test suite, and together they cover every layer of the system an AI agent will touch.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;actions, adapters, admin, cli, core, daemon, desktop-spike,
e2e-tests, mcp, openclaw-plugin, push-relay, sdk, shared, skills, wallet-sdk
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's 683+ test files spread across packages that include:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;The transaction pipeline&lt;/strong&gt; — a 7-stage pipeline covering validate, auth, policy, wait, execute, and confirm&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;The policy engine&lt;/strong&gt; — 21 policy types and 4 security tiers&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;45 MCP tools&lt;/strong&gt; — every tool your Claude or LangChain agent will call&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;15 DeFi protocol integrations&lt;/strong&gt; — including Jupiter, Aave v3, Hyperliquid, and more&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;39 REST API route modules&lt;/strong&gt; — every endpoint the SDK talks to&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;When you call &lt;code&gt;client.sendToken()&lt;/code&gt; from the TypeScript SDK, you're exercising code that has been tested at the unit level, the integration level, and the pipeline level. Let's walk through each of those layers.&lt;/p&gt;

&lt;h2&gt;
  
  
  Layer 1: The Transaction Pipeline
&lt;/h2&gt;

&lt;p&gt;Every transaction an AI agent submits goes through a 7-stage pipeline:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;stage1-validate&lt;/strong&gt; — schema validation and chain-specific checks&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;stage2-auth&lt;/strong&gt; — session token verification&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;stage3-policy&lt;/strong&gt; — policy engine evaluation against all active policies&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;stage4-wait&lt;/strong&gt; — handles DELAY and APPROVAL tier transactions&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;stage5-execute&lt;/strong&gt; — signs and broadcasts to the network&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;stage6-confirm&lt;/strong&gt; — monitors for on-chain confirmation&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;This pipeline is what stands between your agent's intent and an actual blockchain transaction. The test suite covers every stage, including the unhappy paths: what happens when a policy blocks a transaction, what happens when a DELAY times out, what happens when broadcast fails and needs to be retried.&lt;/p&gt;

&lt;p&gt;From your agent's perspective, this pipeline is transparent. You submit a transaction and get back a status. But knowing it's there — and tested — is what lets you trust the output.&lt;/p&gt;

&lt;p&gt;Here's a basic send from the TypeScript SDK:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSClient&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSError&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@waiaas/sdk&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;WAIaaSClient&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="na"&gt;baseUrl&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;WAIAAS_BASE_URL&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;??&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;http://localhost:3100&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;sessionToken&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;WAIAAS_SESSION_TOKEN&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;

&lt;span class="c1"&gt;// Step 1: Check wallet balance&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;balance&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getBalance&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`Balance: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt; &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;symbol&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt; (&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;chain&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;/&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;network&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;)`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="c1"&gt;// Step 2: Send tokens&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;sendResult&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;sendToken&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="na"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;TRANSFER&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;to&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;recipient-address&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;amount&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;0.001&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`Transaction submitted: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;sendResult&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt; (status: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;sendResult&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;status&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;)`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="c1"&gt;// Step 3: Poll for confirmation&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;POLL_TIMEOUT_MS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;60&lt;/span&gt;&lt;span class="nx"&gt;_000&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;startTime&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Date&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="k"&gt;while &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;Date&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="nx"&gt;startTime&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="nx"&gt;POLL_TIMEOUT_MS&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;tx&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getTransaction&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;sendResult&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;tx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;status&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;COMPLETED&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`Transaction confirmed! Hash: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;tx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;txHash&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;tx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;status&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;FAILED&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;error&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`Transaction failed: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;tx&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;error&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;Promise&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;resolve&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="nf"&gt;setTimeout&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;resolve&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;1000&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The pattern is simple because the pipeline complexity is encapsulated. Your agent doesn't need to know about stage3-policy or stage4-wait. It just polls for &lt;code&gt;COMPLETED&lt;/code&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Layer 2: The Policy Engine
&lt;/h2&gt;

&lt;p&gt;The policy engine is probably the most critical thing to get right, and it's the part of WAIaaS with the most test surface area.&lt;/p&gt;

&lt;p&gt;21 policy types. 4 security tiers. Default-deny enforcement. A single misconfigured policy could either block legitimate agent transactions or, worse, allow a transaction that should have required human approval.&lt;/p&gt;

&lt;p&gt;The 4 tiers tell you exactly what will happen to a transaction:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;INSTANT   — Execute immediately, no notification
NOTIFY    — Execute immediately, send notification
DELAY     — Queue for delay_seconds, then execute (cancellable)
APPROVAL  — Require human approval via WalletConnect/Telegram/Push
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Testing this correctly means verifying every boundary condition. An &lt;code&gt;instant_max_usd&lt;/code&gt; of $10 means a $10.00 transaction is INSTANT and a $10.01 transaction is NOTIFY. Those boundary tests exist in the suite.&lt;/p&gt;

&lt;p&gt;Here's what a spending limit policy looks like when you create it via the REST API:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "SPENDING_LIMIT",
    "rules": {
      "instant_max_usd": 100,
      "notify_max_usd": 500,
      "delay_max_usd": 2000,
      "delay_seconds": 900,
      "daily_limit_usd": 5000
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And if a transaction is blocked, the error response is structured and actionable:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"error"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"code"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"POLICY_DENIED"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"message"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Transaction denied by SPENDING_LIMIT policy"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"domain"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"POLICY"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"retryable"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Your agent can catch this, log it, and surface it to a human rather than silently failing. The test suite covers both the policy evaluation logic and the error response format, so you can build reliable error handling on top of a stable contract.&lt;/p&gt;

&lt;h2&gt;
  
  
  Layer 3: The MCP Tools
&lt;/h2&gt;

&lt;p&gt;If you're building on Claude or another MCP-compatible framework, your agent interacts with WAIaaS through 45 MCP tools. Every one of those tools is a tested surface.&lt;/p&gt;

&lt;p&gt;The tool list covers the full range of what an autonomous agent might need:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Wallet operations&lt;/strong&gt;: &lt;code&gt;get-balance&lt;/code&gt;, &lt;code&gt;get-address&lt;/code&gt;, &lt;code&gt;get-assets&lt;/code&gt;, &lt;code&gt;get-wallet-info&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Transactions&lt;/strong&gt;: &lt;code&gt;send-token&lt;/code&gt;, &lt;code&gt;send-batch&lt;/code&gt;, &lt;code&gt;sign-transaction&lt;/code&gt;, &lt;code&gt;simulate-transaction&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;DeFi&lt;/strong&gt;: &lt;code&gt;action-provider&lt;/code&gt;, &lt;code&gt;get-defi-positions&lt;/code&gt;, &lt;code&gt;get-health-factor&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;NFTs&lt;/strong&gt;: &lt;code&gt;get-nft-metadata&lt;/code&gt;, &lt;code&gt;list-nfts&lt;/code&gt;, &lt;code&gt;transfer-nft&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Protocol-specific&lt;/strong&gt;: &lt;code&gt;hyperliquid&lt;/code&gt;, &lt;code&gt;polymarket&lt;/code&gt;, &lt;code&gt;x402-fetch&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Security/auth&lt;/strong&gt;: &lt;code&gt;erc8004-get-reputation&lt;/code&gt;, &lt;code&gt;wc-connect&lt;/code&gt;, &lt;code&gt;list-sessions&lt;/code&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Setting up MCP with Claude Desktop takes one command:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas mcp setup &lt;span class="nt"&gt;--all&lt;/span&gt;    &lt;span class="c"&gt;# Auto-register all wallets with Claude Desktop&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Or you can configure it manually in &lt;code&gt;claude_desktop_config.json&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"mcpServers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"waiaas"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"command"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"npx"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"args"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"-y"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"@waiaas/mcp"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"env"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_BASE_URL"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:3100"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_SESSION_TOKEN"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"wai_sess_&amp;lt;your-token&amp;gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_DATA_DIR"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"~/.waiaas"&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After that, Claude can call &lt;code&gt;get_balance&lt;/code&gt;, &lt;code&gt;send_token&lt;/code&gt;, or &lt;code&gt;execute_action&lt;/code&gt; the same way it calls any other tool — but now the infrastructure behind those calls has been validated by 683+ test files.&lt;/p&gt;

&lt;h2&gt;
  
  
  Layer 4: The DeFi Protocol Integrations
&lt;/h2&gt;

&lt;p&gt;15 DeFi protocol providers are integrated in WAIaaS:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;aave-v3, across, dcent-swap, drift, erc8004, hyperliquid,
jito-staking, jupiter-swap, kamino, lido-staking, lifi,
pendle, polymarket, xrpl-dex, zerox-swap
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Each provider has its own action logic. Testing these means mocking RPC calls, simulating swap quotes, and verifying that the action payload built for Jupiter looks correct before it ever hits mainnet.&lt;/p&gt;

&lt;p&gt;There's also a dry-run capability built into the transaction pipeline. Before your agent executes a DeFi action for real, it can simulate it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/send &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "type": "TRANSFER",
    "to": "recipient-address",
    "amount": "0.1",
    "dryRun": true
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is a first-class feature of the API, not a workaround. You can build agents that dry-run before executing and only proceed if the simulation succeeds.&lt;/p&gt;

&lt;h2&gt;
  
  
  Quick Start: Running It Yourself
&lt;/h2&gt;

&lt;p&gt;You don't need to take our word for the test coverage. You can clone the repo and run the suite locally. But if you want to get an agent connected first:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 1 — Install the CLI and start the daemon&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;-g&lt;/span&gt; @waiaas/cli
waiaas init
waiaas start
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 2 — Create wallets and sessions in one command&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas quickset &lt;span class="nt"&gt;--mode&lt;/span&gt; mainnet
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 3 — Connect to Claude Desktop&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas mcp setup &lt;span class="nt"&gt;--all&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 4 — Or use the TypeScript SDK directly&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; @waiaas/sdk
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSClient&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@waiaas/sdk&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;WAIaaSClient&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="na"&gt;baseUrl&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;http://127.0.0.1:3100&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;sessionToken&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;WAIAAS_SESSION_TOKEN&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;balance&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getBalance&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt; &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;balance&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;symbol&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 5 — Set a policy before going to mainnet&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Use the policy API to configure a spending limit before you let your agent run autonomously. Even a simple &lt;code&gt;SPENDING_LIMIT&lt;/code&gt; with a $10 instant max gives you a meaningful safety net.&lt;/p&gt;

&lt;h2&gt;
  
  
  What 683 Test Files Actually Tells You
&lt;/h2&gt;

&lt;p&gt;A number like 683 test files is only meaningful in context. Here's the context:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The transaction pipeline has stages that are individually tested — including the gas condition stage that holds transactions until gas price meets a threshold&lt;/li&gt;
&lt;li&gt;The policy engine covers all 21 policy types and their boundary conditions&lt;/li&gt;
&lt;li&gt;The 3 auth methods (masterAuth with Argon2id, ownerAuth with SIWS/SIWE, sessionAuth with JWT HS256) are each tested independently&lt;/li&gt;
&lt;li&gt;The 45 MCP tools are tested against the same transaction and policy infrastructure&lt;/li&gt;
&lt;li&gt;The OpenAPI 3.0 spec is auto-generated and available at &lt;code&gt;/doc&lt;/code&gt;, with an interactive reference UI at &lt;code&gt;/reference&lt;/code&gt; — so the API you're coding against is validated against the implementation&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;None of this means bugs don't exist. It means the team has invested in the kind of validation infrastructure that gives you a reasonable basis for trust when you're building financial tooling for autonomous agents.&lt;/p&gt;

&lt;h2&gt;
  
  
  What's Next
&lt;/h2&gt;

&lt;p&gt;If you want to go deeper on how the policy engine works in practice — especially the default-deny behavior and how to configure policies for different agent risk profiles — that's worth its own read. The security model has three distinct layers (session auth, time delay and approval, monitoring and kill switch) that work together in ways that aren't obvious from the policy API alone.&lt;/p&gt;

&lt;p&gt;The best next step is to get a local instance running and connect it to your agent. The CLI makes that fast, and the MCP integration means you can be talking to a real wallet from Claude Desktop in under ten minutes.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;GitHub: &lt;a href="https://github.com/minhoyoo-iotrust/WAIaaS" rel="noopener noreferrer"&gt;https://github.com/minhoyoo-iotrust/WAIaaS&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Official site: &lt;a href="https://waiaas.ai" rel="noopener noreferrer"&gt;https://waiaas.ai&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>testing</category>
      <category>typescript</category>
      <category>architecture</category>
      <category>opensource</category>
    </item>
    <item>
      <title>Mobile-First Transaction Approvals: Push Relay + Telegram for Trading Bot Security</title>
      <dc:creator>Wallet Guy</dc:creator>
      <pubDate>Wed, 01 Jul 2026 10:18:39 +0000</pubDate>
      <link>https://dev.to/walletguy/mobile-first-transaction-approvals-push-relay-telegram-for-trading-bot-security-b63</link>
      <guid>https://dev.to/walletguy/mobile-first-transaction-approvals-push-relay-telegram-for-trading-bot-security-b63</guid>
      <description>&lt;h1&gt;
  
  
  Mobile-First Transaction Approvals: Push Relay + Telegram for Trading Bot Security
&lt;/h1&gt;

&lt;p&gt;Trading bots move fast, but a rogue session or compromised API key can drain your wallet faster. If you're running automated trading strategies — arb bots, MEV searchers, algorithmic DeFi — you already know that speed and security are usually at war with each other. Lock things down too hard and you kill your latency. Leave too much open and one bad transaction wipes the account. WAIaaS's push relay and Telegram signing channels give you a third path: let the bot run freely within tight policy guardrails, and get a mobile ping the moment something needs a human eye.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Real Risk in Automated Trading
&lt;/h2&gt;

&lt;p&gt;Most trading bot setups have an uncomfortable secret: the bot has effectively unlimited signing power. The session token sitting in your &lt;code&gt;.env&lt;/code&gt; file can send anything, to anyone, for any amount. You're trusting that your code has no bugs, your key management is perfect, and nobody has access to that token but you.&lt;/p&gt;

&lt;p&gt;That's a lot of trust.&lt;/p&gt;

&lt;p&gt;The problem compounds at scale. When you're running Jupiter swaps, Drift perps, and LI.FI bridges from the same wallet, a single misconfigured trade or an exploit in one of those protocol integrations becomes a total-loss event. The industry answer has been "just don't keep much in the hot wallet" — but that's not a solution when your strategy requires capital on hand to execute.&lt;/p&gt;

&lt;p&gt;WAIaaS approaches this differently. Rather than treating the wallet as a raw signer, it wraps every transaction in a 7-stage pipeline — validate, auth, policy check, wait, execute, confirm — and gives you fine-grained control over which transactions go through automatically, which trigger a notification, which get delayed, and which require you to pull out your phone and approve.&lt;/p&gt;

&lt;h2&gt;
  
  
  Four Security Tiers, Not Two
&lt;/h2&gt;

&lt;p&gt;The typical "hot wallet vs. cold wallet" framing is too blunt for trading. WAIaaS uses 4 security tiers that map onto how traders actually think about risk:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;INSTANT&lt;/strong&gt; — Execute immediately, no notification. Your bot's routine rebalancing trades under a dollar threshold don't need to wake you up.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;NOTIFY&lt;/strong&gt; — Execute immediately, but send you a push or Telegram message so you know it happened. Good for medium-size trades you want visibility on without creating friction.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;DELAY&lt;/strong&gt; — Queue the transaction for a configurable number of seconds, then execute automatically unless you cancel. This is your circuit breaker for larger trades.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;APPROVAL&lt;/strong&gt; — Full stop. The transaction does not execute until you approve it via WalletConnect, Telegram, or push notification. Required for anything above your risk threshold.&lt;/p&gt;

&lt;p&gt;These tiers aren't manually assigned per transaction. They're derived automatically from your policy configuration. Set up a &lt;code&gt;SPENDING_LIMIT&lt;/code&gt; policy once, and every transaction your bot submits gets routed to the right tier based on its USD value:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "SPENDING_LIMIT",
    "rules": {
      "instant_max_usd": 100,
      "notify_max_usd": 500,
      "delay_max_usd": 2000,
      "delay_seconds": 900,
      "daily_limit_usd": 5000
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With this config: trades under $100 execute instantly (your bot doesn't feel a thing), trades between $100-$500 execute but you get a notification, trades between $500-$2,000 are queued for 15 minutes (you can cancel if something looks wrong), and anything over $2,000 requires explicit approval. The daily cap at $5,000 means a runaway bot can't blow past your intended exposure even if it tries.&lt;/p&gt;

&lt;h2&gt;
  
  
  Three Signing Channels for Mobile Approval
&lt;/h2&gt;

&lt;p&gt;When a transaction hits the APPROVAL tier, WAIaaS needs to reach you. There are 3 signing channels available: a push relay channel, a Telegram signing channel, and a wallet notification channel.&lt;/p&gt;

&lt;p&gt;The push relay is WAIaaS's own notification infrastructure — a separate Docker image (&lt;code&gt;push-relay&lt;/code&gt;) that handles delivery to mobile devices. The Telegram channel works through bot integration, which many traders already have set up for price alerts. The wallet notification channel ties into WalletConnect, letting you approve transactions from your hardware wallet's mobile app.&lt;/p&gt;

&lt;p&gt;From a trading bot perspective, this is significant. Your bot is running autonomously on a server, but you retain a physical approval step for high-value transactions without any manual process changes on the bot side. The bot submits the transaction normally; WAIaaS intercepts it at the policy stage, sends it to whichever signing channel you've configured, and waits for your response.&lt;/p&gt;

&lt;h2&gt;
  
  
  Locking Down the Attack Surface with Policies
&lt;/h2&gt;

&lt;p&gt;For a trading bot, you want more than just spending limits. WAIaaS has 21 policy types — here are the ones most relevant to automated trading:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;CONTRACT_WHITELIST&lt;/code&gt;&lt;/strong&gt; — Your bot should only be touching the protocols you've specifically authorized. If someone compromises your session token and tries to interact with an unknown contract, this blocks it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"contracts"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[{&lt;/span&gt;&lt;span class="nl"&gt;"address"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"JUP6LkbZbjS1jKKwapdHNy74zcZ3tLUZoi5QNyVTaV4"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Jupiter"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"chain"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"solana"&lt;/span&gt;&lt;span class="p"&gt;}]}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;ALLOWED_TOKENS&lt;/code&gt;&lt;/strong&gt; — Default-deny on tokens. Your arb bot that's supposed to trade SOL/USDC shouldn't be able to send random SPL tokens even if a bug tries to:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"tokens"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[{&lt;/span&gt;&lt;span class="nl"&gt;"address"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"symbol"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"USDC"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"chain"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"solana"&lt;/span&gt;&lt;span class="p"&gt;}]}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;APPROVED_SPENDERS&lt;/code&gt;&lt;/strong&gt; — If your strategy involves token approvals (EVM DeFi), this whitelist ensures approvals only go to known protocol contracts. Combined with &lt;code&gt;APPROVE_AMOUNT_LIMIT&lt;/code&gt;, you can block unlimited approvals entirely.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;PERP_MAX_LEVERAGE&lt;/code&gt;&lt;/strong&gt; and &lt;strong&gt;&lt;code&gt;PERP_MAX_POSITION_USD&lt;/code&gt;&lt;/strong&gt; — If you're running Drift perpetual strategies, these policies enforce position size limits directly at the wallet layer, independent of whatever your trading logic says. A bug that calculates 100x leverage instead of 10x gets blocked before it touches the chain.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;RATE_LIMIT&lt;/code&gt;&lt;/strong&gt; — Maximum transactions per period. If your bot suddenly starts firing 50 transactions in a minute when it normally does 5, that's a signal something went wrong:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nl"&gt;"maxTransactions"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;10&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"period"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"hourly"&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;ALLOWED_NETWORKS&lt;/code&gt;&lt;/strong&gt; — Restrict your bot to only the chains it's supposed to operate on. An Ethereum bot shouldn't be able to accidentally send to Solana and vice versa.&lt;/p&gt;

&lt;h2&gt;
  
  
  Gas Conditional Execution
&lt;/h2&gt;

&lt;p&gt;One underrated feature for trading bots: gas conditional execution. Your bot only sends the transaction when gas price meets a threshold you define. This is handled at the pipeline stage level — the transaction waits in the queue until gas conditions are satisfied rather than your bot needing to poll and resubmit.&lt;/p&gt;

&lt;p&gt;For arb strategies where your profit margin is thin, this is not a nice-to-have. A trade that pencils out at 20 gwei becomes a loss at 80 gwei. Rather than building gas oracle logic into your bot, you lean on WAIaaS's pipeline to handle the condition check.&lt;/p&gt;

&lt;h2&gt;
  
  
  Multi-Protocol Access in One API Call
&lt;/h2&gt;

&lt;p&gt;The protocol coverage matters for traders running cross-venue strategies. WAIaaS integrates 15 DeFi protocol providers: aave-v3, across, dcent-swap, drift, erc8004, hyperliquid, jito-staking, jupiter-swap, kamino, lido-staking, lifi, pendle, polymarket, xrpl-dex, and zerox-swap.&lt;/p&gt;

&lt;p&gt;That's Jupiter for Solana spot, Drift for Solana perps, Hyperliquid for perp futures and spot, LI.FI and Across for cross-chain bridging, Aave for EVM lending, Kamino for Solana lending, and Polymarket for prediction markets — all through the same session token, same API server, same policy engine.&lt;/p&gt;

&lt;p&gt;A Jupiter swap from your bot looks like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/actions/jupiter-swap/swap &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "inputMint": "So11111111111111111111111111111111111111112",
    "outputMint": "EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v",
    "amount": "1000000000"
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The same session token that executes that swap can open a Drift position, bridge proceeds via LI.FI, or stake idle SOL on Jito. The policy engine applies uniformly across all of them — you don't need to maintain separate risk logic for each protocol integration.&lt;/p&gt;

&lt;h2&gt;
  
  
  Dry Run Before You Send
&lt;/h2&gt;

&lt;p&gt;For strategies that are hard to backtest perfectly, the dry-run API is useful. You can simulate a transaction before committing:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/send &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "type": "TRANSFER",
    "to": "recipient-address",
    "amount": "0.1",
    "dryRun": true
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The same request with &lt;code&gt;"dryRun": true&lt;/code&gt; runs through the full pipeline — policy checks, validation, everything — without touching the chain. You get back exactly what would happen if you ran it live. For a new strategy going into production, this lets you validate that your transaction construction is correct and that your policies won't block it unexpectedly, before any real capital moves.&lt;/p&gt;

&lt;h2&gt;
  
  
  Quick Start: Bot with Mobile Approvals
&lt;/h2&gt;

&lt;p&gt;Here's the minimal path to a trading bot setup with push approvals for large trades:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 1 — Get WAIaaS running:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git clone https://github.com/minhoyoo-iotrust/WAIaaS.git
&lt;span class="nb"&gt;cd &lt;/span&gt;WAIaaS
docker compose up &lt;span class="nt"&gt;-d&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The daemon starts on &lt;code&gt;127.0.0.1:3100&lt;/code&gt;. Default port binding is &lt;code&gt;127.0.0.1:3100:3100&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 2 — Create a trading wallet and session:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Create the wallet&lt;/span&gt;
curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/wallets &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"name": "trading-wallet", "chain": "solana", "environment": "mainnet"}'&lt;/span&gt;

&lt;span class="c"&gt;# Create a session for your bot&lt;/span&gt;
curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/sessions &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"walletId": "&amp;lt;wallet-uuid&amp;gt;"}'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 3 — Set your spending policy:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Use the &lt;code&gt;SPENDING_LIMIT&lt;/code&gt; curl call from earlier. Tune &lt;code&gt;instant_max_usd&lt;/code&gt;, &lt;code&gt;delay_max_usd&lt;/code&gt;, and &lt;code&gt;delay_seconds&lt;/code&gt; to match your strategy's typical trade sizes. Start conservative — you can always loosen it.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 4 — Add protocol and token restrictions:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Apply &lt;code&gt;CONTRACT_WHITELIST&lt;/code&gt; and &lt;code&gt;ALLOWED_TOKENS&lt;/code&gt; policies for the specific protocols and tokens your strategy touches. Default-deny means anything not on the list is blocked, which is exactly what you want for a live trading bot.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 5 — Configure your notification channel:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Run &lt;code&gt;waiaas notification setup&lt;/code&gt; from the CLI to connect your preferred signing channel. Once configured, APPROVAL-tier transactions will route to your mobile device rather than blocking indefinitely.&lt;/p&gt;

&lt;p&gt;Your bot uses the session token for all trading operations. Large trades get queued and ping your phone. Everything else executes at the latency your strategy needs.&lt;/p&gt;

&lt;h2&gt;
  
  
  Approving from Mobile
&lt;/h2&gt;

&lt;p&gt;When a transaction hits the APPROVAL tier, you receive a mobile notification with the transaction details. The approval flow ties into WAIConnect — you review what the bot is trying to do (amount, recipient, protocol), and tap approve or reject. The transaction then either executes or is cancelled.&lt;/p&gt;

&lt;p&gt;This keeps the human-in-the-loop step lightweight. You're not re-entering keys or going through a multi-step flow — you're reviewing a specific transaction that your bot flagged itself as large enough to warrant oversight, and making a binary decision. The ownerAuth layer handles the cryptographic verification:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/&amp;lt;tx-id&amp;gt;/approve &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Owner-Signature: &amp;lt;ed25519-or-secp256k1-signature&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Owner-Message: &amp;lt;signed-message&amp;gt;"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Under the hood that's what your mobile approval is doing — generating a signature over the transaction ID that WAIaaS verifies before proceeding.&lt;/p&gt;

&lt;h2&gt;
  
  
  What's Next
&lt;/h2&gt;

&lt;p&gt;The policy system has considerably more depth than what's covered here — DeFi-specific policies like &lt;code&gt;LENDING_LTV_LIMIT&lt;/code&gt;, &lt;code&gt;PERP_MAX_LEVERAGE&lt;/code&gt;, and &lt;code&gt;VENUE_WHITELIST&lt;/code&gt; let you encode your risk parameters directly into the wallet layer rather than relying solely on your bot's logic. The full OpenAPI reference is available at &lt;code&gt;http://127.0.0.1:3100/reference&lt;/code&gt; once your daemon is running, with interactive docs you can use to explore the 39 REST API route modules before writing a line of code.&lt;/p&gt;

&lt;p&gt;For the full codebase and deployment configs, head to &lt;a href="https://github.com/minhoyoo-iotrust/WAIaaS" rel="noopener noreferrer"&gt;https://github.com/minhoyoo-iotrust/WAIaaS&lt;/a&gt;. Documentation and further resources are at &lt;a href="https://waiaas.ai" rel="noopener noreferrer"&gt;https://waiaas.ai&lt;/a&gt;.&lt;/p&gt;

</description>
      <category>defi</category>
      <category>security</category>
      <category>api</category>
      <category>selfhosted</category>
    </item>
    <item>
      <title>Self-Documenting AI Agents: OpenAPI 3.0 Spec Generation for MCP Tools</title>
      <dc:creator>Wallet Guy</dc:creator>
      <pubDate>Wed, 24 Jun 2026 15:37:47 +0000</pubDate>
      <link>https://dev.to/walletguy/self-documenting-ai-agents-openapi-30-spec-generation-for-mcp-tools-jld</link>
      <guid>https://dev.to/walletguy/self-documenting-ai-agents-openapi-30-spec-generation-for-mcp-tools-jld</guid>
      <description>&lt;h1&gt;
  
  
  Self-Documenting AI Agents: OpenAPI 3.0 Spec Generation for MCP Tools
&lt;/h1&gt;

&lt;p&gt;MCP developers building onchain AI agents often hit the same wall: your Claude agent can reason brilliantly, but it has no idea what tools are actually available, what parameters they expect, or how to authenticate. WAIaaS solves this by combining 45 MCP tools with a live OpenAPI 3.0 spec — so your agent always has accurate, machine-readable documentation for every wallet, transaction, and DeFi action it can take.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why This Actually Matters
&lt;/h2&gt;

&lt;p&gt;When you wire an AI agent to onchain infrastructure, documentation isn't a nice-to-have — it's load-bearing. If your agent guesses at parameter names, misunderstands authentication requirements, or doesn't know which networks are supported, it makes mistakes with real money. The combination of MCP tooling and a live OpenAPI spec means two things: Claude gets structured tool definitions through the MCP protocol, and any HTTP client (including other agents, scripts, or dashboards you build) can discover the full API surface automatically. Both layers stay in sync because they're generated from the same codebase.&lt;/p&gt;

&lt;h2&gt;
  
  
  One Line in Your Config
&lt;/h2&gt;

&lt;p&gt;Let's start with the fastest path. Add this to your &lt;code&gt;claude_desktop_config.json&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"mcpServers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"waiaas"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"command"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"npx"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"args"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"-y"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"@waiaas/mcp"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"env"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_BASE_URL"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:3100"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_SESSION_TOKEN"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"wai_sess_&amp;lt;your-token&amp;gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_DATA_DIR"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"~/.waiaas"&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's it. Restart Claude Desktop and your agent now has access to 45 MCP tools covering wallet management, token transfers, DeFi actions, NFT operations, and x402 HTTP payment — all authenticated, all policy-governed, all with typed parameters that Claude can introspect before calling them.&lt;/p&gt;

&lt;p&gt;The MCP server package is &lt;code&gt;@waiaas/mcp&lt;/code&gt; on npm, transport is stdio, and tools are served with full schema definitions so Claude understands input shapes without guessing.&lt;/p&gt;

&lt;h2&gt;
  
  
  What the 45 Tools Actually Cover
&lt;/h2&gt;

&lt;p&gt;The tool list isn't just send-token and check-balance. Here's the full scope across categories:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Wallet &amp;amp; balance:&lt;/strong&gt; &lt;code&gt;get-wallet-info&lt;/code&gt;, &lt;code&gt;get-address&lt;/code&gt;, &lt;code&gt;get-balance&lt;/code&gt;, &lt;code&gt;get-assets&lt;/code&gt;, &lt;code&gt;get-nonce&lt;/code&gt;, &lt;code&gt;connect-info&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Transactions:&lt;/strong&gt; &lt;code&gt;send-token&lt;/code&gt;, &lt;code&gt;send-batch&lt;/code&gt;, &lt;code&gt;sign-transaction&lt;/code&gt;, &lt;code&gt;sign-message&lt;/code&gt;, &lt;code&gt;simulate-transaction&lt;/code&gt;, &lt;code&gt;get-transaction&lt;/code&gt;, &lt;code&gt;list-transactions&lt;/code&gt;, &lt;code&gt;list-incoming-transactions&lt;/code&gt;, &lt;code&gt;get-incoming-summary&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;DeFi:&lt;/strong&gt; &lt;code&gt;action-provider&lt;/code&gt;, &lt;code&gt;get-defi-positions&lt;/code&gt;, &lt;code&gt;get-health-factor&lt;/code&gt;, &lt;code&gt;approve-token&lt;/code&gt;, &lt;code&gt;list-offchain-actions&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Account Abstraction:&lt;/strong&gt; &lt;code&gt;build-userop&lt;/code&gt;, &lt;code&gt;sign-userop&lt;/code&gt;, &lt;code&gt;encode-calldata&lt;/code&gt;, &lt;code&gt;call-contract&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;NFT:&lt;/strong&gt; &lt;code&gt;get-nft-metadata&lt;/code&gt;, &lt;code&gt;list-nfts&lt;/code&gt;, &lt;code&gt;transfer-nft&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Protocols:&lt;/strong&gt; &lt;code&gt;hyperliquid&lt;/code&gt;, &lt;code&gt;polymarket&lt;/code&gt;, &lt;code&gt;resolve-asset&lt;/code&gt;, &lt;code&gt;get-tokens&lt;/code&gt;, &lt;code&gt;get-provider-status&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Sessions &amp;amp; auth:&lt;/strong&gt; &lt;code&gt;list-sessions&lt;/code&gt;, &lt;code&gt;list-credentials&lt;/code&gt;, &lt;code&gt;get-policies&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;ERC standards:&lt;/strong&gt; &lt;code&gt;erc8004-get-agent-info&lt;/code&gt;, &lt;code&gt;erc8004-get-reputation&lt;/code&gt;, &lt;code&gt;erc8004-get-validation-status&lt;/code&gt;, &lt;code&gt;erc8128-sign-request&lt;/code&gt;, &lt;code&gt;erc8128-verify-signature&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;WalletConnect:&lt;/strong&gt; &lt;code&gt;wc-connect&lt;/code&gt;, &lt;code&gt;wc-disconnect&lt;/code&gt;, &lt;code&gt;wc-status&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Utility:&lt;/strong&gt; &lt;code&gt;get-rpc-proxy-url&lt;/code&gt;, &lt;code&gt;x402-fetch&lt;/code&gt;, &lt;code&gt;get-transaction&lt;/code&gt; (with full hash resolution)&lt;/p&gt;

&lt;p&gt;When Claude sees &lt;code&gt;simulate-transaction&lt;/code&gt; in the tool list, it knows it can dry-run before executing. When it sees &lt;code&gt;get-health-factor&lt;/code&gt;, it understands DeFi lending positions are trackable. The schema-first design means Claude reasons about what's possible before committing to an action.&lt;/p&gt;

&lt;h2&gt;
  
  
  The OpenAPI Layer: For Everything Else
&lt;/h2&gt;

&lt;p&gt;The MCP interface handles Claude. But you probably also have scripts, dashboards, or other agents that talk to WAIaaS over HTTP. That's where the OpenAPI 3.0 spec comes in.&lt;/p&gt;

&lt;p&gt;WAIaaS auto-generates a live OpenAPI spec at &lt;code&gt;/doc&lt;/code&gt; and serves an interactive Scalar API reference at &lt;code&gt;/reference&lt;/code&gt;. Both stay current with the actual implementation — 39 REST API route modules feeding a single spec.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Download the OpenAPI 3.0 spec&lt;/span&gt;
curl http://127.0.0.1:3100/doc &lt;span class="nt"&gt;-o&lt;/span&gt; openapi.json

&lt;span class="c"&gt;# View the interactive reference in your browser&lt;/span&gt;
open http://127.0.0.1:3100/reference
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The interactive UI at &lt;code&gt;/reference&lt;/code&gt; is useful during development: you can see every endpoint, its authentication requirement, request schema, and response shape without reading source code. When you're building a policy configuration or debugging a DeFi action response, this is significantly faster than grepping through documentation.&lt;/p&gt;

&lt;p&gt;The spec is also what you'd feed to another agent or code generator. If you're building a second AI agent that orchestrates WAIaaS over REST rather than MCP, point it at &lt;code&gt;/doc&lt;/code&gt; and it has a complete, accurate description of the API surface.&lt;/p&gt;

&lt;h2&gt;
  
  
  Authentication Is Part of the Schema
&lt;/h2&gt;

&lt;p&gt;One thing that trips up developers building multi-agent systems: WAIaaS uses three distinct authentication methods, and the OpenAPI spec documents which endpoints require which.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# masterAuth — create wallets, manage sessions, set policies&lt;/span&gt;
&lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt;

&lt;span class="c"&gt;# sessionAuth — AI agent operations (transactions, balance, DeFi)&lt;/span&gt;
&lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_eyJhbGciOiJIUzI1NiJ9..."&lt;/span&gt;

&lt;span class="c"&gt;# ownerAuth — human approval for high-value transactions&lt;/span&gt;
&lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Owner-Signature: &amp;lt;ed25519-or-secp256k1-signature&amp;gt;"&lt;/span&gt;
&lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Owner-Message: &amp;lt;signed-message&amp;gt;"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the MCP context, the session token you put in &lt;code&gt;WAIAAS_SESSION_TOKEN&lt;/code&gt; handles all agent-facing operations. The session was created by a human operator using masterAuth — the agent never sees the master password. This separation is intentional: the agent has a scoped credential with policy limits, not root access to the wallet system.&lt;/p&gt;

&lt;h2&gt;
  
  
  Setting Up a Multi-Wallet MCP Configuration
&lt;/h2&gt;

&lt;p&gt;For more sophisticated setups — say, a trading agent and a separate Solana wallet agent — you can run multiple named MCP servers pointing at the same WAIaaS daemon:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"mcpServers"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"waiaas-trading"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"command"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"npx"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"args"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"-y"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"@waiaas/mcp"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"env"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_BASE_URL"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:3100"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_AGENT_ID"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"019c47d6-51ef-7f43-a76b-d50e875d95f4"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_AGENT_NAME"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"trading-agent"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_DATA_DIR"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"~/.waiaas"&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"waiaas-solana"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"command"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"npx"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"args"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"-y"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"@waiaas/mcp"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"env"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_BASE_URL"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"http://127.0.0.1:3100"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_AGENT_ID"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"019c4cd2-86e8-758f-a61e-9c560307c788"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_AGENT_NAME"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"solana-wallet"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
        &lt;/span&gt;&lt;span class="nl"&gt;"WAIAAS_DATA_DIR"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"~/.waiaas"&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Each MCP server instance has its own session token scoped to a specific wallet. Claude sees both as separate tool namespaces and can reason about which wallet to use for which operation — all documented through the MCP tool schemas.&lt;/p&gt;

&lt;h2&gt;
  
  
  What Claude Can Actually Do After This
&lt;/h2&gt;

&lt;p&gt;Here's what the interaction looks like in practice once MCP is connected:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;User: "Check my wallet balance"
→ Claude calls get_balance tool → returns balance

User: "Swap 0.1 SOL for USDC on Jupiter"
→ Claude calls execute_action tool with jupiter-swap provider

User: "Show my DeFi positions across all protocols"
→ Claude calls get_defi_positions tool → returns lending/staking positions
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The Jupiter swap call hits one of 15 integrated DeFi protocol providers — including Aave v3, Across, Drift, Hyperliquid, Jito staking, Jupiter swap, Kamino, Lido staking, LI.FI, Pendle, Polymarket, XRPL DEX, and 0x swap, among others. Claude doesn't need to know the protocol-specific parameters because the tool schema defines them.&lt;/p&gt;

&lt;p&gt;Before any transaction executes, the 7-stage pipeline processes it: validate → auth → policy → wait → execute → confirm. If a policy blocks it, Claude gets back a structured error:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"error"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"code"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"POLICY_DENIED"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"message"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"Transaction denied by SPENDING_LIMIT policy"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"domain"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"POLICY"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"retryable"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That error code is something Claude can reason about — it knows the transaction was blocked by a spending limit, not a network error, and can explain that to the user or suggest alternatives.&lt;/p&gt;

&lt;h2&gt;
  
  
  Quick Start: From Zero to MCP Tools in 5 Steps
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Step 1: Install the CLI and initialize&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;-g&lt;/span&gt; @waiaas/cli
waiaas init
waiaas start
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 2: Create wallets and sessions in one command&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas quickset &lt;span class="nt"&gt;--mode&lt;/span&gt; mainnet
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This creates wallets and MCP sessions. The output includes the MCP config JSON.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 3: Register with Claude Desktop automatically&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas mcp setup &lt;span class="nt"&gt;--all&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 4: Verify the OpenAPI spec is live&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl http://127.0.0.1:3100/doc &lt;span class="nt"&gt;-o&lt;/span&gt; openapi.json
&lt;span class="c"&gt;# Then open http://127.0.0.1:3100/reference in your browser&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 5: Set a spending policy so the agent has safe limits&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "SPENDING_LIMIT",
    "rules": {
      "instant_max_usd": 100,
      "notify_max_usd": 500,
      "delay_max_usd": 2000,
      "delay_seconds": 900,
      "daily_limit_usd": 5000
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Restart Claude Desktop and ask it to check your balance.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Self-Documenting Part
&lt;/h2&gt;

&lt;p&gt;The reason this system is "self-documenting" isn't marketing language — it's a practical property. The 45 MCP tools and the 39 REST API route modules both derive their schemas from the same source. When WAIaaS adds a new capability, the OpenAPI spec at &lt;code&gt;/doc&lt;/code&gt; updates automatically, the interactive reference at &lt;code&gt;/reference&lt;/code&gt; reflects it, and the MCP tool definitions that Claude receives are current.&lt;/p&gt;

&lt;p&gt;For developers building on top of WAIaaS — whether you're writing an agent orchestration layer, a monitoring dashboard, or a second AI system that talks to WAIaaS over HTTP — you always have an accurate map of the territory. You don't maintain separate documentation, you don't discover parameter mismatches at runtime, and you don't need to read source code to understand what's available.&lt;/p&gt;

&lt;p&gt;That's the core value proposition for MCP developers specifically: you get 45 typed, schema-defined tools that Claude can introspect, plus a live HTTP API that any other client can discover — all from a single self-hosted daemon you control.&lt;/p&gt;

&lt;h2&gt;
  
  
  What's Next
&lt;/h2&gt;

&lt;p&gt;If you want to explore the policy engine in depth — setting spending limits, token whitelists, and DeFi-specific controls like maximum leverage — the 21 policy types give you fine-grained control over what your agent can and can't do autonomously. The Docker deployment path is also worth looking at if you're running this in a persistent server environment rather than locally.&lt;/p&gt;

&lt;p&gt;The full codebase, including the MCP package and all 15 DeFi protocol providers, is at &lt;a href="https://github.com/minhoyoo-iotrust/WAIaaS" rel="noopener noreferrer"&gt;https://github.com/minhoyoo-iotrust/WAIaaS&lt;/a&gt;. More documentation and the official site are at &lt;a href="https://waiaas.ai" rel="noopener noreferrer"&gt;https://waiaas.ai&lt;/a&gt;.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>api</category>
      <category>opensource</category>
      <category>webdev</category>
    </item>
    <item>
      <title>Building the Financial Rails for Machine-to-Machine Commerce</title>
      <dc:creator>Wallet Guy</dc:creator>
      <pubDate>Wed, 24 Jun 2026 09:53:56 +0000</pubDate>
      <link>https://dev.to/walletguy/building-the-financial-rails-for-machine-to-machine-commerce-4k3l</link>
      <guid>https://dev.to/walletguy/building-the-financial-rails-for-machine-to-machine-commerce-4k3l</guid>
      <description>&lt;h1&gt;
  
  
  Building the Financial Rails for Machine-to-Machine Commerce
&lt;/h1&gt;

&lt;p&gt;AI agents will need to pay for compute, data, and API calls — and right now, almost nothing in the infrastructure stack is built to handle that. We talk endlessly about autonomous agents that book travel, execute trades, and negotiate contracts, but when the conversation turns to &lt;em&gt;how they pay&lt;/em&gt;, the answer is usually a hand-wave. Humans still hold the keys, approve every transaction, and act as financial intermediaries for systems that are supposed to operate independently. That's not autonomy. That's a chatbot with extra steps.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Missing Layer
&lt;/h2&gt;

&lt;p&gt;Think about what a truly autonomous AI agent needs to participate in economic activity. It needs to hold funds. It needs to authorize payments without waking a human up at 3 AM. It needs spending guardrails so it can't accidentally drain a treasury on a bad swap. It needs to handle multiple chains because the internet doesn't run on one blockchain. And it needs to do all of this without a centralized custodian that becomes a single point of failure — or control.&lt;/p&gt;

&lt;p&gt;None of the standard wallet tooling was designed for this. Browser extension wallets need a human to click "confirm." Custodial APIs introduce a trust assumption that defeats the purpose of autonomous operation. Raw key management libraries give you signing primitives but nothing resembling a policy engine or an approval workflow.&lt;/p&gt;

&lt;p&gt;The financial rails for machine-to-machine commerce aren't missing because the problem is unsolved. They're missing because the industry has been building for human users. Agents are a different actor class entirely, and they need infrastructure built specifically for them.&lt;/p&gt;

&lt;h2&gt;
  
  
  What Agent-Native Wallet Infrastructure Looks Like
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://waiaas.ai" rel="noopener noreferrer"&gt;WAIaaS&lt;/a&gt; — Wallet-as-a-Service for AI agents — is an open-source, self-hosted daemon that exists specifically to close this gap. It's running today. You can deploy it in under five minutes with Docker. Here's what makes it different from gluing together a keystore and a REST API yourself.&lt;/p&gt;

&lt;h3&gt;
  
  
  The Architecture: Three Auth Layers for Three Actor Classes
&lt;/h3&gt;

&lt;p&gt;The fundamental insight in WAIaaS's design is that &lt;em&gt;who&lt;/em&gt; is touching the wallet matters enormously. There are three distinct actors with three distinct trust levels:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The system administrator&lt;/strong&gt; sets up wallets, creates sessions, and defines policies. They authenticate with a master password hashed using Argon2id. They should almost never be involved in day-to-day operations.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The AI agent&lt;/strong&gt; runs transactions, checks balances, executes DeFi actions. It authenticates with a session JWT (&lt;code&gt;wai_sess_...&lt;/code&gt;). Sessions have configurable TTL, max renewals, and absolute lifetime. The agent gets exactly the access you scope to it — no more.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The fund owner&lt;/strong&gt; — the human who actually owns the money — can approve transactions, connect via WalletConnect, and activate a kill switch if something goes wrong. They authenticate with a cryptographic signature (SIWS or SIWE), not a password.&lt;/p&gt;

&lt;p&gt;This isn't three passwords for the same interface. It's three genuinely different security principals with different capabilities and different threat models.&lt;/p&gt;

&lt;h3&gt;
  
  
  The Policy Engine: Rules That Run Without Human Intervention
&lt;/h3&gt;

&lt;p&gt;The reason you can let an agent operate autonomously is that you've already told the system what it's allowed to do. WAIaaS ships a policy engine with 21 policy types and 4 security tiers: INSTANT, NOTIFY, DELAY, and APPROVAL.&lt;/p&gt;

&lt;p&gt;The tiers work like this: small transactions execute immediately. Medium transactions execute and notify you. Large transactions queue for a time delay (during which you can cancel). Very large transactions require explicit human approval. You define the dollar thresholds.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/policies &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "walletId": "&amp;lt;wallet-uuid&amp;gt;",
    "type": "SPENDING_LIMIT",
    "rules": {
      "instant_max_usd": 100,
      "notify_max_usd": 500,
      "delay_max_usd": 2000,
      "delay_seconds": 900,
      "daily_limit_usd": 5000
    }
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With this policy in place, an agent paying a $12 API bill executes immediately. An agent trying to move $3,000 in one shot waits 15 minutes and you get a notification. An agent trying to do something truly unusual hits an approval gate.&lt;/p&gt;

&lt;p&gt;The default is &lt;em&gt;deny&lt;/em&gt;. If you haven't configured &lt;code&gt;ALLOWED_TOKENS&lt;/code&gt; or &lt;code&gt;CONTRACT_WHITELIST&lt;/code&gt;, transactions are blocked. This is the right default for autonomous systems. You opt into access; you don't opt out of it.&lt;/p&gt;

&lt;p&gt;Beyond spending limits, the full policy set covers: token whitelists, contract whitelists, rate limits, time restrictions, allowed networks, approved spenders, approval amount limits, DeFi-specific controls like LTV limits and max perpetual leverage, and even ERC-8004 onchain reputation thresholds. The policy engine isn't an afterthought — it's the thing that makes autonomous operation safe enough to actually deploy.&lt;/p&gt;

&lt;h3&gt;
  
  
  x402: The Payment Protocol Agents Were Waiting For
&lt;/h3&gt;

&lt;p&gt;The most interesting capability for machine-to-machine commerce specifically is x402 HTTP payment protocol support. x402 extends HTTP with a &lt;code&gt;402 Payment Required&lt;/code&gt; status — when an API returns a 402, the client automatically pays and retries. No human interaction. No pre-negotiated API keys. Just an agent that pays for what it uses.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSClient&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@waiaas/sdk&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;WAIaaSClient&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="na"&gt;baseUrl&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;http://127.0.0.1:3100&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;sessionToken&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;WAIAAS_SESSION_TOKEN&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;

&lt;span class="c1"&gt;// This fetch automatically handles 402 Payment Required responses&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;response&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;x402Fetch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;https://api.example.com/premium-data&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;From the agent's perspective, it's just an HTTP call. The wallet handles the 402 negotiation transparently. This is what actual machine-to-machine micropayments look like in practice — not a whitepaper concept, but a working implementation you can wire into an agent loop today.&lt;/p&gt;

&lt;p&gt;You can lock down which domains an agent is allowed to pay automatically using the &lt;code&gt;X402_ALLOWED_DOMAINS&lt;/code&gt; policy, so an agent can't be tricked into paying arbitrary endpoints.&lt;/p&gt;

&lt;h3&gt;
  
  
  7-Stage Transaction Pipeline
&lt;/h3&gt;

&lt;p&gt;Every transaction — whether it's a simple token transfer, a DeFi action, or an NFT transfer — runs through a 7-stage pipeline: validate, auth, policy, wait, execute, confirm. The "wait" stage is where time-delay policies live. The "policy" stage is where spending limits and whitelists fire. The architecture means every transaction goes through the same safety checks regardless of how it was initiated.&lt;/p&gt;

&lt;p&gt;There's also a dry-run mode for simulating transactions before execution:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/transactions/send &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "type": "TRANSFER",
    "to": "recipient-address",
    "amount": "0.1",
    "dryRun": true
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;A well-built agent doesn't fire transactions blindly. It simulates first, checks the result, then executes. The infrastructure needs to support that workflow, and WAIaaS does.&lt;/p&gt;

&lt;h3&gt;
  
  
  Multi-Chain From Day One
&lt;/h3&gt;

&lt;p&gt;Agent commerce doesn't happen on one chain. WAIaaS supports 2 chain types (EVM and Solana) across 18 networks. The same session token works whether the agent is moving USDC on Ethereum, swapping on Jupiter, or staking SOL via Jito. The wallet abstraction handles chain-specific details — nonces, fee structures, address formats — so agent code stays clean.&lt;/p&gt;

&lt;p&gt;15 DeFi protocol providers are integrated out of the box: Aave v3, Across, D'CENT Swap, Drift, ERC-8004, Hyperliquid, Jito Staking, Jupiter Swap, Kamino, Lido Staking, LI.FI, Pendle, Polymarket, XRPL DEX, and 0x Swap. An agent that needs to rebalance a portfolio, bridge funds cross-chain, enter a yield position, or trade perpetuals can do all of it through the same interface, subject to the same policy engine.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/actions/jupiter-swap/swap &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Authorization: Bearer wai_sess_&amp;lt;token&amp;gt;"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{
    "inputMint": "So11111111111111111111111111111111111111112",
    "outputMint": "EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v",
    "amount": "1000000000"
  }'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  MCP Integration: Agents That Think and Spend
&lt;/h3&gt;

&lt;p&gt;If you're building on the Model Context Protocol — connecting Claude, GPT-4, or another LLM to tools via MCP — WAIaaS ships 45 MCP tools covering wallet operations, transactions, DeFi positions, NFTs, and x402 payments. Setup is one command:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas mcp setup &lt;span class="nt"&gt;--all&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After that, the AI model can check balances, execute swaps, monitor incoming transactions, and pay for API calls as naturally as it calls any other tool. The MCP layer doesn't bypass the policy engine — every tool call still runs through the same 7-stage pipeline. The agent gets capability; you keep control.&lt;/p&gt;

&lt;h2&gt;
  
  
  Getting It Running
&lt;/h2&gt;

&lt;p&gt;The fastest path from zero to a working agent wallet:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 1: Deploy with Docker&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git clone https://github.com/minhoyoo-iotrust/WAIaaS.git
&lt;span class="nb"&gt;cd &lt;/span&gt;WAIaaS
docker compose up &lt;span class="nt"&gt;-d&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The Docker image is &lt;code&gt;ghcr.io/minhoyoo-iotrust/waiaas:latest&lt;/code&gt;, binding to &lt;code&gt;127.0.0.1:3100&lt;/code&gt; by default. For production, use the secrets overlay (&lt;code&gt;docker-compose.secrets.yml&lt;/code&gt;) to inject credentials via Docker Secrets rather than environment variables.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 2: Create a wallet and session&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Create wallet&lt;/span&gt;
curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/wallets &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"name": "trading-wallet", "chain": "solana", "environment": "mainnet"}'&lt;/span&gt;

&lt;span class="c"&gt;# Create agent session&lt;/span&gt;
curl &lt;span class="nt"&gt;-X&lt;/span&gt; POST http://127.0.0.1:3100/v1/sessions &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"Content-Type: application/json"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-H&lt;/span&gt; &lt;span class="s2"&gt;"X-Master-Password: my-secret-password"&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="s1"&gt;'{"walletId": "&amp;lt;wallet-uuid&amp;gt;"}'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 3: Set spending policies before funding&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Configure at minimum a &lt;code&gt;SPENDING_LIMIT&lt;/code&gt; and &lt;code&gt;ALLOWED_TOKENS&lt;/code&gt; policy before you put real funds in. Default-deny means nothing moves without explicit permission.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 4: Wire the session token into your agent&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;WAIaaSClient&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@waiaas/sdk&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;WAIaaSClient&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="na"&gt;baseUrl&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;WAIAAS_BASE_URL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;sessionToken&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;WAIAAS_SESSION_TOKEN&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;balance&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getBalance&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Or use the CLI shortcut that handles steps 2-4 in one shot:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;waiaas quickset &lt;span class="nt"&gt;--mode&lt;/span&gt; mainnet
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Step 5: Connect the interactive API docs&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;open http://127.0.0.1:3100/reference
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The OpenAPI 3.0 spec is auto-generated from the codebase and served at &lt;code&gt;/doc&lt;/code&gt;. The interactive Scalar UI at &lt;code&gt;/reference&lt;/code&gt; lets you explore all 39 REST API route modules and test calls directly — useful when you're building out agent logic and want to see exactly what each endpoint returns.&lt;/p&gt;

&lt;h2&gt;
  
  
  What This Means for the Agent Economy
&lt;/h2&gt;

&lt;p&gt;The question of how AI agents pay for things isn't theoretical anymore. The x402 protocol gives APIs a standard way to charge programmatic clients. ERC-4337 Account Abstraction makes gasless transactions and smart account logic practical. ERC-8004 provides a framework for onchain agent reputation. The pieces are assembling.&lt;/p&gt;

&lt;p&gt;What's been missing is the infrastructure layer that connects agent logic to these payment primitives with appropriate security controls in between. An agent that can spend without guardrails is a liability. An agent that requires human approval for every transaction isn't autonomous. The right answer is a programmable policy engine that enforces rules at the infrastructure level — so that when the agent acts within its mandate, it acts freely, and when it tries to exceed that mandate, the system stops it.&lt;/p&gt;

&lt;p&gt;That's what WAIaaS is built to provide. Not a vision of future infrastructure, but running code you can deploy today.&lt;/p&gt;

&lt;h2&gt;
  
  
  What's Next
&lt;/h2&gt;

&lt;p&gt;The &lt;a href="https://github.com/minhoyoo-iotrust/WAIaaS" rel="noopener noreferrer"&gt;GitHub repository&lt;/a&gt; has the full source, Docker setup, and SDK documentation. The &lt;a href="https://waiaas.ai" rel="noopener noreferrer"&gt;official site&lt;/a&gt; covers architecture and integration guides. If you're building agents that need economic agency — the ability to pay for APIs, execute trades, manage positions, or participate in on-chain protocols — the financial rails are ready when you are.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>web3</category>
      <category>api</category>
      <category>blockchain</category>
    </item>
  </channel>
</rss>
