Execute código em mais de 42 linguagens com uma única chamada API. Veja como começar:
Obtenha sua chave API
Cadastre-se em unsandbox.com/console para obter suas credenciais API.
Faça sua primeira requisição
Envie código para o endpoint de execução e receba resultados instantaneamente.
Construa algo incrível
Use nossa execução em sandbox para agentes de machine learning, playgrounds de código, ferramentas educacionais e mais.
Baixar
# Linux x86_64
wget https://unsandbox.com/downloads/un
chmod +x un
# Move to PATH (optional)
sudo mv un /usr/local/bin/
Compilar do código fonte
# Requirements: GCC, libcurl, libwebsockets
sudo apt-get install build-essential libcurl4-openssl-dev libwebsockets-dev
# Compile
wget https://unsandbox.com/downloads/un.c
gcc -Wall -O2 -o un un.c -lcurl -lwebsockets
Bibliotecas SDK (un-inception)
Para linguagens que precisam de acesso programático, use nossas implementações de SDK:
# Python - download un.py
wget https://unsandbox.com/cli/inception/un.py
python un.py script.py
# JavaScript - download un.js
wget https://unsandbox.com/cli/inception/un.js
node un.js script.py
# Go - download un.go
wget https://unsandbox.com/cli/inception/un.go
go run un.go script.py
Todas as requisições API requerem autenticação por assinatura HMAC-SHA256 para segurança.
Obrigatório
| Header | Description |
|---|---|
Authorization |
Bearer <public_key> (your unsb-pk-xxxx key) |
X-Timestamp |
Unix timestamp in seconds (±5 min tolerance) |
X-Signature |
HMAC-SHA256 signature (lowercase hex) |
Content-Type |
application/json |
Formato da Assinatura
HMAC-SHA256(secret_key, timestamp:METHOD:path:body)
Exemplo de string de assinatura:
1699564800:POST:/execute:{"language":"python","code":"print('hi')"}
Sua chave secreta nunca é transmitida. O servidor verifica assinaturas usando sua chave criptografada.
Execute qualquer arquivo de código. A linguagem é detectada automaticamente pela extensão do arquivo ou shebang.
Uso Básico
# Python
un hello.py
# JavaScript
un app.js
# Rust (compiles and runs)
un main.rs
# C (compiles and runs)
un program.c
# Go
un main.go
Com Opções
# Extended timeout (5 minutes)
un --ttl 300 long_script.py
# With more CPU/RAM (4 vCPUs, 8GB RAM)
un -v 4 heavy_compute.py
# Maximum resources (8 vCPUs, 16GB RAM)
un --vcpu 8 ml_training.py
Resposta
A saída é transmitida diretamente para seu terminal:
$ un hello.py
Hello from unsandbox!
$ echo $?
0
Equivalente API
POST /execute
{
"success": true,
"stdout": "Hello from unsandbox!\n",
"stderr": "",
"exit_code": 0,
"language": "python",
"total_time_ms": 127
}
Execute trechos de código diretamente da linha de comando usando a flag -s.
Uso Básico
# Python
un -s python 'print("Hello World")'
# Bash
un -s bash 'echo "Hello" && date'
# JavaScript
un -s javascript 'console.log(Math.PI)'
# Ruby
un -s ruby 'puts 2 ** 100'
# Go (full program)
un -s go 'package main; import "fmt"; func main() { fmt.Println("Hi") }'
Código Multilinha
# Using heredoc
un -s python <<'EOF'
import json
data = {"name": "unsandbox", "version": 2}
print(json.dumps(data, indent=2))
EOF
Linguagens Suportadas
Qualquer uma das 42 linguagens suportadas funciona com -s:
un -s python 'print(42)'
un -s javascript 'console.log(42)'
un -s typescript 'console.log(42 as number)'
un -s ruby 'puts 42'
un -s php '<?php echo 42;'
un -s perl 'print 42'
un -s lua 'print(42)'
un -s rust 'fn main() { println!("42"); }'
un -s c 'int main() { printf("42"); return 0; }'
un -s cpp 'int main() { std::cout << 42; }'
un -s java 'class M { public static void main(String[] a) { System.out.println(42); }}'
un -s kotlin 'fun main() = println(42)'
un -s go 'package main; import "fmt"; func main() { fmt.Println(42) }'
un -s haskell 'main = print 42'
un -s elixir 'IO.puts 42'
un -s julia 'println(42)'
un -s r 'print(42)'
Passe variáveis de ambiente para seu código usando a flag -e.
Variável Única
un -e DEBUG=1 script.py
un -e API_KEY=secret app.js
Múltiplas Variáveis
un -e DEBUG=1 -e NAME=World -e COUNT=42 script.py
Com Código Inline
un -e NAME=Claude -s python 'import os; print(f"Hello {os.environ[\"NAME\"]}")'
un -e X=10 -e Y=20 -s bash 'echo "Sum: $((X + Y))"'
Exemplo
# config_demo.py
import os
debug = os.environ.get('DEBUG', '0')
name = os.environ.get('NAME', 'World')
if debug == '1':
print(f"Debug mode enabled")
print(f"Hello {name}!")
Executar
$ un -e DEBUG=1 -e NAME=unsandbox config_demo.py
Debug mode enabled
Hello unsandbox!
Teleporte arquivos para o sandbox. O CLI usa a flag -f; a API usa o array input_files.
Uso do CLI
# Single file
un -f data.csv process.py
# Multiple files
un -f data.csv -f config.json -f image.png script.py
# Large files (skip confirmation)
un -f large_dataset.parquet -y ml_training.py
Limites
- Número máximo de arquivos
- Tamanho total máximo
- Tamanho máximo de arquivo único
# Files are placed in working directory
un -f data.csv -s python 'print(open("data.csv").read())'
# Process multiple input files
un -f input.json -f config.yaml script.py
{
"language": "python",
"code": "print(open('data.csv').read())",
"input_files": [
{
"filename": "data.csv",
"content": "bmFtZSxhZ2UKQWxpY2UsMzAKQm9iLDI1"
}
]
}
O conteúdo deve estar codificado em Base64.
Os arquivos são colocados no diretório de trabalho:
- Python:
open('data.csv') - Node.js:
fs.readFileSync('data.csv') - Ruby:
File.read('data.csv') - Go:
os.ReadFile("data.csv") - Bash:
cat data.csv
Teleporte arquivos para fora do sandbox. Use -a para coletar artefatos de /tmp/artifacts/ ou obter binários compilados.
Coletar Arquivos Gerados
# Files in /tmp/artifacts/ are collected
un -a -o ./outputs script.py
Binário pré-compilado
# Compile C and get the binary
un -a -o ./bin main.c
# Compile Rust and get the binary
un -a -o ./bin main.rs
# Compile Go and get the binary
un -a -o ./bin main.go
Compilação WebAssembly
# Compile to WASM (supported languages)
un --wasm -o ./wasm main.c
un --wasm -o ./wasm main.rs
Exemplo: Gerar e Coletar
# generate_report.py
import json
import os
os.makedirs('/tmp/artifacts', exist_ok=True)
data = {"users": 100, "revenue": 50000}
with open('/tmp/artifacts/report.json', 'w') as f:
json.dump(data, f, indent=2)
print("Report generated!")
Executar
$ un -a -o ./reports generate_report.py
Report generated!
$ ls ./reports
report.json
Zero Trust (padrão)
Isolamento completo de rede. Sem acesso à internet.
# Default - no network
un script.py
Semi-Confiável
Acesso à internet via proxy de saída.
# Enable network access
un -n semitrusted script.py
# Or with sessions
un session -n semitrusted
Casos de Uso
# Zero Trust - safe for untrusted code
un -s python 'print("Isolated execution")'
# Semi-Trusted - when you need network
un -n semitrusted -s python '
import requests
r = requests.get("https://api.github.com")
print(r.status_code)
'
# Semi-Trusted session for development
un session -n semitrusted --shell bash
Inicie uma sessão de shell interativo em um contêiner sandbox.
Sessão Básica
# Default bash shell
un session
# Choose your shell
un session --shell zsh
un session --shell fish
Sessões REPL
# Python REPL
un session --shell python3
un session --shell ipython
un session --shell bpython
# Node.js REPL
un session --shell node
# Ruby REPL
un session --shell irb
# Other REPLs
un session --shell julia
un session --shell ghci # Haskell
un session --shell iex # Elixir
Gravação de sessão
# With network access
un session -n semitrusted
# With persistence (can reconnect)
un session --tmux
un session --screen
# With timeout (1 hour)
un session --ttl 3600
# Full audit recording
un session --audit -o ./logs
Equivalente API
POST /sessions
{
"session_id": "sess_xyz789",
"websocket_url": "wss://api.unsandbox.com/sessions/sess_xyz789/shell",
"status": "running"
}
Listar Trabalhos Ativos
un session --list
Saída
Active sessions: 2
SESSION ID CONTAINER SHELL TTL STATUS
sess_abc123... unsb-vm-12345 python3 45m30s active
sess_def456... unsb-vm-67890 bash 1h2m active
Obter Detalhes da Sessão
un session --info sess_abc123
Equivalente API
GET /sessions and GET /sessions/{id}
{
"sessions": [
{
"session_id": "sess_abc123",
"status": "running",
"network_mode": "zerotrust",
"shell": "python3"
}
]
}
Reconecte-se a sessões persistentes (requer --tmux ou --screen).
Criar Sessão Persistente
# With tmux (recommended)
un session --tmux
# With screen
un session --screen
Desconectar
# tmux: Press Ctrl+b then d
# screen: Press Ctrl+a then d
Desconto
# By session ID
un session --attach sess_abc123
# By container name
un session --attach unsb-vm-12345
Encerrar Sessão
# Kill by ID
un session --kill sess_abc123
# Kill by container name
un session --kill unsb-vm-12345
Equivalente API
DELETE /sessions/{id}
{"status": "terminated"}
Shells e REPLs disponíveis para sessões interativas:
Shells
bash, dash, sh, zsh, fish, ksh
tcsh, csh, elvish, xonsh, ash
REPLs
# Python
python3, bpython, ipython
# JavaScript
node
# Ruby
ruby, irb
# Other
lua, php, perl, guile, scheme
ghci, erl, iex, sbcl, clisp
r, julia, clojure
Equivalente API
GET /shells retorna a lista completa de shells disponíveis.
Congele sessões para economizar recursos enquanto preserva o estado.
Congelar Sessão
un session --freeze sess_abc123
Descongelar Sessão
un session --unfreeze sess_abc123
Equivalente API
POST /sessions/{id}/freeze
{"status": "frozen"}
POST /sessions/{id}/unfreeze
{"status": "running", "unfreeze_time_ms": 1250}
Crie snapshots pontuais do estado da sessão.
Criar Snapshot
# With name
un session --snapshot sess_abc123 --name "before-upgrade"
# Quick snapshot (auto-generated name)
un session --snapshot sess_abc123
Restaurar a partir do Snapshot
un session --restore snap_xyz789
Equivalente API
POST /sessions/{id}/snapshot
{
"snapshot_id": "snap_abc123",
"name": "before-upgrade",
"size_bytes": 52428800
}
POST /sessions/{id}/restore
{"status": "restored"}
Create long-running services with automatic HTTPS at *.on.unsandbox.com. TLS certificates are provisioned automatically via Let's Encrypt. Custom domains supported via CNAME.
Serviço Básico
# Simple web server
un service --name myapp --ports 80 --bootstrap "python -m http.server 80"
# With multiple ports
un service --name api --ports 80,443 --bootstrap "./start.sh"
Com Arquivos
# Deploy app tarball
un service --name blog --ports 8000 \
-f app.tar.gz \
--bootstrap "tar xzf app.tar.gz && cd app && ./start.sh"
Domínios Personalizados
un service --name api --ports 80 \
--domains api.example.com,www.api.example.com \
--bootstrap "./start.sh"
Nível de Serviço:
# Web service (default)
un service --name web --ports 80
# Minecraft server
un service --name mc --type minecraft --bootstrap ./setup.sh
# Game server types
un service --name game --type mumble
un service --name game --type teamspeak
un service --name game --type source
Equivalente API
POST /services
{
"service_id": "svc_abc123",
"name": "myapp",
"url": "https://myapp.on.unsandbox.com",
"status": "starting",
"ports": [80]
}
Listar Serviços
un service --list
Obter Info do Serviço
un service --info svc_abc123
Congelar/Descongelar Serviço
# Freeze (auto-unfreezes on HTTP request)
un service --freeze svc_abc123
# Manual unfreeze
un service --unfreeze svc_abc123
Bloquear/Desbloquear
# Prevent accidental deletion
un service --lock svc_abc123
# Allow deletion
un service --unlock svc_abc123
Destruir Serviço
un service --destroy svc_abc123
Endpoint de API acessado
GET /services- Listar todos os serviçosGET /services/{id}- Obter detalhes do serviçoPOST /services/{id}/freeze- Congelar serviçoPOST /services/{id}/unfreeze- Descongelar serviçoPOST /services/{id}/lock- Bloquear serviçoPOST /services/{id}/unlock- Desbloquear CofreDELETE /services/{id}- Destruir serviço
Descongelamento Automático
Quando habilitado, serviços congelados acordam automaticamente quando recebem uma requisição HTTP.
# Enable auto-unfreeze (default for new services)
un service --auto-unfreeze svc_abc123
# Disable auto-unfreeze
un service --no-auto-unfreeze svc_abc123
Exibição da Página de Congelamento
Controle o que os visitantes veem ao acessar um serviço congelado.
# Show HTML payment page (default)
un service --show-freeze-page svc_abc123
# Return JSON error instead
un service --no-show-freeze-page svc_abc123
Equivalente API
PATCH /services/{id}
# Enable auto-unfreeze
{"unfreeze_on_demand": true}
# Disable freeze page (return JSON error)
{"show_freeze_page": false}
Comportamento da Página de Congelamento
show_freeze_page: true- Exibe página HTML com opções de pagamentoshow_freeze_page: false- Retorna JSON: {"error": "service_frozen"}
Use o modo JSON para serviços API onde respostas HTML quebrariam os clientes.
Ver Logs de Bootstrap
# All logs
un service --logs svc_abc123
# Last 9000 lines
un service --tail svc_abc123
Executar Código
# Run any command
un service --execute svc_abc123 'ls -la'
# Check service status
un service --execute svc_abc123 'systemctl status myapp'
# View application logs
un service --execute svc_abc123 'journalctl -u myapp -n 50'
Exportar Script de Bootstrap
# Print to stdout
un service --dump-bootstrap svc_abc123
# Save to file
un service --dump-bootstrap svc_abc123 backup.sh
Equivalente API
GET /services/{id}/logs
{"log": "Bootstrap started...\nInstalling...\nServer listening on port 80"}
POST /services/{id}/execute
{
"stdout": "...",
"stderr": "",
"exit_code": 0
}
Armazenamento criptografado para segredos do serviço. Variáveis são injetadas quando o contêiner inicia ou descongela.
Definir Variáveis de Ambiente
# Using the API (PUT /services/{id}/env)
# Content-Type: text/plain
# Body: .env format
DATABASE_URL=postgres://user:pass@host/db
API_SECRET=abc123
DEBUG=false
Obter Status do Cofre
GET /services/{id}/env
{
"exists": true,
"variable_count": 3,
"updated_at": "2026-01-14T12:00:00Z"
}
Exportar Cofre Descriptografado
POST /services/{id}/env/export
{"env": "DATABASE_URL=postgres://...\nAPI_SECRET=abc123\nDEBUG=false"}
Excluir
DELETE /services/{id}/env
{"status": "deleted"}
Reexecutar Bootstrap
# Re-run existing bootstrap
un service --redeploy svc_abc123
# Redeploy with new bootstrap
un service --redeploy svc_abc123 --bootstrap ./new-setup.sh
Criar Snapshot do Serviço
# Standard snapshot (pauses briefly)
un service --snapshot svc_abc123 --name "stable-v1.0"
# Hot snapshot (no pause)
un service --snapshot svc_abc123 --hot
Equivalente API
POST /services/{id}/redeploy
{"state": "redeploying"}
POST /services/{id}/snapshot
{
"snapshot_id": "snap_def456",
"name": "stable-v1.0",
"size_bytes": 104857600
}
Listar Todos os Snapshots
un snapshot --list
Saída
Snapshots: 3
SNAPSHOT ID NAME SOURCE SIZE CREATED
snap_a1b2-c3d4-e5f6-g7h8 before-upgrade session 512 MB 2h ago
snap_i9j0-k1l2-m3n4-o5p6 stable-v1.0 service 1.2 GB 1d ago
snap_q7r8-s9t0-u1v2-w3x4 dev-checkpoint session 256 MB 3d ago
Obter Info do Snapshot
un snapshot --info snap_a1b2-c3d4-e5f6-g7h8
Excluir Snapshot
un snapshot --delete snap_a1b2-c3d4-e5f6-g7h8
Equivalente API
GET /snapshots
{
"snapshots": [
{
"snapshot_id": "snap_abc123",
"name": "before-upgrade",
"source_type": "session",
"size_bytes": 52428800
}
]
}
Restaurar para o Original
# Restore session from snapshot
un session --restore snap_abc123
# Restore service from snapshot
un service --restore snap_def456
Clonar para Novo Contêiner
POST /snapshots/{id}/clone
# Clone to new session
{
"type": "session",
"shell": "bash"
}
# Clone to new service
{
"type": "service",
"name": "cloned-app"
}
Resposta
Clonar para sessão:
{"session_id": "sess_new123"}
Clonar para serviço:
{
"service_id": "svc_new456",
"url": "https://cloned-app.on.unsandbox.com"
}
Bloquear/Desbloquear Snapshots
POST /snapshots/{id}/lock - Impedir exclusão
POST /snapshots/{id}/unlock - Permitir exclusão
Todas as requisições API devem ser feitas para:
https://api.unsandbox.com
A API suporta dois modos de rede:
- zerotrust (default) — Sem acesso à rede, execução totalmente isolada
- semitrusted — Acesso à rede via proxy de saída, pode acessar a internet
Os exemplos em Perl abaixo requerem as seguintes bibliotecas de terceiros:
LWP::UserAgentJSON
Certifique-se de que estes pacotes estão instalados em seu ambiente antes de executar os exemplos.
Execute código imediatamente e aguarde os resultados. Ideal para scripts rápidos e uso interativo.
Parâmetros da Requisição
| Parameter | Type | Required | Description |
|---|---|---|---|
language |
string | ✓ | Programming language |
code |
string | ✓ | Source code to execute |
env |
object | Environment variables (key-value pairs) | |
network_mode |
string | "zerotrust" or "semitrusted" | |
ttl |
integer | Timeout 1-900s (default: 60) | |
return_artifact |
boolean | Return compiled binary | |
return_wasm_artifact |
boolean | Return WebAssembly binary | |
vcpu |
integer | vCPUs 1-8 (each includes 2GB RAM) | |
input_files |
array | Arquivos para upload (veja Arquivos de Entrada) |
#!/usr/bin/env perl
# HMAC-SHA256 authenticated request to unsandbox API
use strict;
use warnings;
use HTTP::Tiny;
use JSON::PP qw(encode_json decode_json);
use Digest::SHA qw(hmac_sha256_hex);
my $public_key = $ENV{UNSANDBOX_PUBLIC_KEY} // "unsb-pk-test-0000-0000-0001";
my $secret_key = $ENV{UNSANDBOX_SECRET_KEY} // "unsb-sk-test0-vault-unlck-12345";
my $timestamp = time();
my $method = "POST";
my $path = "/execute";
my $body = encode_json({
language => 'perl',
code => 'print "Hello from unsandbox!\n";'
});
my $message = "$timestamp:$method:$path:$body";
my $signature = hmac_sha256_hex($message, $secret_key);
my $http = HTTP::Tiny->new();
my $response = $http->request('POST', "https://api.unsandbox.com$path", {
headers => {
'Content-Type' => 'application/json',
'Authorization' => "Bearer $public_key",
'X-Timestamp' => $timestamp,
'X-Signature' => $signature
},
content => $body
});
die "Request failed: $response->{status} $response->{reason}\n" unless $response->{success};
my $result = decode_json($response->{content});
print $result->{stdout};
{
"success": true,
"stdout": "Hello from unsandbox!\n",
"stderr": "",
"exit_code": 0,
"language": "python",
"job_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"network_mode": "zerotrust",
"total_time_ms": 236
}
{
"success": false,
"stdout": "",
"stderr": "SyntaxError: invalid syntax\n",
"exit_code": 1,
"language": "python",
"job_id": "b2c3d4e5-f6a7-8901-bcde-f23456789012",
"network_mode": "zerotrust",
"total_time_ms": 312
}
Submit code for execution and receive a job ID to poll for results. Best for long-running scripts or when you need to decouple submission from execution.
Parâmetros da Requisição
| Parameter | Type | Required | Description |
|---|---|---|---|
language |
string | ✓ | Programming language |
code |
string | ✓ | Source code to execute |
env |
object | Environment variables (key-value pairs) | |
network_mode |
string | "zerotrust" or "semitrusted" | |
ttl |
integer | Timeout 1-900s (default: 60) | |
return_artifact |
boolean | Return compiled binary | |
return_wasm_artifact |
boolean | Return WebAssembly binary | |
vcpu |
integer | vCPUs 1-8 (each includes 2GB RAM) | |
input_files |
array | Arquivos para upload (veja Arquivos de Entrada) |
#!/usr/bin/env perl
# HMAC-SHA256 authenticated async execution
use strict;
use warnings;
use HTTP::Tiny;
use JSON::PP qw(encode_json decode_json);
use Digest::SHA qw(hmac_sha256_hex);
my $public_key = $ENV{UNSANDBOX_PUBLIC_KEY} // "unsb-pk-test-0000-0000-0001";
my $secret_key = $ENV{UNSANDBOX_SECRET_KEY} // "unsb-sk-test0-vault-unlck-12345";
my $http = HTTP::Tiny->new();
# Helper function for HMAC signature
sub sign_request {
my ($method, $path, $body) = @_;
my $timestamp = time();
my $message = "$timestamp:$method:$path:$body";
my $signature = hmac_sha256_hex($message, $secret_key);
return ($timestamp, $signature);
}
# Submit job
my $path = "/execute/async";
my $body = encode_json({
language => 'perl',
code => 'print "Computing...\n";',
ttl => 300
});
my ($timestamp, $signature) = sign_request('POST', $path, $body);
my $response = $http->request('POST', "https://api.unsandbox.com$path", {
headers => {
'Content-Type' => 'application/json',
'Authorization' => "Bearer $public_key",
'X-Timestamp' => $timestamp,
'X-Signature' => $signature
},
content => $body
});
die "Request failed: $response->{status} $response->{reason}\n" unless $response->{success};
my $result = decode_json($response->{content});
my $job_id = $result->{job_id};
print "Job submitted: $job_id\n";
# Poll for results
while (1) {
my $job_path = "/jobs/$job_id";
my ($ts, $sig) = sign_request('GET', $job_path, '');
my $status_response = $http->get("https://api.unsandbox.com$job_path", {
headers => {
'Authorization' => "Bearer $public_key",
'X-Timestamp' => $ts,
'X-Signature' => $sig
}
});
if ($status_response->{success}) {
my $status = decode_json($status_response->{content});
my $state = $status->{status};
if ($state eq 'completed') {
print $status->{stdout};
last;
} elsif ($state eq 'timeout' || $state eq 'cancelled') {
print "Job $state\n";
last;
}
}
sleep 1;
}
{
"job_id": "ba943906-4ea6-a61c-9980-445f459368d",
"status": "pending",
"message": "Job accepted for execution"
}
Execute code with automatic language detection via shebang. Send raw code as the request body with Content-Type: text/plain.
Request
- Content-Type:
text/plain - Body: Raw code with shebang (e.g.,
#!/usr/bin/env python3)
Query Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
env |
string | URL-encoded JSON object with environment variables | |
network_mode |
string | "zerotrust" or "semitrusted" | |
ttl |
integer | Timeout 1-900s (default: 60) | |
return_artifact |
boolean | Return compiled binary | |
return_wasm_artifact |
boolean | Return WebAssembly binary |
#!/usr/bin/env perl
# HMAC-SHA256 authenticated request to run code with auto-detect
use strict;
use warnings;
use HTTP::Tiny;
use JSON::PP qw(decode_json);
use Digest::SHA qw(hmac_sha256_hex);
my $public_key = $ENV{UNSANDBOX_PUBLIC_KEY} // "unsb-pk-test-0000-0000-0001";
my $secret_key = $ENV{UNSANDBOX_SECRET_KEY} // "unsb-sk-test0-vault-unlck-12345";
my $timestamp = time();
my $method = "POST";
my $path = "/run";
my $body = qq{#!/usr/bin/env perl
print "Language auto-detected!\\n";};
my $message = "$timestamp:$method:$path:$body";
my $signature = hmac_sha256_hex($message, $secret_key);
my $http = HTTP::Tiny->new();
my $response = $http->request('POST', "https://api.unsandbox.com$path", {
headers => {
'Content-Type' => 'text/plain',
'Authorization' => "Bearer $public_key",
'X-Timestamp' => $timestamp,
'X-Signature' => $signature
},
content => $body
});
die "Request failed: $response->{status} $response->{reason}\n" unless $response->{success};
my $result = decode_json($response->{content});
print $result->{stdout};
{
"success": true,
"stdout": "Language auto-detected!\n",
"stderr": "",
"exit_code": 0,
"language": "python",
"detected_language": "python",
"job_id": "f6a7b8c9-d0e1-2345-fghi-678901234567",
"network_mode": "zerotrust"
}
Submit code with automatic language detection and receive a job ID. Combines the convenience of /run with the flexibility of async execution.
Request
- Content-Type:
text/plain - Body: Raw code with shebang (e.g.,
#!/usr/bin/env ruby)
Query Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
env |
string | URL-encoded JSON object with environment variables | |
network_mode |
string | "zerotrust" or "semitrusted" | |
ttl |
integer | Timeout 1-900s (default: 60) | |
return_artifact |
boolean | Return compiled binary | |
return_wasm_artifact |
boolean | Return WebAssembly binary |
#!/usr/bin/env perl
# HMAC-SHA256 authenticated async run with auto-detect
use strict;
use warnings;
use HTTP::Tiny;
use JSON::PP qw(encode_json decode_json);
use Digest::SHA qw(hmac_sha256_hex);
my $public_key = $ENV{UNSANDBOX_PUBLIC_KEY} // "unsb-pk-test-0000-0000-0001";
my $secret_key = $ENV{UNSANDBOX_SECRET_KEY} // "unsb-sk-test0-vault-unlck-12345";
my $http = HTTP::Tiny->new();
# Helper function for HMAC signature
sub sign_request {
my ($method, $path, $body) = @_;
my $timestamp = time();
my $message = "$timestamp:$method:$path:$body";
my $signature = hmac_sha256_hex($message, $secret_key);
return ($timestamp, $signature);
}
# Submit job
my $path = "/run/async";
my $body = qq{#!/usr/bin/env perl
print "Running async with auto-detect!\\n";};
my ($timestamp, $signature) = sign_request('POST', $path, $body);
my $response = $http->request('POST', "https://api.unsandbox.com$path", {
headers => {
'Content-Type' => 'text/plain',
'Authorization' => "Bearer $public_key",
'X-Timestamp' => $timestamp,
'X-Signature' => $signature
},
content => $body
});
die "Request failed: $response->{status} $response->{reason}\n" unless $response->{success};
my $result = decode_json($response->{content});
my $job_id = $result->{job_id};
print "Job submitted: $job_id\n";
# Poll for results
while (1) {
my $job_path = "/jobs/$job_id";
my ($ts, $sig) = sign_request('GET', $job_path, '');
my $status_response = $http->get("https://api.unsandbox.com$job_path", {
headers => {
'Authorization' => "Bearer $public_key",
'X-Timestamp' => $ts,
'X-Signature' => $sig
}
});
if ($status_response->{success}) {
my $status = decode_json($status_response->{content});
my $state = $status->{status};
if ($state eq 'completed') {
print encode_json($status);
print "\n";
last;
} elsif ($state eq 'timeout' || $state eq 'cancelled') {
print "Job $state\n";
last;
}
}
sleep 1;
}
{
"job_id": "ba943906-4ea6-a61c-9980-445f459368d",
"status": "pending",
"detected_language": "python",
"message": "Job accepted for execution"
}
Via GET /jobs/{id}
{
"job_id": "a7b8c9d0-e1f2-3456-ghij-789012345678",
"status": "completed",
"created_at": "2025-01-11T12:00:00Z",
"started_at": "2025-01-11T12:00:01Z",
"completed_at": "2025-01-11T12:00:02Z",
"success": true,
"stdout": "Running async with auto-detect!\n",
"stderr": "",
"exit_code": 0,
"language": "ruby",
"network_mode": "zerotrust",
"total_time_ms": 1234
}
Check the status and results of an asynchronous job. Poll this endpoint after submitting a job via /execute/async or /run/async.
URL Parameters
| Parameter | Type | Description |
|---|---|---|
id |
string | Job ID returned from async endpoint |
Possible Status Values
pending- Job queued, waiting to executerunning- Job currently executingcompleted- Job finished successfullyfailed- Job execution failedtimeout- Job exceeded TTL limitcancelled- Job was cancelled via DELETE
#!/usr/bin/env perl
# HMAC-SHA256 authenticated request to get job status
use strict;
use warnings;
use HTTP::Tiny;
use JSON::PP qw(decode_json encode_json);
use Digest::SHA qw(hmac_sha256_hex);
my $public_key = $ENV{UNSANDBOX_PUBLIC_KEY} // "unsb-pk-test-0000-0000-0001";
my $secret_key = $ENV{UNSANDBOX_SECRET_KEY} // "unsb-sk-test0-vault-unlck-12345";
my $job_id = "job_1234567890_abc";
my $timestamp = time();
my $method = "GET";
my $path = "/jobs/$job_id";
my $body = "";
my $message = "$timestamp:$method:$path:$body";
my $signature = hmac_sha256_hex($message, $secret_key);
my $http = HTTP::Tiny->new();
my $response = $http->get("https://api.unsandbox.com$path", {
headers => {
'Authorization' => "Bearer $public_key",
'X-Timestamp' => $timestamp,
'X-Signature' => $signature
}
});
if ($response->{success}) {
my $result = decode_json($response->{content});
print encode_json($result);
print "\n";
} elsif ($response->{status} == 404) {
print "Job not found (already completed or never existed)\n";
} else {
die "Request failed: $response->{status} $response->{reason}\n";
}
{
"job_id": "c3d4e5f6-a7b8-9012-cdef-345678901234",
"status": "completed",
"created_at": "2025-01-11T12:00:00Z",
"started_at": "2025-01-11T12:00:01Z",
"completed_at": "2025-01-11T12:00:05Z",
"success": true,
"stdout": "Hello from unsandbox!\n",
"stderr": "",
"exit_code": 0,
"language": "python",
"network_mode": "zerotrust",
"total_time_ms": 4021
}
List all active (pending or running) jobs for your API key. Useful for monitoring multiple async executions.
#!/usr/bin/env perl
# HMAC-SHA256 authenticated request to list jobs
use strict;
use warnings;
use HTTP::Tiny;
use JSON::PP qw(encode_json decode_json);
use Digest::SHA qw(hmac_sha256_hex);
my $public_key = $ENV{UNSANDBOX_PUBLIC_KEY} // "unsb-pk-test-0000-0000-0001";
my $secret_key = $ENV{UNSANDBOX_SECRET_KEY} // "unsb-sk-test0-vault-unlck-12345";
my $timestamp = time();
my $method = "GET";
my $path = "/jobs";
my $body = "";
my $message = "$timestamp:$method:$path:$body";
my $signature = hmac_sha256_hex($message, $secret_key);
my $http = HTTP::Tiny->new();
my $response = $http->get("https://api.unsandbox.com$path", {
headers => {
'Authorization' => "Bearer $public_key",
'X-Timestamp' => $timestamp,
'X-Signature' => $signature
}
});
die "Request failed: $response->{status} $response->{reason}\n" unless $response->{success};
my $result = decode_json($response->{content});
print encode_json($result);
print "\n";
[
{
"job_id": "ba943906-4ea6-a61c-9980-445f459368d",
"status": "completed",
"language": "python",
"network_mode": "zerotrust",
"created_at": "2025-01-11T12:00:00Z"
},
{
"job_id": "c1d2e3f4-5678-90ab-cdef-1234567890ab",
"status": "running",
"language": "rust",
"network_mode": "zerotrust",
"created_at": "2025-01-11T12:01:00Z"
}
]
Cancel a pending or running job. If the job is already executing, it will be terminated and partial output returned.
URL Parameters
| Parameter | Type | Description |
|---|---|---|
id |
string | Job ID to cancel |
#!/usr/bin/env perl
# HMAC-SHA256 authenticated request to delete a job
use strict;
use warnings;
use HTTP::Tiny;
use JSON::PP qw(decode_json encode_json);
use Digest::SHA qw(hmac_sha256_hex);
my $public_key = $ENV{UNSANDBOX_PUBLIC_KEY} // "unsb-pk-test-0000-0000-0001";
my $secret_key = $ENV{UNSANDBOX_SECRET_KEY} // "unsb-sk-test0-vault-unlck-12345";
my $job_id = "job_1234567890_abc";
my $timestamp = time();
my $method = "DELETE";
my $path = "/jobs/$job_id";
my $body = "";
my $message = "$timestamp:$method:$path:$body";
my $signature = hmac_sha256_hex($message, $secret_key);
my $http = HTTP::Tiny->new();
my $response = $http->delete("https://api.unsandbox.com$path", {
headers => {
'Authorization' => "Bearer $public_key",
'X-Timestamp' => $timestamp,
'X-Signature' => $signature
}
});
if ($response->{success}) {
my $result = decode_json($response->{content});
print encode_json($result);
print "\n";
} elsif ($response->{status} == 404) {
print "Job not found (already completed or never existed)\n";
} else {
die "Request failed: $response->{status} $response->{reason}\n";
}
{
"job_id": "ba943906-4ea6-a61c-9980-445f459368d",
"status": "cancelled",
"message": "Job cancelled",
"completed_at": "2025-01-11T12:00:30Z",
"success": true,
"stdout": " Compiling hello v0.1.0 (/tmp)\n",
"artifacts": []
}
Imagens são snapshots de contêiner independentes e transferíveis que sobrevivem à exclusão do contêiner. Diferente dos snapshots (vinculados ao ciclo de vida do contêiner), imagens podem ser:
- Transferido entre chaves API
- Compartilhado com usuários específicos via confiança
- Tornado público para o marketplace
- Usado para criar novos serviços
Níveis de Visibilidade
- private — Somente o proprietário pode ver/usar (padrão)
- unlisted — Oculto da listagem, mas pode ser compartilhado via confiança
- public — Visível para todos os usuários (marketplace)
Publique uma imagem a partir de um serviço ou snapshot.
Corpo da Requisição
| Parameter | Type | Required | Description |
|---|---|---|---|
source_type |
string | ✓ | "service" or "snapshot" |
source_id |
string | ✓ | ID of service or snapshot |
name |
string | User-friendly name | |
description |
string | Optional description |
Metadados de Requisição:
{
"source_type": "service",
"source_id": "unsb-service-abc123",
"name": "my-app-v1.0",
"description": "Production-ready app image"
}
Resposta
{
"id": "unsb-image-xyz789",
"name": "my-app-v1.0",
"description": "Production-ready app image",
"source_type": "service",
"source_id": "unsb-service-abc123",
"fingerprint": "abc123def456...",
"size_bytes": 524288000,
"visibility": "private",
"locked": false,
"owner_api_key": "unsb-pk-xxxx-xxxx-xxxx-xxxx",
"created_at": "2025-01-11T12:00:00Z"
}
Liste todas as imagens que pertencem à ou foram compartilhadas com sua chave API.
Endpoints Relacionados
GET /images/public— Listar imagens do marketplaceGET /images/owned— Listar apenas suas imagensGET /images/shared— Listar imagens compartilhadas com você
Resposta
{
"images": [
{
"id": "unsb-image-xyz789",
"name": "my-app-v1.0",
"fingerprint": "abc123...",
"size_bytes": 524288000,
"visibility": "private",
"locked": false,
"created_at": "2025-01-11T12:00:00Z"
}
]
}
Obtenha informações detalhadas sobre uma imagem.
Parâmetros de URL
| Parameter | Type | Description |
|---|---|---|
id |
string | Image ID (unsb-image-xxxx) |
Resposta
{
"id": "unsb-image-xyz789",
"name": "my-app-v1.0",
"description": "Production-ready app image",
"source_type": "service",
"source_id": "unsb-service-abc123",
"fingerprint": "abc123def456...",
"node": "cammy",
"size_bytes": 524288000,
"visibility": "private",
"locked": false,
"owner_api_key": "unsb-pk-xxxx-xxxx-xxxx-xxxx",
"trusted_keys": [],
"created_at": "2025-01-11T12:00:00Z"
}
Crie um novo serviço usando esta imagem como base.
Corpo da Requisição
| Parameter | Type | Required | Description |
|---|---|---|---|
name |
string | Service name | |
ports |
array | Ports to expose | |
network_mode |
string | "zerotrust" or "semitrusted" | |
bootstrap |
string | Optional bootstrap script |
Metadados de Requisição:
{
"name": "my-app-instance",
"ports": [8080],
"network_mode": "semitrusted"
}
Resposta
{
"service_id": "unsb-service-xyz789",
"name": "my-app-instance",
"source_image": "unsb-image-abc123",
"state": "starting"
}
Visibilidade e Compartilhamento
POST /images/{id}/visibility
{"visibility": "unlisted"}
Clonar Imagem
POST /images/{id}/clone
{
"name": "my-copy-of-app",
"description": "My personal copy"
}
Bloquear/Desbloquear
POST /images/{id}/lock— Impedir exclusãoPOST /images/{id}/unlock— Permitir exclusão
Excluir
DELETE /images/{id}
Conceder Acesso
POST /images/{id}/grant
{
"api_key": "unsb-pk-xxxx-xxxx-xxxx-xxxx"
}
Revogar Acesso
POST /images/{id}/revoke
{
"api_key": "unsb-pk-xxxx-xxxx-xxxx-xxxx"
}
Listar Chaves de Confiança
GET /images/{id}/trusted
{
"trusted_keys": [
"unsb-pk-aaaa-bbbb-cccc-dddd",
"unsb-pk-1111-2222-3333-4444"
]
}
Transferir Propriedade
POST /images/{id}/transfer
{
"to_api_key": "unsb-pk-xxxx-xxxx-xxxx-xxxx"
}
A API retorna códigos de status HTTP padrão junto com informações detalhadas de erro.
| Code | Status | Description |
|---|---|---|
200 |
OK | Requisição bem-sucedida (verifique o campo 'success' para o resultado da execução) |
400 |
Bad Request | Corpo da requisição inválido ou parâmetros obrigatórios ausentes |
401 |
Unauthorized | Chave API / assinatura ausente ou inválida |
403 |
Forbidden | Conta suspensa ou recurso não disponível |
404 |
Not Found | ID do job não encontrado ou expirado |
429 |
Too Many Requests | Limite de taxa excedido |
500 |
Internal Error | Erro no servidor, por favor tente novamente |
Formato de Resposta de Erro
{
"error": "Invalid API key",
"code": "INVALID_KEY",
"details": "The provided public key does not exist"
}
Os limites de taxa são aplicados por chave API e variam por plano. Veja os preços para detalhes do plano →
Limite de Requisições:
Os cabeçalhos de resposta incluem informações de limite de taxa:
X-RateLimit-Limit— requisições/minutoX-RateLimit-Remaining— Requisições restantesX-RateLimit-Reset— Timestamp Unix quando o limite é redefinido
Quando limitado pela taxa, aguarde o tempo de redefinição ou faça upgrade do seu plano para limites maiores.
Valide seu par de chaves API e recupere sua configuração incluindo limites de taxa, limites de concorrência e status de expiração.
Isso é útil para:
- Verificando se seu par de chaves é válido
- Visualizando seus limites atuais
- Construindo interfaces de gerenciamento de chaves
- Monitorando expiração da chave
Autenticação
Usa autenticação HMAC padrão (igual a todos os outros endpoints).
# Sign the request
TIMESTAMP=$(date +%s)
PUBLIC_KEY="unsb-pk-xxxx-xxxx-xxxx-xxxx"
SECRET_KEY="unsb-sk-xxxxx-xxxxx-xxxxx-xxxxx"
BODY="{}"
MESSAGE="${TIMESTAMP}:POST:/keys/validate:${BODY}"
SIGNATURE=$(echo -n "$MESSAGE" | openssl dgst -sha256 -hmac "$SECRET_KEY" | cut -d' ' -f2)
# Make the request
curl -X POST https://api.unsandbox.com/keys/validate \
-H "Authorization: Bearer $PUBLIC_KEY" \
-H "X-Timestamp: $TIMESTAMP" \
-H "X-Signature: $SIGNATURE" \
-H "Content-Type: application/json" \
-d "$BODY"
{
"valid": true,
"public_key": "unsb-pk-xxxx-xxxx-xxxx-xxxx",
"rate_per_minute": 60,
"burst": 10,
"concurrency_limit": 5,
"expires_at": "2026-12-31T23:59:59Z",
"tier": "Tier 3"
}
Retorna todas as linguagens de programação suportadas e seus aliases.
Aliases Comuns
node,js→javascriptts→typescriptlisp→commonlisp
Resposta
{
"languages": [
"python",
"javascript",
"typescript",
"ruby",
"go",
"rust",
"c",
"cpp"
],
"aliases": {
"js": "javascript",
"node": "javascript",
"ts": "typescript",
"lisp": "commonlisp"
},
"count": 42
}
Retorna todos os shells e REPLs suportados para sessões interativas, agrupados por categoria.
Categorias
- unix — bash, dash, sh, zsh, fish, ksh
- python — python, python3, ipython, bpython
- javascript — node
- ruby — ruby, irb
- lisp — scheme, guile, sbcl, clisp, clojure
- erlang — erl, iex
- data — r, julia, sqlite3
Resposta
{
"shells": [
"bash", "bpython", "clisp",
"clojure", "dash", "fish",
"ghci", "guile", "iex",
"ipython", "irb", "julia"
],
"categories": {
"unix": ["bash", "dash", "sh", "zsh", "fish"],
"python": ["python", "python3", "ipython", "bpython"],
"javascript": ["node"],
"ruby": ["ruby", "irb"],
"lisp": ["scheme", "guile", "sbcl", "clisp", "clojure"]
},
"count": 35
}
Endpoint simples de verificação de integridade. Retorna o status do serviço.
Resposta
{"status": "ok"}
Obtenha informações sobre o pool de contêineres e status do sistema.
Modos de Rede
- zerotrust_only — Only isolated containers
- semitrusted_only — Only network-enabled containers
- hybrid — Both types available
Resposta
{
"mode": "pooled",
"pool_size": 288,
"allocated": 5,
"available": 280,
"spawning": 0,
"total_containers": 285,
"network_mode": "hybrid",
"network_breakdown": {
"zerotrust": {
"allocated": 2,
"available": 140,
"total": 142
},
"semitrusted": {
"allocated": 3,
"available": 140,
"services": 1,
"total": 143
}
}
}
Obtenha o status de todos os pools de contêineres registrados (escalabilidade horizontal).
Resposta
{
"pool_count": 2,
"total_capacity": 288,
"total_allocated": 8,
"total_available": 280,
"pools": [
{
"id": "pool_manager@cammy",
"allocated": 4,
"available": 140,
"total": 144
},
{
"id": "pool_manager@ai",
"allocated": 4,
"available": 140,
"total": 144
}
]
}
Obtenha estatísticas detalhadas do sistema incluindo carga e métricas de contêineres.
Resposta
{
"containers": 285,
"load_1min": "2.15",
"load_5min": "1.89",
"load_15min": "1.45"
}
Implementações completas de SDK com autenticação HMAC em 42 linguagens. Use quando precisar de acesso programático a partir do seu próprio código.
Navegue por todas as 42 implementações de linguagens →
Padrão de Uso
# Download the SDK for your language
wget https://unsandbox.com/cli/inception/un.py
# Use it in your code
# un.py provides: execute_code(), create_session(), create_service()
# Or run it as a CLI
python un.py script.py
python un.py -s python 'print("Hello")'
Pronto para começar?
Obtenha uma chave API gratuita e comece a executar código em minutos.