TraceGuard
A tool list for this key.
Until the list is locked, a tool call is recorded and not stopped. After it is locked, Contain is the first step in that session. Kill is the next step. Kill ends the hop with HTTP 403 traceguard_killed. The console is where the step is named.
What you configure
The list belongs to the key. Check the tool names it may use, add a name, and lock it. A key can save 25 lists. Applying a saved list locks that list for the next run. The list is set in the console.
Until you lock, every tool is recorded and the call is not stopped. A name that is not on a locked list is marked Direct the first time it appears in the session. Direct does not stop the call, and it does not remove the tool.
What the caller sees
The names are Observe, Direct, Contain, and Kill. The console Response column uses the lowercase word. Observe, Direct, and Contain can continue to the model. Kill returns HTTP 403 traceguard_killed.
Observe. The Response column is observe. The model reply has no tg_action.
Direct. The Response column is direct. The model reply has no tg_action. The call is not stopped.
Contain. The Response column is contain. The named tool is taken off that request, the model is still called, and a non-stream reply carries rea_meta.tg_action set to stripped.
Kill. The Response column is kill. The hop ends with HTTP 403, error traceguard_killed, reason TG_L6_KILL, and rea_meta.tg_action set to killed. The vendor is not called and no forwarded call is used.
The same session_id gets that 403 on later hops. A new session can still be contained. Safe mode, or a mode change back through observe, clears the killed state. With no session id, only that hop is refused. The Kill row is class-only, with billed=false and 0 tokens. A streaming Kill is a JSON 403, not SSE. The same rule applies to /v1/chat/completions, /v1/messages, /v1/responses, and /v1beta.
On a non-stream Contain reply:
"rea_meta": {
"tg_action": "stripped"
}
Contain returns the model’s reply. Kill returns a JSON 403 before any model reply.
If the tool list cannot be removed from that request, the caller gets HTTP 403 and the model is not called. This is the strip-unsupported reply, not the Kill reply. notice_id is empty unless a notice was issued.
{
"error": "traceguard_blocked",
"reason_code": "TG_STRIP_UNSUPPORTED",
"response": "contain",
"notice_id": "",
"message": "Blocked by TraceGuard for this session.",
"rea_meta": {
"tg_action": "refused"
}
}
If enforcement is on and the checker cannot run, the caller gets HTTP 503 and the model is not called. A sidecar that is down:
{
"error": "traceguard_blocked",
"reason_code": "TG_SIDECAR_UNAVAILABLE",
"message": "TraceGuard enforcement is temporarily unavailable; request not processed.",
"rea_meta": {
"tg_action": "blocked_unavailable"
}
}
An engine that cannot decide:
{
"error": "traceguard_blocked",
"reason_code": "TG_ENGINE_UNAVAILABLE",
"message": "TraceGuard enforcement is temporarily unavailable; request not processed.",
"rea_meta": {
"tg_action": "blocked_engine"
}
}
Contain, then Kill
These are steps in one session. They are not two names for the same removal.
Contain is the first step. The same tool is tried again: that one tool is blocked for the rest of the session. The call tries to leave the sandbox the first time: tools, network, and the sandbox are frozen for the session. The call uses an egress path it was not given: that egress class is blocked. The model is still called. The hop stays up.
Kill is the next step. The session tries to leave the sandbox a second time, or a secret-shaped call arrives after the session was already contained. The session's tools, egress, and sandbox are wiped, not merely frozen. Kill ends the hop with HTTP 403 traceguard_killed. The vendor is not called.
A first use of a tool that is not on the locked list is neither. It is Direct. The call is not stopped.
What the receipt keeps
The receipt stores the tool names, the class, the signal, and the response label. It can also record hop status, timings, the model, token counts, and the structural hash. It does not store the message or the tool arguments.
A secret marker on a declared path is a PreFlight check. The Firecracker probe is LoopGuard. Both are on Architecture.
Questions
Does the user see an error when TraceGuard acts?
Contain removes tools and the model still answers. A non-stream Contain reply carries rea_meta.tg_action set to stripped. Kill ends the hop with HTTP 403 traceguard_killed, reason TG_L6_KILL, and rea_meta.tg_action set to killed. The model is not called. The console names the step.
What is the difference between Contain and Kill?
Contain is first. A repeated tool is blocked for that session. The first attempt to leave the sandbox freezes tools, network, and the sandbox. An egress path the key was not given is blocked. Kill is later in the same session. A second attempt to leave the sandbox, or a secret-shaped call after the session was already contained, wipes the session's tools, egress, and sandbox. Contain still calls the model. Kill returns HTTP 403 traceguard_killed and ends the hop.
What is Direct?
The first time a tool is not on the locked list, the receipt says Direct. The call is not stopped and the tool is not removed. The same tool again, in that session, is Contain.
What does the console show that the chat does not?
The step, the tool name, the class, and the signal. Not the prompt, not the completion, and not the arguments. A key can keep 25 lists. Applying one locks it.
Does Contain or Kill count as a forwarded call?
Contain does: the model is still called, the vendor can bill the tokens, and REA counts a forwarded call. Kill does not: the vendor is not called. PreFlight refusals, LoopGuard stops, and TraceGuard HTTP 403 or 503 replies are not forwarded calls.
When does the caller get an HTTP error?
When the tools cannot be removed from that request: HTTP 403, traceguard_blocked, reason TG_STRIP_UNSUPPORTED, and rea_meta.tg_action set to refused. When enforcement is on and the checker cannot run: HTTP 503, reason TG_SIDECAR_UNAVAILABLE or TG_ENGINE_UNAVAILABLE. Kill returns HTTP 403, traceguard_killed, reason TG_L6_KILL, and rea_meta.tg_action set to killed. Contain still calls the model; a non-stream reply sets rea_meta.tg_action to stripped.