Ruby SDK

Zero dependencies. Pure net/http. Works with Rails, Sinatra, or plain Ruby.

Installation

gem install satsrail

Or add to your Gemfile:

gem "satsrail"

Then run bundle install

Configuration

Global configuration
require "satsrail"

SatsRail.api_key = "sk_test_your_key_here"
Rails initializer

Create config/initializers/satsrail.rb

SatsRail.configure do |config|
  config.api_key  = ENV["SATSRAIL_API_KEY"]
  config.base_url = "https://satsrail.com" # default
  config.timeout  = 30 # seconds
end
Never hardcode your secret key. Use environment variables: ENV["SATSRAIL_API_KEY"]

Creating Orders

order = SatsRail::Order.create(
  amount_usd: 50.00,
  description: "Order #1234",
  metadata: {
    customer_id: "cust_abc",
    sku: "premium-plan"
  }
)

puts order.id               # "ord_..."
puts order.status            # "pending"
puts order.lightning_invoice  # bolt11 string (if auto-generated)

Pass generate_invoice: true to get a Lightning invoice in the same call:

order = SatsRail::Order.create(
  amount_usd: 25.00,
  description: "Subscription",
  generate_invoice: true,
  payment_method: "lightning"
)
puts order.invoice.bolt11  # lnbc...

Listing Orders

# List all orders
orders = SatsRail::Order.list

# Filter by status
pending = SatsRail::Order.list(status: "pending")

# Pagination
page2 = SatsRail::Order.list(page: 2, per_page: 25)

orders.data.each do |order|
  puts "#{order.id}: #{order.status} — $#{order.amount_usd}"
end

Getting Order Details

order = SatsRail::Order.retrieve("ord_abc123")

puts order.id
puts order.status
puts order.amount_usd
puts order.created_at

Generating Invoices

invoice = SatsRail::Invoice.generate(
  order_id: "ord_abc123",
  payment_method: "lightning"
)

puts invoice.id          # "inv_..."
puts invoice.bolt11       # Lightning payment string
puts invoice.amount_sats

Checking Invoice Status

status = SatsRail::Invoice.status("inv_abc123")

puts status.paid         # true or false
puts status.settled_at    # timestamp if paid
puts status.amount_sats

# Poll until paid
def wait_for_payment(invoice_id)
  loop do
    s = SatsRail::Invoice.status(invoice_id)
    return s if s.paid
    sleep 2
  end
end

Checkout Sessions

Create a hosted checkout page — perfect when you don't want to build your own payment UI.

session = SatsRail::CheckoutSession.create(
  amount_usd: 99.00,
  description: "Annual Plan",
  success_url: "https://yoursite.com/success",
  cancel_url: "https://yoursite.com/cancel",
  metadata: { plan: "annual" }
)

# Redirect customer to hosted checkout
puts session.url  # https://satsrail.com/checkout/...

# In a Rails controller:
redirect_to session.url, allow_other_host: true

Webhook Verification

Verify webhook signatures to ensure events are genuinely from SatsRail.

Rails Controller
class SatsrailWebhooksController < ApplicationController
  skip_before_action :verify_authenticity_token

  def create
    signature = request.headers["X-SatsRail-Signature"]
    payload = request.body.read

    begin
      event = SatsRail::Webhook.verify(payload, signature, "whsec_your_secret")

      case event.type
      when "order.paid"
        Rails.logger.info "Order paid: #{event.data.id}"
        # Fulfill the order
      when "invoice.settled"
        Rails.logger.info "Invoice settled: #{event.data.id}"
      end

      render json: { received: true }
    rescue SatsRail::WebhookSignatureError => e
      render plain: e.message, status: :bad_request
    end
  end
end
Sinatra
post "/webhooks/satsrail" do
  signature = request.env["HTTP_X_SATSRAIL_SIGNATURE"]
  payload = request.body.read

  begin
    event = SatsRail::Webhook.verify(payload, signature, "whsec_your_secret")

    case event.type
    when "order.paid"
      puts "Order paid: #{event.data.id}"
    end

    { received: true }.to_json
  rescue SatsRail::WebhookSignatureError
    halt 400, "Invalid signature"
  end
end

Error Handling

begin
  order = SatsRail::Order.create(amount_usd: 50.00)
rescue SatsRail::AuthenticationError
  puts "Invalid API key"
rescue SatsRail::RateLimitError => e
  puts "Rate limited — retry after #{e.retry_after}"
rescue SatsRail::SatsRailError => e
  puts "API error: #{e.message} (#{e.code})"
end

Start building with Ruby

Get your API key and accept Bitcoin payments in minutes.