How to Capture Website Screenshots in Ruby

How to Capture Website Screenshots in Ruby

Ruby is a good fit for screenshot automation because many teams already have Ruby jobs running around reporting, QA, content ops, or Rails admin workflows. You do not need to run a browser cluster inside your app just to capture a marketing page. The clean path is to call a screenshot API, receive the image bytes, and save the file.

The browser details still matter. Playwright and Chrome DevTools Protocol expose full-page capture, viewport sizing, device scale factors, image formats, and clipped regions. FrameSnap wraps that rendering work behind an API, so your Ruby code can focus on when to capture, where to store the result, and how to move it through the rest of your workflow.

1. Use Net::HTTP or HTTParty

Ruby's standard library includes Net::HTTP, which is enough for a direct GET request. If your app already uses the httparty gem, HTTParty gives you a terser interface and convenient query handling. Either way, keep the screenshot settings explicit: target URL, full-page mode, viewport width, output format, and any delay needed after page load.

require "net/http"
require "uri"

uri = URI("https://api.framesnap.dev/v1/screenshot")
uri.query = URI.encode_www_form(
  url: "https://example.com/pricing",
  format: "png",
  full_page: true,
  viewport_width: 1440
)

request = Net::HTTP::Get.new(uri)
request["Authorization"] = "Bearer #{ENV.fetch("FRAMESNAP_API_KEY")}"

2. Make the authenticated GET request

Treat screenshot calls like any other external dependency. Set open and read timeouts, check for non-200 responses, and log enough context to retry safely without leaking the API key. A screenshot may take longer than a JSON API call because the service has to load the page and encode the final image.

response = Net::HTTP.start(uri.host, uri.port, use_ssl: true, read_timeout: 60) do |http|
  http.request(request)
end

unless response.is_a?(Net::HTTPSuccess)
  raise "Screenshot failed: #{response.code} #{response.message}"
end

3. Save the image response with File.binwrite

Do not parse the response as text. A PNG, JPEG, or PDF response is binary data, so write response.body directly with File.binwrite. Use deterministic filenames that include the page, viewport, and capture date.

filename = "screenshots/pricing-1440-#{Time.now.utc.strftime("%Y%m%d")}.png"
FileUtils.mkdir_p(File.dirname(filename))
File.binwrite(filename, response.body)

If you prefer HTTParty, the same pattern applies: send headers and query params, verify the status code, then write the raw body. The important part is not the client library; it is keeping authentication, capture parameters, response validation, and binary file handling boring and repeatable.

4. Background batch jobs with Sidekiq

Batch screenshot work should not run inside a web request. Sidekiq is built for Ruby background processing, which makes it a natural place to capture many URLs for QA reports, onboarding, competitor monitoring, or documentation refreshes. Queue one job per URL, store the requested parameters with the job, and make the worker idempotent by writing to a predictable object key or file path.

For larger runs, add rate limits and retries with backoff. A useful worker records the target URL, viewport, content type, output path, API status, and capture duration.

Use FrameSnap from Ruby

FrameSnap gives Ruby developers a simple API for turning URLs into PNG, JPEG, PDF, or retina screenshot outputs without maintaining browser infrastructure. Use the FrameSnap screenshot tool for a one-off capture, or create a FrameSnap API key when you are ready to wire screenshots into Rails, Sidekiq, QA checks, or reporting jobs. Free accounts include 100 calls per month.

FAQ

Can Ruby capture website screenshots without launching Chrome locally?

Yes. Ruby can call a screenshot API over HTTPS, receive the rendered image as binary data, and save it with File.binwrite. That avoids managing browser processes inside your app.

Should I use Net::HTTP or HTTParty for a Ruby screenshot API?

Use Net::HTTP when you want no extra gem dependency. Use HTTParty if your app already uses it and you prefer cleaner query and header handling. Both can save binary image responses correctly.

When should screenshot capture move to Sidekiq?

Move screenshot capture to Sidekiq when captures are slow, repeated, or batched. Background jobs keep Rails requests fast and make retries, rate limits, and monitoring easier.

Capture Screenshots with FrameSnap

One API call. PNG, JPEG, or PDF. Free tier included.