TypeScript
Better Agent infers types from your agents, schemas, tools, memory, and app registration. You do not need generated client types.
Agent names
Registered agent names become valid handles on the app.
const support = app.agent("support");
// TypeScript error when no registered agent has this name.
const billing = app.agent("billing");The same name checking works in the browser when the client uses the server app type.
Context
contextSchema defines the context shape for runs, streams, instructions,
tools, and hooks.
const analyst = defineAgent({
name: "analyst",
model: openai("gpt-5.5"),
contextSchema: z.object({
userId: z.string(),
plan: z.enum(["free", "pro", "enterprise"]),
}),
instruction: (context) => `The user is on ${context.plan}.`,
});
await app.agent("analyst").run({
messages,
context: {
userId: "usr_123",
plan: "pro",
},
});See Agent for agent configuration.
Tools
Tool schemas infer the input type passed to server tools.
const searchDocs = defineTool({
name: "search_docs",
target: "server",
description: "Search internal docs.",
inputSchema: z.object({
query: z.string(),
limit: z.number().default(5),
}),
execute: async (input) => {
return docs.search(input.query, { limit: input.limit });
},
});Client tool handlers infer the input for each matching client tool.
const agent = useAgent(client.agent("support"), {
toolHandlers: {
confirm_address: async (input) => {
return openAddressDialog(input.address);
},
},
});See Tools for server tools, client tools, approvals, MCP tools, and provider tools.
Structured output
output.schema infers result.structured.
const extractor = defineAgent({
name: "extractor",
model: openai("gpt-5.5"),
output: {
schema: z.object({
title: z.string(),
priority: z.enum(["low", "medium", "high"]),
}),
},
});
const result = await app.agent("extractor").run({ messages });
result.structured.priority;See Structured Output for schema formats and per-run output.
Client type sharing
Export your server app and pass its type to the client.
// server.ts
export const app = betterAgent({
agents: [supportAgent, analyst],
});
export default app;// client.ts
import { createClient } from "@better-agent/client";
import type app from "@/better-agent/server";
export const client = createClient<typeof app>({
baseURL: "/api/agents",
});The client now knows agent names, context, memory helpers, and client tool handlers.
See Client for browser usage.
Schema types
Schemas can be Zod, any Standard Schema, or plain JSON Schema.
const schema = {
type: "object",
properties: {
name: { type: "string" },
tags: { type: "array", items: { type: "string" } },
},
required: ["name"],
additionalProperties: false,
} as const;Use as const with plain JSON Schema when you want narrower inferred types.
Helper types
| Type | Package | Use it for |
|---|---|---|
AgentContextOf | @better-agent/core | Get the context type from an agent. |
InferSchemaInput | @better-agent/core | Infer input from a schema. |
InferSchemaOutput | @better-agent/core | Infer output from a schema. |
BetterAgentApp | @better-agent/core | Type an app when exporting helpers. |
BetterAgentErrorCode | @better-agent/core | Type error-code handling. |
AgentNameOf | @better-agent/client | Get valid agent names from an app type. |
AgentContextFor | @better-agent/client | Get client context for one agent. |
ToolHandlersFor | @better-agent/client | Type client tool handlers. |