{{E0.teams.0.name}} if it knows linear__list_teams returns {teams: [{name, …}]}. MCP tools rarely declare output schemas — so graph learns them empirically.
How it works
After every successful tool call — from chat,ask, a plan step, or tools test — graph infers a compact JSON Schema and a truncated example from the actual result and stores them keyed by tool name, with a seen-count.
At planning time (plan_and_execute, and every replan attempt), each tool’s entry in the planner’s context includes the best available shape, in priority order:
- a declared output schema (from the MCP server, a
tool_overridesentry, or a user tool’soutput_schema) - the observed shape from the cache, marked as empirical
What this means in practice
- Everyday usage trains the planner. After you’ve used
linear__list_issuesonce,plan_and_executewrites correct field references against it forever after. - Cold caches degrade, not break. With no shape, the planner is instructed to use whole-result references (
{{E0}}) or stop and continue planning after real results exist; a wrong deep path fails with a digest of the keys that do exist, and one replan fixes it. - You can inspect it. It’s just files:
Backend caveat
The cache lives in the storage backend. With the defaultfile backend it accumulates across runs; with GRAPH_STORAGE=memory (the ephemeral backend for CI) each process starts cold and learns only within its own run — one reason a future centralized backend is attractive for CI fleets. See Storage.