Server Tools
What are Server Tools?
Server tools are functions that run on your backend that the Built-in Agent can invoke. They're defined using defineTool() with Zod schemas for type-safe parameters.
When should I use this?
- Your agent needs to access databases, APIs, or other backend services
- You want type-safe tool parameters with validation
- The tool logic requires server-side secrets or resources
Defining a tool
const getWeather = defineTool({
name: "getWeather",
description: "Get the current weather for a city",
parameters: z.object({
city: z.string().describe("The city name"),
}),
execute: async ({ city }) => {
// Your implementation here
return { temperature: 72, condition: "sunny", city };
},
});
const builtInAgent = new BuiltInAgent({
model: "openai:gpt-5.4",
tools: [getWeather],
});
Tool response
Tools can return any JSON-serializable value. The agent uses the response to continue the conversation.
Multiple tools
Pass an array of tools — the agent chooses which to call based on the user's request:
const searchDocs = defineTool({
name: "searchDocs",
description: "Search the documentation for relevant articles",
parameters: z.object({
query: z.string().describe("The search query"),
}),
execute: async ({ query }) => {
const results = await search(query);
return { results, count: results.length };
},
});
const createTicket = defineTool({
name: "createTicket",
description: "Create a support ticket",
parameters: z.object({
title: z.string().describe("Ticket title"),
priority: z.enum(["low", "medium", "high"]).describe("Ticket priority"),
description: z.string().describe("Detailed description of the issue"),
}),
execute: async ({ title, priority, description }) => {
const ticket = await db.tickets.create({ title, priority, description });
return { ticketId: ticket.id, status: "created" };
},
});
const builtInAgent = new BuiltInAgent({
model: "openai:gpt-5.4",
tools: [searchDocs, createTicket], // [!code highlight]
});
Complex Zod schemas
Use nested objects, arrays, enums, and optional fields for sophisticated tool parameters:
const bookFlight = defineTool({
name: "bookFlight",
description: "Search for and book flights",
parameters: z.object({
trip: z.object({
origin: z.string().describe("Origin airport code (e.g., SFO)"),
destination: z.string().describe("Destination airport code (e.g., JFK)"),
date: z.string().describe("Departure date in YYYY-MM-DD format"),
}),
passengers: z.array(
z.object({
name: z.string(),
seatPreference: z.enum(["window", "middle", "aisle"]).optional(),
})
).describe("List of passengers"),
class: z.enum(["economy", "business", "first"]).default("economy"),
}),
execute: async ({ trip, passengers, class: seatClass }) => {
const flights = await searchFlights(trip, seatClass);
return { flights, passengerCount: passengers.length };
},
});
Error handling
Throw errors or return error objects from your tool — the agent will see the error and can inform the user or try a different approach:
const getUser = defineTool({
name: "getUser",
description: "Look up a user by email",
parameters: z.object({
email: z.string().email().describe("The user's email address"),
}),
execute: async ({ email }) => {
const user = await db.users.findByEmail(email);
if (!user) {
throw new Error(`No user found with email: ${email}`); // [!code highlight]
}
return { id: user.id, name: user.name, role: user.role };
},
});
Multi-step tool calling
By default, the agent performs a single step. If your agent needs to chain tool calls (e.g., search first, then create a ticket), set maxSteps:
const builtInAgent = new BuiltInAgent({
model: "openai:gpt-5.4",
maxSteps: 5, // [!code highlight]
tools: [searchDocs, createTicket, getUser],
});
With maxSteps: 5, the agent can:
- Call
searchDocsto find relevant info - Process the result
- Call
createTicketwith details from the search - Continue until done (up to 5 iterations)
See Advanced Configuration for more options like toolChoice, temperature, and providerOptions.
If you're using the Custom Agent instead of BuiltInAgent, see the "With Tools" examples for how to wire tools with AI SDK, TanStack AI, or custom backends.