Overview
DurableAgent is a class for building AI agents that maintain state across workflow executions. It wraps AI model providers with durable execution capabilities, ensuring that your AI agents can survive interruptions, handle long-running operations, and automatically recover from failures.
Constructor
options DurableAgentOptions
required
Configuration for the durable agent model string | (() => Promise<LanguageModel>)
required
The AI model to use. Can be:
A string for AI Gateway (e.g., 'anthropic/claude-opus')
A function returning a model instance from a provider
Tools available to the agent. Each tool should have:
description: Human-readable description
inputSchema: Zod schema for validation
execute: Function to run (can be a workflow step)
System prompt to guide the agent’s behavior
Strategy for tool selection. Options: 'auto', 'required', 'none', or { type: 'tool', toolName: string } Default: 'auto'
Maximum tokens to generate in responses
Sampling temperature (0-1+). Higher values increase randomness. Recommended: Set either temperature or topP, not both
Nucleus sampling probability (0-1). Only tokens with top P probability mass are considered. Recommended: Set either temperature or topP, not both
Only sample from top K options. Advanced use only.
Penalty for repeating information (-1 to 1). 0 means no penalty.
Penalty for repeating words/phrases (-1 to 1). 0 means no penalty.
Stop generation when these sequences are encountered
Random seed for deterministic generation (if supported by model)
Maximum retry attempts for transient failures
Observability configuration for tracing and metrics
Methods
stream()
Streams AI responses with tool execution and state management.
options DurableAgentStreamOptions
required
Conversation history in AI SDK format. Each message has:
role: 'user', 'assistant', or 'system'
content: String or array of content parts
writable WritableStream<UIMessageChunk>
required
Stream to write response chunks. Use getWritable() from workflow package.
Override the system prompt for this request
Keep stream open after completion (useful for multiple writes)
Send a ‘start’ chunk at the beginning of the stream
Send a ‘finish’ chunk at the end of the stream
Maximum number of sequential LLM calls. Prevents infinite loops.
stopWhen StopCondition | StopCondition[]
Conditions to stop generation early (e.g., when specific tools are called)
Override tool selection strategy for this request
Limit available tools to this subset
Parse structured output from the response. Use Output.object({ schema }) or Output.text().
Accumulate UIMessage[] during streaming. Result will include uiMessages property.
Include raw provider chunks in the stream for advanced use cases
Callback before each LLM call. Use for context management or dynamic configuration. onStepFinish StreamTextOnStepFinishCallback
Called after each LLM step completes
onFinish StreamTextOnFinishCallback
Called when all steps complete successfully
onError StreamTextOnErrorCallback
Called when an error occurs during streaming
onAbort StreamTextOnAbortCallback
Called when the operation is aborted
Context passed to tool execution functions
experimental_repairToolCall Function to repair failed tool call parsing
experimental_transform StreamTextTransform | StreamTextTransform[]
Custom stream transformations
Custom URL download handler
Returns: Promise<DurableAgentStreamResult>
Final conversation messages including all tool calls and results
Details for each LLM step executed during the stream
Parsed structured output (only when experimental_output is specified)
Accumulated UI messages (only when collectUIMessages: true)
Examples
Basic Usage
Structured Output
Dynamic Context Management
Type Definitions
ModelMessage
StepResult
Best Practices
Use workflow steps for tools : Mark tool execute functions with 'use step' for automatic retries and durability
Set maxSteps : Always set a reasonable maxSteps limit to prevent infinite loops
Handle errors gracefully : Use onError callback to log and handle errors appropriately
Manage context size : Use prepareStep to inject/remove messages dynamically and manage context window
Stream to the client : Always use getWritable() to stream responses for better UX
Choose the right model : Use prepareStep to switch models based on task complexity
See Also