Skip to content
Comparison

TanStack AI vs pi

pi is built for an agent that runs in one process: a terminal coding agent, a bot, or a script. TanStack AI does that too, and it also lets you split the agent across a client and a server. Pick pi if you want pi's coding agent CLI or its subscription logins. Pick TanStack AI for everything else, and for any app with a browser in it.

Both are open-source TypeScript toolkits under the MIT license. Both stream model output, call tools, run an agent loop, and talk to many providers. The difference is where the agent can run.

Where the agent runs

piTanStack AI
In one processYes. agentLoop() runs next to the code that reads its events (agent.subscribe)Yes. chat() returns an async stream you read in the same process. A harness keeps a session open across turns
In a terminalpi-tui, or pi-coding-agentrunCli from @tanstack/ai-harness-cli: line mode, print mode for scripts and CI, NDJSON, and ACP for editors
Split across client and serverNot built in. pi-protocol and RPC mode can send events to another process. streamProxy keeps the loop in the browser and sends only the model call through your serverBuilt in. The loop and the server tools run on the server. The browser gets AG-UI events over HTTP and renders them with useChat
With a browser UIYour own codeuseChat for React, Solid, Vue, Svelte, Preact, Angular and more, with approvals, reconnects and saved history

So pi gives you an agent to embed in one process. TanStack AI gives you the same agent, plus a client and a server that talk to each other when you need them.

Pick TanStack AI when

  • You build a terminal agent, a bot, or a script. chat() runs the loop in your process. A harness keeps the conversation open, queues and steers messages, and runs typed agents from code. See Run a harness in the terminal.
  • You build a web app. useChat renders the run on the client, and the run survives a slow network or a reload. See UI and Resumable Streams.
  • Your tools must run on the server. Database calls, secrets and paid APIs stay on the server. The browser never sees them.
  • You want to define a tool once. One schema gives the input and output types on the server and on the client. Add .server() or .client() to run it on either side. See Tools.
  • You want people to approve tool calls. needsApproval pauses the run, and the user answers in the terminal or in the browser. See Tool approval.

TanStack AI also has these, each in its own package:

  • Coding-agent harnesses. Run Claude Code, Codex, OpenCode, Grok Build, or any ACP agent as a chat backend, in a local process or a sandbox. The harness is experimental. See Coding agents.
  • Subagents. A tool can run a child agent, and the client shows its run as a card. See Subagents.
  • Persistence. Writes to your database, in your schema. See Persistence.
  • Media beyond chat. Images, video, speech, transcription, music and realtime voice use the same adapters and persistence as chat. See Generations.

Pick pi when

  • You want pi's coding agent as the product. pi-coding-agent is a finished terminal agent that reads, edits and runs code in your repo. It saves sessions and loads extensions and skills.
  • You sign in with a model subscription. pi has OAuth logins for Claude Pro and Max, ChatGPT, GitHub Copilot and OpenRouter.
  • The loop must stay in the browser. streamProxy keeps the loop and the tools on the user's machine and sends only the model call through your server.

How the core APIs map

piTanStack AI
@earendil-works/pi-ai@tanstack/ai and one adapter package per provider
createModels(), setProvider(anthropicProvider()), models.getModel('anthropic', id)anthropicText(id) from @tanstack/ai-anthropic
models.streamSimple(model, context)chat({ adapter, messages })
models.completeSimple(model, context)chat({ adapter, messages, stream: false })
systemPrompt in the contextsystemPrompts: ['...']
AgentTool with TypeBox parameters and executetoolDefinition({ inputSchema }).server(fn)
agentLoop() or the Agent classchat({ tools }), which runs the loop
beforeToolCall / afterToolCallmiddleware: [...] with tool call hooks
agent.followUp(message)The message queue of useChat
agent.subscribe() and AgentEventThe AG-UI events of chat(), read by useChat on the client
streamProxy() in the browsertoServerSentEventsResponse on the server, useChat on the client
@earendil-works/pi-mcp@tanstack/ai-mcp. See MCP.
@earendil-works/pi-codemode@tanstack/ai-code-mode. See Code Mode.

Feature comparison

Versions: pi 1.4 and TanStack AI 1.0.

FeaturepiTanStack AI
LicenseMITMIT
Main useAn agent in one process: coding agent CLI, and the libraries under itAgents in one process, in a terminal, or split across client and server
Wire protocolIn-process AgentEvent objects. Remote sessions over CBOR (pi-protocol)Native AG-UI, in both directions
ProvidersAbout 35 in pi-ai, plus any OpenAI-compatible APIOpenAI, Anthropic, Gemini, Vertex, Bedrock, Grok, Groq, Mistral, OpenRouter, and more. Any OpenAI-compatible endpoint
Subscription loginsOAuth for Claude Pro and Max, ChatGPT, GitHub Copilot, OpenRouter (Node only)API keys
UIpi-tui for the terminalTerminal (runCli), plus React, Solid, Vue, Svelte, Preact, Angular, Octane, Remix, React Native
ToolsAgentTool with a TypeBox schema, run in the agentOne toolDefinition(), with .server() and .client()
Tool approvalbeforeToolCall can block a callPer-tool needsApproval, with batched approvals and interrupts
Steering and follow-upBuilt-in queues on the AgentA message queue in useChat. The harness also steers a running turn (experimental)
SubagentsTask-owned child conversations in pi-durable (experimental)Built in, with a card per child run
Structured outputConstrained sampling for tool argumentsTyped message part, streamed with tools and kept in the history
Token usageUsage and cost on each assistant messageUsage on each model call, and cost when the provider reports it
PersistenceJSONL session files with branching. pi-durable is experimentalwithPersistence middleware, server or browser stores
Resumable streamspi-durable resumes a turn after a crash (experimental)Built in. useChat reconnects by itself
MCP clientpi-mcp: stdio and Streamable HTTP@tanstack/ai-mcp: multi-server pools, generated types, lazy tools, managed lifecycle
Code Modepi-codemode: QuickJS on Node, Bun and Cloudflare6 isolate drivers: Node, QuickJS WASM, QuickJS Bun, Cloudflare, Daytona, E2B
Coding agentspi-coding-agent, a CLI with extensions, skills and themesClaude Code, Codex, OpenCode, Grok Build, and any ACP agent, on a local process or a sandbox
ImageImage generation through OpenRouterStable, typed per model
Video, speech, musicNot built inStable
Realtime voiceNot built inStable: OpenAI, Gemini, Grok, ElevenLabs

To try TanStack AI, start with the Quick Start.