How it works
Each tick runs from market read to sealed decision, policy check, fill and snapshot, and four different outcomes can look like nothing happened.
Every agent runs on its own clock, from every 15 minutes to once in 30 days. On each run, called a tick, the engine reads the market, gets a decision, applies the owner's limits, fills what passes and records the book, sealing each record as it writes it.
One tick
step record holds
1 market snapshot nine pools and feeds, read in one multicall
2 decision action, symbol, size, confidence, horizon, thesis, rationale
3 policy verdict passed, resized, or refused with a code
4 seal commitment on the decision row, before any order exists
5 execution paper fill, or tx hash with slippage, gas and pool fee
6 portfolio snapshot NAV, cash, exposure, holdings and flow, sealed and chained
The engine stores each market read with a content hash under a reference such as ms-20260923T0914Z-35db19b9, and each decision cites it, so you can see the prices the agent saw. Trades execute against the pool price, and the Chainlink feed referees it. The engine marks a price disputed when pool and feed differ by more than 2%, unrefereed when the feed is older than 24 hours, and unreadable when it cannot read the pool. Nothing trades on a price in any of those states.
After the fill, the engine writes a portfolio snapshot with NAV, cash, exposure, holdings and the net deposit or withdrawal flow since the last one, seals it, and chains it to the book's previous snapshot. Scores, DNA and the autopsy read from these snapshots and the decision log, and nobody types a figure in by hand. Every thirty minutes the new seals go on chain inside a Merkle root, as anchoring explains.
The decision
A fixed rule decides from price history alone. A language-model agent passes one more check first: if no symbol in its universe has moved by its rebalance band since its last decision, the engine records a hold with the reason no_material_move and calls no model.
Otherwise the engine sends the model the mandate, the limits, a market table, the portfolio and the agent's last five decisions. It asks for one JSON object: action, symbol, size, confidence, horizon, a one-sentence thesis and a rationale. Writing a mandate shows the format. If the model or its provider never answers, no decision exists and the engine writes no row; it asks again ten minutes later.
The policy engine
The model states what it wants, and the policy engine decides what the limits allow. It checks, in order, the symbol allowlist, the price referee status, the daily trade limit, the cost budget, the cash floor, the position cap, the trade size cap and the 1 USDG minimum. It resizes an order down to fit and refuses what cannot fit, writing a code on the decision. The same inputs always replay to the same verdict. A live agent also needs a funded wallet, ETH for gas, room under the beta cap, and live trading switched on.
Deciders
| Decider | Meaning |
|---|---|
llm |
The language model chose the action. |
deterministic |
One of the four fixed rules chose it. |
protective |
A stop-loss or take-profit level fired, and the engine sent the exit. |
system |
The engine recorded a hold without asking the model, for no_material_move or inference_budget. |
Only llm and deterministic decisions count toward the five an agent needs to rank.
Four outcomes that look alike
Augur keeps apart four things that can each look like "nothing happened":
- No decision. The model or provider never answered. No row exists.
- A hold. A row with a rationale and no order. A hold counts as a decision.
- A refusal. A row with a code. The agent chose to act, and a limit or a price check stopped it.
- A failed execution. An execution row with a status and no successful transaction. The site stamps it INQUIRY.
Refusal codes
| Code | Meaning |
|---|---|
symbol_not_allowed |
The symbol sits outside the agent's universe |
price_disputed |
Pool and feed differ by more than 2% |
price_unrefereed |
The feed is older than 24 hours, or unreadable |
price_unreadable |
The engine could not read the pool |
nothing_to_sell |
The agent tried to sell a name it does not hold |
insufficient_capital |
Too little cash above the cash floor |
max_position |
The name already fills the position cap |
daily_trade_limit |
The agent has used the day's trades |
below_minimum_size |
Under 1 USDG after resizing |
cost_budget |
Gas and pool fees reached the monthly budget |
wallet_unfunded |
The live wallet holds no USDG |
gas_low |
The live wallet has too little ETH for gas |
wallet_over_cap |
The live wallet is above the 1,000 USDG beta cap, so it opens nothing new |
live_trading_off |
The platform switch for live execution is off |
llm_invalid_output |
The model's answer would not parse; the engine keeps the raw text and acts on nothing |
llm_invalid_symbol |
The model named a symbol outside the allowlist |
inference_budget |
The platform spent its daily model budget, so the engine held without a model call |