The problem
AI agents are starting to hold keys. An agent with a hot wallet and a swap router can drain itself in one bad loop, or be steered into a manipulated pool. Aegis puts the guardrails on-chain, where the agent can't talk its way around them.
How it works
One Anchor program with three parts:
- Policy vaults. An agent's funds sit in a vault with a daily spending limit and a
large-transaction threshold. Swaps under the threshold run immediately; above it they become
a
PendingActionthat a human must approve; anything over the daily limit is rejected. - Constant-product AMM. Pools with configurable fees, LP tokens, and a minimum first deposit so the pool can't be initialised at a manipulated ratio.
- Oracle checks. A Pyth reader with a configurable staleness bound, meant to compare the pool price against the market before a swap goes through.
agent ── request_swap(amount) ──► daily window reset? ──► over daily limit → reject
└─► over threshold → PendingAction
└─► otherwise → swap
human ── approve_pending_action ──► swapDesign decisions
- The 24-hour window resets from on-chain time. The vault stores
last_reset_timestampfrom the Clock sysvar, so an agent can't fake the clock. - The threshold must sit below the daily limit, checked at vault creation, so every vault has a path where a human sees a large trade.
- Swaps take
min_amount_out. Slippage protection is enforced in the program, not left to the client.
What could go wrong
The spending policy was the whole point of the project, and it wasn't reachable: the vault instructions weren't exported from the program, swaps were simulated, and pending actions could be any account passed in by the caller.
| Vector | Status |
|---|---|
| Policy not reachable | Fixed: vault instructions are part of the program and move real SOL |
| Pending action overwritten | Fixed: each request is its own account at [action, vault, nonce] |
| Approval paying the wrong address | Fixed: approval pays only the destination recorded in the request, with a test |
| Agent approving itself | Fixed: approval is bound to the owner's key; tested |
| Vault drained below rent | Fixed: payouts stop at the rent-exempt minimum |
| Sandwich and slippage on the AMM | Mitigated: min_amount_out enforced on every swap |
| Oracle not compiled | Open: the Pyth reader still isn't wired in |
Where it stands
A hackathon project, reworked and redeployed to Solana devnet. The vault has 8 tests and a page where you play the agent and the owner. The older AMM pages are hidden: they pointed at pools from the first deployment, which the new program doesn't have.