OpenSandbox

中文版

Ruby SDK for the open-sandbox.ai API — manage isolated container sandboxes for secure code execution.

⚠️ This is an unofficial Ruby gem, not affiliated with or maintained by the OpenSandbox team. Official project: alibaba/OpenSandbox

Gem Version CI

What is OpenSandbox?

OpenSandbox is a general-purpose sandbox platform for AI applications, open-sourced by Alibaba and listed in the CNCF Landscape.

The Problem It Solves

Modern AI applications — coding agents, browser automation, RL training, AI code execution — need to run untrusted or model-generated code safely. Spinning up ephemeral containers manually, wiring up lifecycle management, handling networking, streaming logs, and tearing everything down reliably is complex and error-prone.

OpenSandbox solves this by providing:

  • Isolated runtime environments — each sandbox runs in its own container, fully isolated from the host and other workloads. Supports secure runtimes like gVisor, Kata Containers, and Firecracker microVM.
  • Unified sandbox lifecycle API — provision, monitor, pause, resume, renew, and terminate sandboxes via a single consistent API, backed by Docker or Kubernetes.
  • In-sandbox execution — run shell commands, execute multi-language code (Python, Node.js, etc.), manage files, expose ports, and stream logs/metrics from inside the sandbox.
  • Resource Pools — pre-warm sandbox pools to eliminate cold-start latency for high-throughput workloads.
  • Network policy — per-sandbox ingress/egress controls with unified gateway routing.

Typical Use Cases

Scenario Description
Coding Agents Run Claude Code, Gemini CLI, Codex, and other agent tools in isolated sandboxes
AI Code Execution Safely execute model-generated code, stream outputs, iterate with reproducible environments
Browser Automation Run Chrome / Playwright workloads with controlled runtime and networking
Remote Development Host VS Code Web and cloud desktop environments securely
RL Training Launch reinforcement learning tasks with managed sandbox lifecycle and resource controls

This Ruby gem wraps the OpenSandbox HTTP API so you can use all of the above from your Ruby or Rails application.

Installation

Add to your Gemfile:

gem "open_sandbox", path: "../open_sandbox"   # local development
# or, once published:
gem "open_sandbox", "~> 0.1"

Rails

Generate the initializer in your Rails app:

rails generate open_sandbox:install

This creates config/initializers/open_sandbox.rb:

OpenSandbox.configure do |config|
  # config.base_url = ENV.fetch("SANDBOX_DOMAIN", "https://api.open-sandbox.ai")
  # config.api_key  = ENV.fetch("SANDBOX_API_KEY")
  # config.timeout  = 300
  # config.logger   = Rails.logger
end

Uncomment and adjust the options you need. By default the SDK reads SANDBOX_DOMAIN and SANDBOX_API_KEY from ENV, so the initializer can stay empty for most setups.

Quick Start

require "open_sandbox"

# Configure (picks up SANDBOX_DOMAIN / SANDBOX_API_KEY from ENV by default)
OpenSandbox.configure do |c|
  c.base_url = "http://localhost:8787"   # or "https://api.open-sandbox.ai"
  c.api_key  = "sk-..."                  # omit for local dev
  c.logger   = Logger.new($stdout, level: :debug)
end

Runner — one-shot code execution

# Python
result = OpenSandbox::Runner.python("print(2 ** 10)")
result.output    # => "1024\n"
result.success?  # => true
result.elapsed   # => 3.14

# Node.js
result = OpenSandbox::Runner.node("console.log('hi')")

# Shell
result = OpenSandbox::Runner.shell("echo $((6 * 7))")

# Custom image
result = OpenSandbox::Runner.call(
  image:   "ubuntu:24.04",
  command: ["bash", "-c", "ls /"],
  timeout: 60
)

The sandbox is always deleted after the run (even on error). Runner uses OpenSandbox.logger — set it to Rails.logger in your initializer to get structured logs.

Timeout resolution order: explicit timeout: argument → SANDBOX_TIMEOUT ENV → 300 s (default).

OpenSandbox client

client = OpenSandbox.client

# Create a sandbox
sandbox = client.sandboxes.create(
  image:           "python:3.11-slim",
  entrypoint:      ["python", "-c", "print(2 ** 10)"],
  timeout:         300,
  resource_limits: { "cpu" => "500m", "memory" => "256Mi" }
)
puts sandbox.id        # => "c9a03139-..."
puts sandbox.status.state  # => "Running"

# Wait until Running
client.sandboxes.wait_until(sandbox.id, target_state: OpenSandbox::SandboxState::RUNNING)

# Get endpoint for a service on port 8080
ep = client.sandboxes.endpoint(sandbox.id, port: 8080)
puts ep.url   # => "http://sb-xxx.sandbox.local:8080"

# Proxy an HTTP request directly to the sandbox
response = client.sandboxes.proxy(sandbox.id, port: 8080, method: :post,
                                  path: "/run", body: { code: "print(1)" })

# Fetch logs (Docker timestamps stripped automatically)
puts client.sandboxes.logs(sandbox.id, tail: 100)

# Lifecycle management
client.sandboxes.pause(sandbox.id)
client.sandboxes.resume(sandbox.id)
client.sandboxes.renew_expiration(sandbox.id, expires_at: Time.now + 3600)
client.sandboxes.delete(sandbox.id)

Resource Pools (pre-warm for low cold-start)

pool = client.pools.create(
  name:     "python-pool",
  template: { spec: { containers: [{ name: "main", image: "python:3.11-slim" }] } },
  capacity_spec: OpenSandbox::PoolCapacitySpec.new(
    buffer_max: 5, buffer_min: 2, pool_max: 20, pool_min: 2
  )
)

# Use the pool when creating a sandbox
client.sandboxes.create(
  image:      "python:3.11-slim",
  entrypoint: ["python", "app.py"],
  resource_limits: { "cpu" => "1", "memory" => "512Mi" },
  extensions: { "poolRef" => "python-pool" }
)

Diagnostics

puts client.sandboxes.logs(id, tail: 200, since: "10m")
puts client.sandboxes.events(id, limit: 50)
puts client.sandboxes.diagnostics(id)     # inspect + events + logs combined

Configuration

Option ENV var Default
base_url SANDBOX_DOMAIN http://localhost:8787
api_key SANDBOX_API_KEY nil (optional for local)
timeout SANDBOX_TIMEOUT 300 (seconds)
logger Logger.new(nil) (silent)

Error Handling

rescue OpenSandbox::NotFoundError   => e  # 404
rescue OpenSandbox::AuthenticationError   # 401
rescue OpenSandbox::ForbiddenError        # 403
rescue OpenSandbox::ConflictError         # 409
rescue OpenSandbox::ValidationError       # 422
rescue OpenSandbox::ServerError           # 5xx
rescue OpenSandbox::ConnectionError       # network / timeout
rescue OpenSandbox::Error                 # catch-all

Log Utility

Strip Docker-style timestamp prefixes from raw log strings:

raw = "2026-04-29T13:37:33.993Z 1024\n"
OpenSandbox::LogUtils.strip_timestamps(raw)
# => "1024\n"

Development

bundle install
bundle exec rake test     # run all tests

Other SDKs

OpenSandbox provides official SDKs for multiple languages. See the full list at alibaba/OpenSandbox — SDKs.

License

MIT