Vercel AI SDK Tool Calling Cheat Sheet

Just a guy who loves to write code and watch anime.
Search for a command to run...

Just a guy who loves to write code and watch anime.
No comments yet. Be the first to comment.
Qualities that make outstanding builders.

Bipedal vs quadrupedal: how many legs This is about the number of legs the creature walks on. Bipedal. Two legs. Humans, ostriches, T-rex, kangaroos, most fantasy humanoids. Quadrupedal. Four legs. Do

Intro You hear "lerp" and "smoothstep" everywhere in game dev. They sound like math jargon. They're not. Both are small tools that do the same job: smoothly move from one value to another. The problem

What is Kinematics Kinematics is the math field. It's the study of how things move without worrying about forces (which would be dynamics). FK and IK are the two branches: forward kinematics and inver

Intro Textures are usually the biggest cost in a 3D scene. Memory, bandwidth, and load time all get eaten by them. Resizing them is the obvious lever. There's more. This post is about the less obvious

import { z } from "zod";
import { tool, generateText } from "ai";
// Define a tool
const weatherTool = tool({
description: "Get weather for a location",
parameters: z.object({
location: z.string().describe("City name"),
unit: z.enum(["celsius", "fahrenheit"]).optional(),
}),
execute: async ({ location, unit = "celsius" }) => {
// Implement weather lookup
return { temperature: 22, conditions: "Sunny" };
},
});
// Use the tool
const result = await generateText({
model: yourModel,
tools: { weather: weatherTool },
prompt: "What's the weather in Paris?",
});
// Default -> model chooses whether to use tools
toolChoice: 'auto'
// Force the model to use a tool
toolChoice: 'required'
// Prevent tool usage
toolChoice: 'none'
// Force specific tool
toolChoice: { type: 'tool', toolName: 'weather' }
const { text, steps } = await generateText({
model: yourModel,
tools: { weather: weatherTool },
maxSteps: 3, // Allow up to 3 steps (tool call → result → text)
prompt: "Weather in Paris?",
// Optional callback for each step
onStepFinish({ text, toolCalls, toolResults }) {
console.log(`Step completed with ${toolCalls.length} tool calls`);
},
});
// Access all tool calls/results
const allToolCalls = steps.flatMap((step) => step.toolCalls);
try {
const result = await generateText({
model: yourModel,
tools: { weather: weatherTool },
prompt: "Weather forecast?",
});
} catch (error) {
// Tool doesn't exist
if (NoSuchToolError.isInstance(error)) {
}
// Invalid arguments
if (InvalidToolArgumentsError.isInstance(error)) {
}
// Error during execution
if (ToolExecutionError.isInstance(error)) {
}
}
// With streaming
return result.toDataStreamResponse({
getErrorMessage: (error) => {
if (NoSuchToolError.isInstance(error)) return "Unknown tool requested";
// Handle other error types...
},
});
import { ToolCallUnion, ToolResultUnion } from "ai";
// Create a tool set
const myTools = {
weather: weatherTool,
calculator: calculatorTool,
};
// Type helpers
type MyToolCall = ToolCallUnion<typeof myTools>;
type MyToolResult = ToolResultUnion<typeof myTools>;
// Type-safe function for processing results
function processToolResult(result: MyToolResult) {
if (result.toolName === "weather") {
// TypeScript knows the shape of weather results
return `It's ${result.result.temperature}° and ${result.result.conditions}`;
}
}
const contextTool = tool({
description: "Sample tool with context",
parameters: z.object({ query: z.string() }),
execute: async (args, context) => {
// Tool call ID
const id = context.toolCallId;
// Conversation history
const history = context.messages;
// Handle cancellation
context.abortSignal.addEventListener("abort", () => {
// Clean up resources
});
return { result: "Done" };
},
});
const result = await generateText({
model: yourModel,
tools: myTools,
prompt: "Calculate 5+7",
experimental_repairToolCall: async ({ toolCall, tools, error }) => {
if (error.name === "InvalidToolArgumentsError") {
// Fix invalid arguments and return new tool call
return {
...toolCall,
args: JSON.stringify({ a: 5, b: 7 }),
};
}
return null; // Can't repair
},
});
// Initial conversation
const messages = [{ role: "user", content: "What's the weather?" }];
// Generate with tools
const { response } = await generateText({
model: yourModel,
tools: { weather: weatherTool },
messages,
});
// Update conversation history with all messages (text, tool calls, results)
// needed for memory
messages.push(...response.messages);