module RubyLLM

RubyLLM is an AI framework for Ruby and Rails. Build conversations and agents, generate media, process documents, and work with model providers through one Ruby API. The guides at rubyllm.com/ introduce each feature; this reference documents its classes, arguments, and results.

RubyLLM.configure do |config|
  config.openai_api_key = ENV['OPENAI_API_KEY']
end

chat = RubyLLM.chat
chat.ask "What is the capital of France?"

Conversations, tools, and agents

RubyLLM.chat returns a Chat that holds the conversation. Chat#ask accepts text and attachments, runs tools as needed, and returns a Message. Give it a block to receive Chunk objects as the response streams:

chat.ask("Summarize this report", with: "report.pdf") do |chunk|
  print chunk.content
end

Configure the request with chainable methods:

Subclass Tool and implement execute to give the model an application action. Tool.requires_approval pauses execution for a human decision; Chat#approve and Chat#deny record it. Tool#progress reports what a running tool is doing to Chat#after_tool_progress as a Progress. Chat#with_provider_tools enables provider-executed tools such as web search, code execution, and remote MCP. Their calls appear as ServerToolCall values, with Citation values for sources. MCP is a Model Context Protocol client: describe a server to connect to in an MCP class, and Chat#with_mcp gives the model its tools. RubyLLM.mcp connects to one inline.

Agent defines a reusable configuration with model, instructions, tools, schema, and runtime inputs. Chat#ask_later, Chat#generate, Chat#run_tools, and Chat#step expose the conversation loop for jobs and application logic.

Images, video, and speech

Individual operations do not require a chat. Image, Video, and Speech results share +save(path)+ and to_blob:

RubyLLM.paint("A red panda coding Ruby, watercolor").save("panda.png")
RubyLLM.animate("A paper boat sailing down a gutter").save("boat.mp4")
RubyLLM.speak("Welcome to RubyLLM.").save("welcome.mp3")

Image.paint accepts source images and masks for editing. Video.animate accepts reference media, video edits, and extensions on supported models. RubyLLM.animate waits for the clip; RubyLLM.animate_later returns a VideoJob that you can poll. Speech.speak also streams SpeechChunk objects while retaining the complete audio result.

Documents, audio, and retrieval

transcript = RubyLLM.transcribe("meeting.wav")
document = RubyLLM.ocr("report.pdf", pages: [0, 1])
embedding = RubyLLM.embed("Ruby is a programmer's best friend")

Transcription provides text, timestamps, and speaker information when the model reports them; streaming yields TranscriptionChunk objects. OCR returns document pages and combined markdown. Embedding returns vectors for text or supported media, and RubyLLM.rerank returns a Rerank whose results order documents by relevance. SearchResults lets a Tool return source documents that the model can cite.

RubyLLM.upload returns an UploadedFile for reuse across requests. RubyLLM.download returns a DownloadedFile with the same saving interface:

RubyLLM.download(file.id, provider: file.provider).save("report.pdf")

Tokenization, moderation, and research

RubyLLM.count_tokens and Chat#count_tokens count a model request without generating a response. RubyLLM.tokenize returns plain-text token IDs and a count as a Tokenization, excluding chat formatting and attachments.

result = RubyLLM.tokenize("Hello Ruby", model: "grok-4.3", provider: :xai)
result.ids
result.count

RubyLLM.moderate screens text and images, returning Moderation results with categories, scores, and flagged?. RubyLLM.research runs a hosted research task and returns its report as a Message; RubyLLM.research_later returns a ResearchJob for polling and cancellation. Hosted agent identities are selected separately from model IDs.

Evaluations

Evaluation runs your application against a dataset of cases and grades each result. Implement Evaluation#perform to return a value, Message, Chat, or Agent. Without declared criteria, a model checks each result against the case’s expected_output. Evaluations can also use an Agent or a Judge as their evaluator, and Ruby assertions. Datasets live under app/evals, named after the class:

class SupportEvaluation < RubyLLM::Evaluation
  def perform(input)
    SupportAgent.new.ask(input)
  end
end
SupportEvaluation.run.passed?

Evaluation.run returns an Evaluation::Report with each trial’s verdicts, tokens, and cost. The ruby_llm:eval Rake task, Evaluation::RSpec, and Evaluation::Minitest run the same cases from the command line and tests.

Typed judgments

Judge defines reusable probability, choice, and score questions. Its judge method evaluates supplied text, structured data, or images passed as with: and returns a Judgment:

class Urgency < RubyLLM::Judge
  probability :urgent, "Does this need attention today?"
end
Urgency.judge("Please help today.").urgent.probability

RubyLLM.judge accepts question definitions as a Hash. Probability, Choice, and Score answers retain uncertainty; Judgment reports the model, tokens, and cost. Questions share the supplied input and do not retain chat history.

Batches, usage, and configuration

RubyLLM.batch submits staged chats or EmbeddingRequest objects for provider-side processing. Batch exposes progress, results, token usage, and cost. RubyLLM.cache creates a managed CachedContent resource for reuse with Chat#with_caching.

Tokens and Cost report usage and pricing. Chat totals include retries and attempts that produced no message. Provider-reported costs take precedence over estimates; unknown usage and prices remain nil. RubyLLM.with_usage_owner attributes the usage of operations to a record. OpenTelemetry.enable enables optional tracing alongside existing subscribers. Your application configures the OpenTelemetry SDK and exporters.

RubyLLM.workflow groups instrumentation from ordinary Ruby code into named Workflow steps.

RubyLLM.configure sets global Configuration; RubyLLM.context creates isolated settings for a request or tenant. Models finds, filters, and describes the model catalog. Provider supplies endpoints, authentication, and protocol selection; Protocol implements request and response formats. Error subclasses normalize provider failures, and Error#request_shape describes a refused conversation request as a RequestShape.

Rails integration

ActiveRecord::ActsAs adds acts_as_chat and acts_as_message to your application’s models. ActiveRecord::ChatMethods and ActiveRecord::MessageMethods provide the conversation API with persistence, Active Storage attachments, and support for Hotwire streaming and jobs. Approvals and cancellation survive requests and processes.

Your application owns chats and messages; RubyLLM owns usage, tool calls, models, batches, MCP credentials, and provider files. ActiveRecord::Record configures their shared database connection. Agent can create and reload your chat records through Agent.chat_model. Individual operations also work directly in Rails services and jobs.