Quickstart
In five minutes you will have an agent that calls a Python function as a tool, remembers a conversation, and leaves a record of every step it took — which you will read back.About five minutes, and a fraction of a cent of model usage. Every output on this
page is what the code printed when it was run; the model’s wording will differ on
your run.
1
Install
python --version. On 3.10 or
3.11, the install stops and says so.The core install is light. Databases, sandboxes, the server and the rest come
as extras, when you need them.2
Set your model key
3
Your first agent
Save this as
hello_agent.py and run python hello_agent.py:result is a dictionary; which keys it has depends on how the run ended:The run’s cost in dollars is in its trajectory, next step:
trajectory["totals"]["estimated_cost_usd"].4
Give it a tool
A tool is a Python function with type hints and a docstring. The model
decides when to call it.The last lines are the run’s trajectory: every step, the tool the model
called, the arguments it chose, how the call ended, and what the run cost.
Every run keeps one. Everything in a trajectory
— including exactly what the model was sent and what each tool returned —
is on the Observability page.
5
Remember a conversation
Runs with the same History lives in memory by default. To keep it across restarts, use Redis,
Postgres or MongoDB (Memory).
session_id share their history. A different one starts
fresh.What you just used
Without asking for any of it, that agent ran the runtime’s loop — the model calling tools, independent calls in one batch, results as structured observations — with session memory, a workspace for files, the prompt-injection guardrail, and a full record of the run. You will find aworkspace/ folder where you ran the script: the agent’s files
(files/), large tool results saved for the agent to read back (artifacts/),
and the record of every run (telemetry/). To keep it elsewhere, set
agent_config={"workspace_config": {"workspace_dir": "/path/to/workspace"}}. The agent is also
governed already: the default policy (permissive-dev) allowed its tool, and
would have refused raw secrets, shell commands on the host, unrestricted
network and package installs (the defaults).
Everything else you switch on when you want it: a stricter policy, a sandbox
for commands, budgets, background runs, a server.
When things go wrong
These are the messages you will actually see.ValueError: LLM_API_KEY not found in environment variables
ValueError: LLM_API_KEY not found in environment variables
The key is not set in the shell that runs the script:The runtime does not read
.env files itself. If your key is in one, load it
at the top of your script:ValueError: model_config.provider is required
ValueError: model_config.provider is required
Name both the provider and the model:
The model call was refused: the provider does not serve the model … to this account
The model call was refused: the provider does not serve the model … to this account
The run ends with Check the spelling against your provider’s model list, and that
status "error" and this message when the model name is
wrong, or your account cannot use that model:model_config["provider"] is the provider that serves it.Next
Take the tour
Fifteen minutes: a policy that asks a person, a sandbox for commands, a
budget, and the evidence of it all.
Tools and MCP
Your functions, MCP servers, and code mode.
Every run is evidence
Trajectories, outcomes, training records, exporters.
Serve it
REST and SSE for runs, approvals and traces.