Skip to content

Agents

Controllers for AI interactions. Like Rails controllers, agents have actions, callbacks, views, and concerns—but they generate AI responses instead of rendering HTML.

Quick Example

ruby
class SupportAgent < ApplicationAgent
  before_generation :load_user_context

  def help
    prompt message: "User needs help: #{params[:message]}"
  end

  private

  def load_user_context
    @user = User.find(params[:user_id]) if params[:user_id]
  end
end

Usage:

ruby
SupportAgent.with(user_id: 1, message: "Need help").help.generate_now

How It Works

The request-response cycle mirrors Rails controllers:

  1. Action called - Agent.with(params).action
  2. Callbacks run - before_generation, before_prompt
  3. Context built - prompt() or embed() configures messages
  4. View rendered - ERB template (if exists) renders content
  5. Provider executes - AI service generates response
  6. Result returned - Response object with message and metadata

Building Agents

Basic Structure

Inherit from ActiveAgent::Base (or ApplicationAgent) and define actions:

ruby
class TranslationAgent < ApplicationAgent
  generate_with :openai, model: "gpt-4o"

  def translate
    prompt message: "Translate '#{params[:text]}' to #{params[:target_lang]}"
  end
end

Actions are public instance methods that call prompt() or embed().

Invocation

Call agents using with() to pass parameters:

ruby
# With parameters
generation = TranslationAgent.with(
  text: "Hello world",
  target_lang: "es"
).translate

# Execute synchronously
response = generation.generate_now
# response.message.content  # => "Hola mundo"

For prototyping, use direct methods:

ruby
response = ApplicationAgent.prompt(message: "Hello").generate_now

See Generation for complete documentation on execution patterns and response objects.

Actions Interface

Agents define actions using prompt() or embed() to configure generation context:

ruby
class MyAgent < ApplicationAgent
  def my_action
    # Simple message
    prompt "User message: #{params[:message]}"
  end

  def embed_text
    # Simple input
    embed "Text to embed: #{params[:input]}"
  end
end

See Actions for complete documentation on messages, tools, structured output, and embeddings.

Advanced Features

Using Concerns

Extend agents with concerns to share functionality across multiple agents:

ruby
# app/agents/concerns/research_tools.rb
module ResearchTools
  extend ActiveSupport::Concern

  def search_papers
    prompt message: "Search: #{params[:query]}"
  end

  def analyze_data
    prompt message: "Analyze: #{params[:data]}"
  end
end

# app/agents/research_agent.rb
class ResearchAgent < ApplicationAgent
  include ResearchTools  # Adds search_papers and analyze_data actions

  generate_with :openai, model: "gpt-4o"
end

Concerns let you:

  • Share tool actions across multiple agents
  • Organize complex agents into logical modules
  • Reuse common patterns (authentication, logging, data access)
  • Test functionality independently

Callbacks

Hook into the generation lifecycle:

ruby
class MyAgent < ApplicationAgent
  before_generation :load_context
  after_generation :log_response

  def chat
    prompt message: params[:message]
  end

  private

  def load_context
    @user = User.find(params[:user_id]) if params[:user_id]
  end

  def log_response
    Rails.logger.info "Generated response"
  end
end

See Callbacks for complete documentation.

Streaming

Stream responses in real-time:

ruby
class StreamingAgent < ApplicationAgent
  on_stream :broadcast_chunk

  def chat
    prompt message: params[:message], stream: true
  end

  private

  def broadcast_chunk(chunk)
    # In real app: ActionCable.server.broadcast("chat", content: chunk.delta)
  end
end

See Streaming for complete documentation.

Learn More

Core Features:

Related Topics: