Event schema for the monitor
The events a running Guard publishes on its local API, for the monitor page, Telegram alerts and your own tools.
Guard’s own address, local only (127.0.0.1:8547 by default), over HTTP:
GET /guard/events?since=N: the events after sequence numberN, oldest first (the last 1,000 are kept in memory). Poll it; pass the lastseqyou saw.GET /guard/decision?nonce=N: Guard’s decision on one request, by the nonce the bot signed it with, and what was sent for it. Read from the journal on disk, so it reaches back to Guard’s first day.GET /guard/status: the state now (mode, kill switch, risk state, alerts, rules).
Read-only: nothing sent to them changes Guard. The one write path is the kill switch (POST /guard/kill, signed with a client key): it can only pull, never release.
Envelope
Section titled “Envelope”Every event has:
| Field | Type | Meaning |
|---|---|---|
seq | integer | 1, 2, 3, … over the journal’s life; a gap means you missed events |
at_ms | integer | UTC epoch milliseconds |
kind | string | one of the kinds below |
The schema is version 1 (the started event and the status carry schema: 1). Fields may be added within a version, never removed or changed in meaning. Money is a decimal string, never a JSON number: "0.03144", not 0.03144.
started
Section titled “started”Guard started: schema, version, mode (paper, testnet, mainnet), account, rules (the zr1_ code), clients (the client addresses).
decision
Section titled “decision”One per request to /exchange (HTTP or WebSocket), also when it was refused before it could be judged.
{"seq":42,"at_ms":1791000000000,"kind":"decision","via":"http", "client":"0x14791697260e4c9a71f18484c9f997b308e59325","signed_as":"testnet","nonce":1791000000000, "action":"order","verdict":"resize","code":"resized", "text":"a loss at the stop within 2% of equity and open risk within 6%", "changes":["limit price 3150 pulled in to 3015, 0.5% from the mid 3000", "size 10 cut to 2.5537 ETH for a loss at the stop within 2% of equity and open risk within 6%", "a stop loss at 2940 attached (2% from the price)"], "request":{"type":"order","orders":[…],"grouping":"na"}, "pre":[{"type":"updateLeverage","asset":1,"isCross":false,"leverage":4}], "forward":{"type":"order","orders":[…],"grouping":"normalTpsl"}, "post":[]}verdict:allow,resize(something changed: seechanges) orveto.code: Veto and reason codes.client,signed_as,nonceare null for a request whose signature did not check out.pre,forward,post: what Guard sends, or would send in paper mode: the leverage first, the action, then cancelling Guard’s own stop once a tighter one of the bot’s rests.
What went to Hyperliquid and what came back (never in paper mode): decision (the decision’s seq), nonce (Guard’s own), ok, reply (the venue’s answer).
Whenever the risk engine’s state changes: state (active, or halted_for_day / stopped with their details), equity, open_positions, discrepancies, journal_error.
flatten
Section titled “flatten”A daily loss stop, drawdown halt or the kill switch closed everything: reason, actions (the cancels and closes), problems (what could not be priced), sent (false in paper mode).
protect
Section titled “protect”Positions without a market stop covering them in full: Guard placed its own stop (actions), closed a position whose stop the venue refused, or in paper mode would have. coins, actions, problems, sent.
The kill switch latched: reason (from zunder-guard kill, the kill file, or POST /guard/kill with the client that pulled it).
text: something went wrong outside a request (reading the account, a refused close). Never contains a key; addresses only.
stopped
Section titled “stopped”Guard stopped: reason (a signal).
Example: a day in events
Section titled “Example: a day in events”seq 41 started paper, rules zr1_…seq 42 decision order → resize (size 10 cut to 2.5537 ETH, stop 2940 attached)seq 43 sent ok, filled 2.5537 @ 3015seq 44 decision order → veto [market_not_allowed]seq 45 decision modify → veto [stop_loosened] (2940 to 2900 would loosen it)seq 46 protect ETH: Guard's stop at 2940 for a position opened in the appseq 47 risk halted_for_day, equity 1880seq 48 flatten daily loss stop: 1 cancel, 1 closeThis page as plain Markdown, for people and LLMs: /docs/reference/events.md