Integrations / Ruby SDK

Ruby SDK

Create sessions, interact with pages, and extract structured data.

Installation #

Install the gem from RubyGems:

gem install browserbeam

Or add it to your Gemfile:

gem "browserbeam"

Then run:

bundle install
Requires Ruby 3.0+. The SDK uses Faraday for HTTP requests — it is installed automatically as a dependency.

Quick Start #

Create a client, open a session, and interact with a page:

require "browserbeam"

client = Browserbeam::Client.new(api_key: "bb_your_key")

session = client.sessions.create(url: "https://example.com")
session.click(text: "More information")
result = session.extract(title: "string", paragraphs: ["string"])
puts result.extraction
session.close

Configuration #

Pass options when you create the client:

client = Browserbeam::Client.new(
  api_key: "bb_your_key",       # or set BROWSERBEAM_API_KEY env var
  base_url: "https://api.browserbeam.com",  # default
  timeout: 120                  # request timeout in seconds, default 120
)
Option Default Description
api_key ENV["BROWSERBEAM_API_KEY"] Your API key. The param takes priority over the env var.
base_url https://api.browserbeam.com API base URL.
timeout 120 HTTP request timeout in seconds.
If you omit api_key, the SDK reads BROWSERBEAM_API_KEY from the environment. If neither is set, it raises an ArgumentError.

Creating Sessions #

Call client.sessions.create to launch a browser session. It returns a Session object you use for all subsequent actions.

session = client.sessions.create(
  url: "https://example.com",
  viewport: { width: 1280, height: 720 },
  locale: "en-US",
  timezone: "America/New_York",
  user_agent: "MyBot/1.0",
  proxy: "http://user:pass@proxy.example.com:8080",
  block_resources: ["image", "font"],
  auto_dismiss_blockers: true,
  cookies: [{ name: "session", value: "abc123", domain: ".example.com" }],
  idempotency_key: "unique-request-id"
)

puts session.page.title
Parameter Type Description
url String URL to navigate to after launch.
viewport Hash { width:, height: } — browser viewport size.
locale String Browser locale, e.g. "en-US".
timezone String IANA timezone, e.g. "America/New_York".
user_agent String Custom user-agent string.
proxy String HTTP proxy URL.
block_resources Array Resource types to block, e.g. ["image", "font"].
auto_dismiss_blockers Boolean Auto-dismiss cookie banners and overlays.
cookies Array Cookies to set before navigation.
idempotency_key String Prevents duplicate session creation.

Session Methods #

Every method below sends a step to the browser and returns the updated session envelope.

Method Description
goto(url)Navigate to a URL.
observeGet page content and interactive elements.
clickClick an element by ref, text, or label.
typeType text character by character.
selectSelect a dropdown option.
checkToggle a checkbox.
fillSet the value of an input field; target by ref, text, or label.
fill_formFill multiple form fields at once.
extractExtract structured data matching a schema.
screenshotTake a screenshot of the page.
scroll_collectScroll the page and collect content.
scrollScroll the page or to an element.
waitWait for time, selector, text, or JS expression.
uploadUpload files to a file input.
pdfGenerate a PDF of the page.
execute_jsRun JavaScript in the browser.
closeClose the browser session.

goto(url) #

Navigate the browser to a new URL.

session.goto("https://example.com/about")

# Wait for a CSS selector or JS expression
session.goto("https://example.com", wait_for: ".loaded", wait_timeout: 5000)
session.goto("https://example.com", wait_until: "document.readyState === 'complete'")

observe #

Read the page content and discover interactive elements. Use this to understand what you can click or fill.

result = session.observe(scope: "main", format: "markdown")
puts result.page.markdown.content

result.page.interactive_elements.each do |el|
  puts "#{el.ref} — #{el.tag} — #{el.label}"
end

click #

Click an element. Target by ref (from observe), visible text, or label.

# By ref from observe results
session.click(ref: "a7")

# By visible text
session.click(text: "Sign in")

# By label (for buttons, links, inputs)
session.click(label: "Submit")

fill #

Set the value of an input field. Target by ref, text, or label. Clears existing content first.

# By ref
session.fill("hello@example.com", ref: "input3")

# By label
session.fill("hello@example.com", label: "Email")

# By visible text
session.fill("hello@example.com", text: "Email")

fill_form #

Fill multiple form fields in a single step. Optionally submit the form.

session.fill_form([
  { label: "Email", value: "hello@example.com" },
  { label: "Password", value: "s3cret" }
], submit: true)

extract #

Extract structured data from the page. Define a schema using Ruby keyword arguments.

result = session.extract(
  title: "string",
  price: "number",
  features: ["string"]
)

puts result.extraction
# => { "title" => "Pro Plan", "price" => 29, "features" => ["API access", "Priority support"] }

screenshot #

Capture a screenshot. The image is returned as base64 in media.

result = session.screenshot(full_page: true)

# Save to file
require "base64"
File.write("page.png", Base64.decode64(result.media.first.data))

scroll_collect #

Scroll through the page and collect all content. Useful for infinite-scroll pages.

result = session.scroll_collect(max_scrolls: 10)
puts result.page.markdown.content

close #

Close the browser session and release resources.

session.close
Sessions expire automatically after the configured timeout, but closing them explicitly frees resources immediately and stops billing.

type #

Type text character by character. Useful for inputs with autocomplete or client-side filtering. Target by ref, text, or label.

session.type("search query", ref: "input5", delay: 50)
session.type("hello", label: "Search")

select #

Select a dropdown option by value. Target the select element by ref, text, or label.

session.select("us", label: "Country")

check #

Toggle a checkbox or radio button. Target by ref, text, or label.

session.check(label: "I agree to the terms")
session.check(ref: "cb3", checked: false)

scroll #

Scroll the page or scroll an element into view. Target by ref, text, or label.

session.scroll(to: "bottom")
session.scroll(direction: "down", amount: 500)
session.scroll(text: "Footer section")

wait #

Wait for a duration, CSS selector, visible text, or a JavaScript expression to become truthy.

session.wait(ms: 2000)
session.wait(selector: ".loaded", timeout: 10000)
session.wait(until: "document.querySelectorAll('.item').length > 5")

upload #

Upload files to a file input. Target by ref, text, or label.

session.upload(["https://example.com/file.pdf"], ref: "file1")
session.upload(["https://example.com/photo.jpg"], label: "Upload photo")

pdf #

Generate a PDF of the page. Supports format, landscape, background, scale, and margin options.

result = session.pdf(format: "A4", landscape: true, scale: 0.8,
  margin: { top: "1cm", bottom: "1cm" })
require "base64"
File.write("page.pdf", Base64.decode64(result.media.first.data))

execute_js #

Run JavaScript code in the browser. The result is stored in the extraction under the specified key.

result = session.execute_js("return document.title")
puts result.extraction["js_result"]

# With custom result key and timeout
result = session.execute_js("return document.querySelectorAll('a').length",
  result_key: "link_count", timeout: 5000)

Session Management #

List, inspect, and destroy sessions through the client.sessions namespace.

List sessions

result = client.sessions.list(status: "active", limit: 10)
result.sessions.each do |s|
  puts "#{s.session_id} — #{s.status} — #{s.started_at}"
end

# Pagination
if result.has_more
  next_page = client.sessions.list(after: result.next_cursor)
end

Get session info

info = client.sessions.get("ses_abc123")
puts info.status        # => "active"
puts info.expires_at    # => "2026-03-24T12:00:00Z"

Destroy a session

client.sessions.destroy("ses_abc123")

Error Handling #

All errors inherit from Browserbeam::Error. Each error exposes message, code, status_code, context, and request_id.

Class HTTP When
AuthenticationError401Invalid or missing API key.
InvalidRequestError400Malformed request or invalid parameters.
SessionNotFoundError404Session does not exist or has expired.
RateLimitError429Too many requests. Check retry_after.
QuotaExceededError429Plan quota reached. Check retry_after.
EngineUnavailableError503Service temporarily unavailable. Check retry_after.
StepExecutionErrorvariesA step failed. Check step_index and action.
begin
  session = client.sessions.create(url: "https://example.com")
  session.click(ref: "missing")
  session.close
rescue Browserbeam::RateLimitError => e
  puts "Rate limited. Retry after #{e.retry_after}s"
rescue Browserbeam::SessionNotFoundError => e
  puts "Session gone: #{e.message}"
rescue Browserbeam::AuthenticationError => e
  puts "Bad API key: #{e.message}"
rescue Browserbeam::Error => e
  puts "Error [#{e.code}]: #{e.message}"
  puts "Request ID: #{e.request_id}"
end

Full Example #

Extract the top stories from Hacker News, search for a topic, and save a screenshot.

require "browserbeam"
require "base64"
require "json"

client = Browserbeam::Client.new

# Navigate to Hacker News
session = client.sessions.create(url: "https://news.ycombinator.com/")

# Extract top stories from the front page
result = session.extract(
  stories: [{ "_parent": ".titleline", "title": "a >> text", "url": "a >> href" }]
)
result.extraction["stories"].first(5).each do |story|
  puts "#{story['title']} — #{story['url']}"
end

# Fill the search form and submit
session.fill_form({ "q" => "browser automation" }, submit: true)

# Take a screenshot of search results
shot = session.screenshot(full_page: true)
File.write("hn-search.png", Base64.decode64(shot.media.first.data))

session.close

Source code on GitHub. Found an issue? Open a ticket.

API Reference

Give your AI agent a faster, leaner browser

Structured page data instead of raw HTML. Your agent processes less, decides faster, and costs less to run.

Stability detection built in
Fraction of the payload size
Diffs after every action
No credit card required. 1 hour of free runtime included.