Each adapter also gives a model helper that is the gateway with the run token:
openai_agents.model(inv), agno.model(inv) and agentosModel(inv) (all take a role, "main" by default).
Examples
- OpenAI Agents SDK
- LangGraph
- Agno
- Vercel AI SDK
- Mastra
How checkpoints and results work
- A paused framework’s state is kept in run state under
agentos.<adapter>.<name>(keys startingagentos.belong to the SDKs). Passname=/{name}to give each framework call of one handler its own key; the default isdefault. - A checkpoint belongs to the hold it asked and is used only on that hold’s resume. One larger than 1 MiB is refused before asking (
too_large). An OpenAI AgentsRunStateor an AI SDK conversation grows with the run’s transcript, so watch long runs. - Once the framework call finishes, its result (JSON) replaces the checkpoint. A later invocation of the same run gets that result back instead of running the framework again, which would repeat its side effects. In Python it is a
Stored(a dict whose keys are also attributes, withstoredtrue); in TypeScript an object withstored: true. Passfresh=True/{fresh: true}to run it anew. - In Python a result over 1 MiB isn’t kept, but the call is still remembered as finished: later invocations get an empty
Storedwithdroppedtrue, never a second run.
Memory tools
agentos.adapters.openai_agents.memory_tools(inv, paths=[...]) gives the agent’s memory tools as OpenAI Agents SDK FunctionTools, and memoryTools(inv, {paths}) from @agentos/sdk/ai-sdk as Vercel AI SDK tools.
Frameworks without an adapter
- CrewAI Flows: use the core SDK. Ask in a flow step and keep the flow’s state in run state.
- CrewAI Crews (
Crew.kickoff) can’t pause without running again from the start. Move the approval into a Flow step. - Plain tool loops, Upsonic and anything else: use the core SDK’s
ask()and state directly.
When a guardrail blocks a model call
A guardrail block is an HTTP 400 from the gateway withcode: content_filter and an agentos_guardrail object. How frameworks surface it with their default settings:
Through the SDKs’ own
inv.llm.chat() and stream(), a block raises GuardrailBlocked; uncaught, the invocation answers failed with blocked_by_guardrail.
