Console surfaces
The live monitor and a finished run’s gg tab are one view over one stream: live, then rebuilt from the recording, laid out identically down to the order of the cards. Five surfaces read a run.
Dashboard
Section titled “Dashboard”The whole-run read-out: status, the token and cost tally with its caching (cached against uncached input) and reasoning (reasoning against non-reasoning output) splits shown as rings, an overview of the agents that ran, and the configuration the run’s independent variable is.
Beside the status sit the turns the session has spent across every agent and its tokens per second, which is everything the run generated over the time it spent inside its model calls, averaged across every model it used. A multi-model run’s card names each model’s own rate on hover. The two counts say how much a run has done and spent; the rate says whether the wall-clock behind them went into generating or into waiting.
Under the turn count sits the errors row, which shares its denominator: one tile for how many of those turns failed and what fraction that is, one for the longest failing streak any one agent reached, and one ranking the types they failed with.
The clocks take a row of four tiles. Runtime is the wall clock, measured over the run’s execution, and it is what the ceiling on the time limit tile beside it is measured against. Active is every agent’s own time summed, and the gap between it and the wall clock is the parallelism the configuration bought. Active means working: an agent blocked waiting on its subagents or on a board issue has freed its running slot, so its wait is subtracted from that sum and reported on the Waiting tile instead, since folded in a delegating run whose parents mostly wait would report a figure several times the work it did. The count under those two tiles is how many agents are in that state at this moment rather than how many contributed to the total.
Each agent in the overview reads as a row carrying its own turn count, the peak
its context window reached, its share of the run’s tokens, and what it called,
chipped in that agent’s own vocabulary. A tool-calling agent’s chips name its
tools; a code-shaped one’s name the API
functions its programs wrote (gg.files.readFile). Each row links into that
agent’s files in the Instances explorer.
The cost read-out leads the row it shares with the token tally and is the taller tile, carrying the run’s whole account of its spend with the configuration slotted in under the tokens beside it. That account is the total; the split per class (input, cached input, reasoning, output), pricing each token against the model that produced it rather than at one blanket rate; the input-against-output ring; and where the money went, as bars per profile, each naming the model that profile was bound to, and bars per model, the same spend folded onto the models that did it. Both are always shown. A run that binds one model per profile lists the same rows twice, which is a fact about that configuration.
A run binds one model per agent profile, so every usage
event names the profile id and model that spent
it and every split above is derived from the delta stream, from the run’s first
turn. Each delta also names the cost figure its
turn fed, work or total, so both the total and the work cost are summed off
the same stream. The slot_usage rollups, one per (profile, model) the run
touched and all of them emitted once the run’s last agent has joined, carry the
same figures for the durable record; a consumer sums the deltas, never both.
Agents
Section titled “Agents”The run read per configured agent rather than per running one. A configuration declares agent profiles and the run makes as many instances of each as the work calls for, so a profile that spawns twelve implementers is one arm of the experiment. This panel groups the instances by the id of the profile they ran under and sums them, under the name that profile carries.
It is one collapsible row per agent, all closed to begin with. Closed, a row is the comparison line: instances, turns, tokens, cost, and peak context, each with its share of the run. The panel is therefore a short list to read down a column of. A profile the configuration declares but the run never instantiated still gets a row, because “the reviewer never ran” is a result.
Clicking a row opens that agent’s detail, and only that agent’s: how many instances ran and how they ended, what a typical one cost, how full a typical window got against the worst one, how often they compacted, the same Tokens and Cost widgets the Dashboard uses, what they called between them, and the context spend.
The detail leads with the profile’s instances, one chip each, opening that instance in the Instances explorer. Every figure under them is a sum over them. What the profile asked for (the capability chips) and what gg resolved out of them annotate those instances, in that order. The offered set is headed Tools or APIs by the mode the instances reported answering in.
That offered set is a union across the profile’s instances rather than a sum. An
offered set is not a quantity, and instances of one profile legitimately differ,
since where an instance stands in its machine gates what it may
call. An entry only some of them were offered carries the fraction that says so.
An entry the profile never called reads a real 0× and is muted rather than
removed, which is the contrast the section exists for.
The observed-usage section at the foot of the detail is the other half of that contrast and is a separate read-out. It is headed by the surface its instances called on: API calls for a code-shaped profile, Tool calls for a tool-calling one, the same naming an instance’s Overview gives its Failed API calls and Failed tool calls ranking, and it itemizes the profile in that surface’s own vocabulary.
Under the offered set sits the one read-out on the panel that is not a sum: what this profile’s instances hold. Module state does not fold, since twelve instances may be reading one store or twelve, and which of those it is is the configuration under test. Each module kind therefore states its distribution. The one shape whose contents belong to the agent, a single store every instance binds at once, shows them inline.
Instances
Section titled “Instances”Everything else, one running agent at a time. The rich views are per agent: the prompt the agent was given, activity, the context-window breakdown, the message log, and the metric graphs. Which agent’s window filled, and which agent’s requests these were, are the questions they answer.
The explorer lays the run out as a filesystem. Every agent is a folder, the
things you can monitor about it are its files, and every agent an agent spawned
is a folder under a subagents folder, so the delegation tree
is the directory tree, rooted at the main agent. What the agent holds lives one
level in, under a modules folder of its own: a file per module,
each stating which store it is, who else is holding it, and what it costs this
window, so an agent’s own files stay facts about the agent and a store four
agents share is legible as one store from any of them.
An agent that succeeded another through an exec or an
FSM transition hangs directly off its predecessor’s folder, tagged
with where it came from (⇢ verify, ⇢ exec), so a chain of incarnations reads
as one lineage. A fork is a genuine child and goes under
subagents, tagged ⑂ fork. Either way the arriving agent’s Overview states
what it inherited: the state it entered, and which modules were
carried, copied, linked, dropped and started fresh. Both halves of the handoff
appear in the activity feed on the streams they landed on.
Each agent folder leads with its lifecycle dot (running, waiting, done, failed)
in place of a folder glyph and carries the profile it runs under on the row’s
trailing edge. Only the main agent is named root. An agent the board
dispatched for an issue is a top-level folder beside
it and reads by its own issue-derived name (AUTH-1.0i, its reviewers
AUTH-1.0i.0r) everywhere it is named: the tree, its Overview, and the
Dashboard’s agent overview.
Which files an agent has
Section titled “Which files an agent has”A file is offered when the run’s configuration justifies it rather than when data happens to arrive. A capability the run has always has its file, showing its own “nothing yet” state until the first event streams; a capability the run lacks has none; Context is always offered, because every run has a window that fills. Overview, Prompt and activity are unconditional, because every agent was given something. A subagent was given the brief its parent handed it, which rides on the always-present spawn event; the main agent was given its opening prompt.
Directly after Prompt sits the one file gated on the instance rather than on the
configuration: what that instance was
offered to call. It is named tools for an agent
that answers in tool calls and apis for a
code-shaped one, and it is offered exactly
when that instance reported a surface. An instance read before its surface event
arrives has no such file, since a file showing an empty toolset would assert the
very thing it exists to distinguish.
Every row reads count first (12× read_file), so the figures line up in a fixed
leading column that can be read straight down the list. A tool the instance never
reached for reads a real 0× and is muted rather than dropped, which is the
point of the file; the row’s hover text says the same zero in the same words
(“offered, 0 calls”) and spends the rest of its length saying that this is a
finding about something the agent held. The list is the resolved surface gg
reported on the instance’s own event rather than a re-reading of the
configuration, so what the file shows is what the model was given.
A code agent reads the same thing through its modules: one card per module,
carrying the one-line description its own system prompt introduced the module by,
over the functions this instance bound, each carrying its own count. No gg tool
name appears on that file. gg records a model-facing call under the operation it
resolved to, so a view call, a documentation lookup, an ending call and a
program-library call are counted exactly as a file read
is, and two functions over one implementation (gg.files.readFile and
gg.views.openFile both perform one read) are two
figures rather than one shared between them. The file’s own heading names the
documentation-view flags this instance ran under, because the tokens those flags
cost are this agent’s own. Every row carries a figure, so a 0× is a bound function the
model did not use rather than a gap in the record.
The Overview file
Section titled “The Overview file”The Overview carries the agent’s own call breakdown: everything it called, how
many times, and how much each call’s results added to its window. What it was
offered is the file above; the two are named apart because they are the two
halves of one question. Like every read-out of what an agent did, the breakdown
is taken on the surface that agent called on and says which in its caption: Tool
calls for a tool-calling instance, API calls for a code-shaped one. The API view
carries no per-entry token column: a program’s calls return into the program, so
the only tool-role messages a code turn leaves are its submit_program
acknowledgements and there is nothing per-function in the window to attribute.
Beside it sits the agent’s Errors widget: its errored turns against the turns it took, its worst unbroken streak of them, its ranked error types, and the calls it failed, ranked by class. The run-wide figures on the Dashboard are a sum, in which an instance that failed every turn and one that failed none are indistinguishable. The call ranking is captioned Failed API calls for a code-shaped instance and Failed tool calls for a tool-calling one: the first is what the model’s own programs were thrown, including the calls no gg tool ever ran, and the second is what gg dispatched. They are never summed with each other, and never mixed into the turn ranking above them, which counts turns rather than calls.
The Overview also states the agent’s working directory, which is the isolated
worktree checkout its tools are rooted at or the
shared workspace. While the agent is blocked it states what the agent is waiting
on. blocked on its own is indistinguishable from stuck, so the wait names its
condition: the issue it suspended for, or the subagents it is collecting.
The Shell file
Section titled “The Shell file”An agent whose profile enables the shell capability carries a
shell file: every command line gg ran on that agent’s behalf, in order, read
from the shell telemetry events on its own
stream. Each row leads with the command, states the directory it ran in when
that is not the agent’s own workspace root, names the command path that issued
it, and ends with its exit code as the verdict, so the rows worth opening stand
out. An opened row shows the command’s stdout and stderr as the event capped
them, with a note stating how much leading output the cap dropped.
The file lists what ran rather than what the model asked for. A hook’s command
appears tagged hook, since gg ran it without the model asking, and a
responses-as-code program’s
gg.shell.shell(…) calls appear beside the shell tool’s, tagged apart. The
file is offered whenever the profile holds the capability, showing its own
empty state until the first command runs.
Modules
Section titled “Modules”The run read by the state it holds rather than by the agents holding it, sitting between Instances and Project. Module instances are grouped by kind, one row per backing store however many agents hold it, and each kind’s group leads with a whole-run overview of how that capability is being used: how many stores exist, how widely they are shared, what they cost every turn, and how many were never written to.
It exists because the Dashboard, the Agents panel and the Instances explorer are all read per agent, which is the wrong axis for a thing several agents can hold at once. Read per agent, one store shared by four reviewers looks exactly like four stores that happen to agree, which is the difference between “the shared-memory arm worked” and “it fell back to private notebooks”. The surface is offered whenever the run enables a module-backed capability.
Project
Section titled “Project”The run-global project management board. The board is shared run-wide, so it is its own top-level section rather than a file under any one agent.