How CubeAPI Works in CubeSandbox: Architecture and Implementation Guide
CubeAPI is a stateless, E2B-compatible REST API server that exposes sandbox lifecycle operations on port 3000, forwarding validated HTTP requests to the Cubelet daemon via Unix socket RPC.
CubeAPI serves as the primary control plane interface in the TencentCloud/CubeSandbox repository, translating external HTTP calls into internal sandbox management commands. This lightweight Go binary (cube-api) implements the E2B API contract, enabling developers to create, monitor, and terminate isolated execution environments through standardized REST endpoints.
Architecture Overview
CubeAPI operates as a stateless façade that bridges client requests and the host runtime. The system comprises four principal components working in concert:
- Cube API Server (
cube-api): Exposes public REST endpoints such as/v1/sandboxesand/v1/sandboxes/:idon port 3000. It handles optional authentication callbacks and domain injection before forwarding commands to the host. - Cubelet (
cubelet): The sandbox runtime daemon that listens on/var/run/cubelet.sock. It performs heavy-lifting operations including namespace creation, storage provisioning, and container launch. - Network Agent: Manages TAP device allocation and IP assignment for sandbox networking when Cubelet requests network interfaces.
- Auth Callback (optional): External HTTP endpoint that receives credential headers (
Authorization,X-Auth-Token) to determine request validity.
Request Flow: Creating a Sandbox
Understanding how CubeAPI processes requests requires examining the complete lifecycle of a sandbox creation operation. The flow follows a strict validation-to-execution pipeline:
1. Client Request and Authentication
The client initiates communication via standard HTTP POST to the CubeAPI endpoint:
POST /v1/sandboxes
Content-Type: application/json
{
"template_id": "nodejs-18",
"env": {"PORT":"8080"},
"sandbox_name": "my-app"
}
When launched with --auth-callback-url, CubeAPI forwards the request's authentication headers to the specified external service via POST. The callback must return HTTP 200 for allowed requests or 403 for rejections, optionally including a JSON body with {"allowed": true} or {"allowed": false, "message": "invalid token"}.
2. Internal RPC Translation
Upon validation, CubeAPI marshals the request into the internal protobuf message cubebox.RunCubeSandboxRequest. This binary payload includes the sandbox domain (if configured via --sandbox-domain) and networking hints. The API server transmits this message over the Unix socket /var/run/cubelet.sock to the Cubelet process.
3. Sandbox Instantiation
Cubelet receives the RPC and executes the physical sandbox creation:
- Provisions storage using the copy-on-write (Cow) engine
- Creates the sandbox VM and namespaces
- Requests TAP device allocation from the Network Agent
- Launches user containers inside the isolated environment
Cubelet then returns a RunCubeSandboxResponse containing the sandbox ID, allocated IP address, exposed ports, and endpoint URLs.
4. Response Serialization
CubeAPI translates the protobuf response into JSON format and returns it to the client:
{
"id": "sandbox-uuid",
"status": "running",
"ip": "10.0.0.5",
"ports": {"8080": "8080"}
}
All subsequent operations—listing sandboxes, retrieving logs, creating snapshots, or killing instances—follow this identical pattern: HTTP request, optional auth validation, RPC translation, Cubelet execution, and JSON response.
Configuration Options
CubeAPI supports several runtime flags that modify its behavior:
Authentication Callback
cube-api \
--listen 0.0.0.0:3000 \
--auth-callback-url https://my-auth-service/verify
Custom Sandbox Domain
Setting --sandbox-domain myapp.example.com injects the domain into sandbox metadata. This enables code running inside the sandbox to resolve the host via the SANDBOX_DOMAIN environment variable or injected DNS records.
Health Monitoring
The server exposes a /healthz endpoint at the address specified by --health-addr, used by systemd scripts for service health checks.
Logging
Operational logs write to /data/log/CubeAPI/ with daily rotation, configured through the systemd unit cube-sandbox-cube-api.service.
Implementation Examples
Go Client Implementation
The repository provides a reference implementation in CubeAPI/examples/go/client.go demonstrating create and kill operations:
package main
import (
"bytes"
"encoding/json"
"fmt"
"net/http"
)
type CreateReq struct {
TemplateID string `json:"template_id"`
Env map[string]string `json:"env,omitempty"`
}
type CreateResp struct {
ID string `json:"id"`
Status string `json:"status"`
}
func main() {
apiURL := "http://localhost:3000"
// Create sandbox
payload := CreateReq{
TemplateID: "nodejs-18",
Env: map[string]string{"PORT": "8080"},
}
body, _ := json.Marshal(payload)
resp, err := http.Post(apiURL+"/v1/sandboxes", "application/json", bytes.NewReader(body))
if err != nil {
panic(err)
}
defer resp.Body.Close()
var created CreateResp
json.NewDecoder(resp.Body).Decode(&created)
fmt.Printf("Created sandbox %s (status=%s)\n", created.ID, created.Status)
// Kill sandbox
req, _ := http.NewRequest(http.MethodDelete, fmt.Sprintf("%s/v1/sandboxes/%s", apiURL, created.ID), nil)
http.DefaultClient.Do(req)
fmt.Println("Sandbox terminated")
}
Command Line Usage
Raw HTTP interaction via curl follows the E2B-compatible API contract:
# Create a sandbox
curl -X POST http://localhost:3000/v1/sandboxes \
-H "Content-Type: application/json" \
-d '{"template_id":"python-3.10","env":{"PORT":"8000"}}'
# List active sandboxes
curl http://localhost:3000/v1/sandboxes
# Terminate specific instance
curl -X DELETE http://localhost:3000/v1/sandboxes/<sandbox-id>
Summary
- CubeAPI is a stateless Go server providing E2B-compatible REST endpoints on port 3000 for the CubeSandbox platform.
- It communicates with the host runtime via Unix socket RPC (
/var/run/cubelet.sock) using protobuf messages such ascubebox.RunCubeSandboxRequest. - Optional authentication callbacks delegate credential validation to external services before processing requests.
- The sandbox domain feature (
--sandbox-domain) enables custom DNS resolution for code running inside sandboxes. - All sandbox lifecycle operations (create, kill, list, logs) translate HTTP requests into Cubelet commands with JSON responses.
- Reference implementations are available in
CubeAPI/examples/go/client.go, with systemd service management documented for production deployment.
Frequently Asked Questions
What is the default port for CubeAPI?
CubeAPI listens on port 3000 by default. You can configure the binding address using the --listen flag when starting the cube-api binary.
How does CubeAPI handle authentication?
CubeAPI supports optional external authentication via the --auth-callback-url flag. When configured, the server forwards incoming request headers (including Authorization or X-Auth-Token) to the specified callback URL. The callback service must return HTTP 200 to allow the request or 403 to reject it.
Where does CubeAPI store its logs?
According to the source configuration, CubeAPI writes logs to /data/log/CubeAPI/ with daily rotation. The systemd service file cube-sandbox-cube-api.service manages both the log path and the health check polling against the /healthz endpoint.
Can I use CubeAPI without the E2B SDK?
Yes. CubeAPI implements the E2B API contract directly, allowing you to interact with it using standard HTTP clients like curl or custom code. The CubeAPI/examples/go/client.go file demonstrates a minimal implementation that requires only the standard net/http package and proper JSON marshaling of request payloads.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →