Skip to main content

Chalk Sandbox SDK

Python SDK for the Chalk Sandbox gRPC service. Create sandboxes, execute commands, and stream output over bidirectional gRPC streams.

Contributor note: for testing deployed functions against local chalkcompute or local chalk-remote-call-python changes, see local-sdk-remote-call-testing.md.

Install

pip install grpcio protobuf

Quick start

from chalkcompute import Sandbox

# Create a sandbox from a pre-built image
sandbox = Sandbox(image="ubuntu:latest").run()

# Run a command
result = sandbox.exec("echo", "hello world")
print(result.stdout_text)  # "hello world"
print(result.exit_code)    # 0

# Clean up
sandbox.terminate()

Declarative images

Build custom container images with a fluent API instead of writing Dockerfiles. The image spec is serialized as protobuf and transmitted to the sandbox service, which builds and caches the image before starting the container.

from chalkcompute import Image, Sandbox

# Build a data-science image declaratively
img = (
    Image.debian_slim()
    .pip_install(["pandas", "numpy", "scikit-learn"])
    .run_commands(
        "apt-get update && apt-get install -y git curl",
    )
    .workdir("/home/user/app")
    .env({"PYTHONDONTWRITEBYTECODE": "1"})
)

sandbox = Sandbox(image=img).run()
result = sandbox.exec("python", "-c", "import pandas; print(pandas.__version__)")
print(result.stdout_text)

Base images

# Arbitrary base image
img = Image.base("node:25-trixie-slim")

# Convenience: python + debian slim
img = Image.debian_slim()  # python:3.14-slim-trixie

# From an existing Dockerfile (contents are inlined, so you can chain more steps)
img = Image.from_dockerfile("Dockerfile").pip_install(["extra-dep"])

Build steps

img = (
    Image.debian_slim()
    # Install Python packages
    .pip_install(["requests", "flask"])

    # Install from a requirements.txt (read locally, inlined into the spec)
    .pip_install_from_requirements("requirements.txt")

    # Run shell commands (each becomes a Docker RUN layer)
    .run_commands(
        "apt-get update && apt-get install -y git",
        "mkdir -p /app/data",
    )

    # Add local files into the image
    .add_local_file("config.yaml", "/app/config.yaml")
    .add_local_file("entrypoint.sh", "/app/entrypoint.sh", mode=0o755)
    .add_local_dir("src", "/app/src")

    # Raw Dockerfile instructions
    .dockerfile_commands(["EXPOSE 8080", "HEALTHCHECK CMD curl -f http://localhost:8080/"])

    # Image-level configuration
    .workdir("/app")
    .env({"FLASK_APP": "app:create_app"})
    .entrypoint(["/app/entrypoint.sh"])
    .cmd(["serve"])
)

Immutable composition

Each builder method returns a new Image, so intermediate images can be shared:

from chalkcompute import Image, Sandbox

base = Image.debian_slim().pip_install(["requests"])

# Two different images that share the same base
api_image = base.pip_install(["flask"]).workdir("/api")
worker_image = base.pip_install(["celery"]).workdir("/worker")

api_sandbox = Sandbox(image=api_image).run()
worker_sandbox = Sandbox(image=worker_image).run()

Connecting

from chalkcompute import SandboxClient
import grpc

# Insecure (local dev)
client = SandboxClient("localhost:50051")

# With TLS
creds = grpc.ssl_channel_credentials()
client = SandboxClient("sandbox.example.com:443", credentials=creds)

# As a context manager
with SandboxClient("localhost:50051") as client:
    ...

Rotating workload identity

The SDK can use a directly usable Chalk JWT from a rotating token file instead of a client ID and secret:

export CHALK_WEB_IDENTITY_TOKEN_FILE=/var/run/secrets/chalk/identity-token
export CHALK_API_SERVER=https://api.chalk.ai

Each SDK client caches the token for the shorter of one hour or half of the token's remaining lifetime from its exp claim, then re-reads the file on its next authenticated operation. Tokens without exp use the one-hour limit. Changing the configured file path bypasses the cache. The JWT's environment_id claim selects the environment unless CHALK_ENVIRONMENT or CHALK_ENVIRONMENT_ID is set explicitly. Queued function calls additionally require CHALK_GRPC_ENGINE, because identity JWTs do not contain engine-routing data.

Sandbox lifecycle

from chalkcompute import Sandbox, SandboxClient

# Create with resource limits
sandbox = Sandbox(
    image="ubuntu:latest",
    cpu="2",
    memory="4Gi",
    env={"DEBIAN_FRONTEND": "noninteractive"},
).run()

client = SandboxClient.from_env()

# List all sandboxes
for info in client.list():
    print(f"{info.id} {info.status} {info.name}")

# Get a handle to an existing sandbox by ID
sandbox = client.get(id="550e8400-e29b-41d4-a716-446655440000")

# Fetch info from server
info = sandbox.refresh()  # force re-fetch
print(info.status)

# Terminate
sandbox.terminate()
sandbox.terminate(grace_period_seconds=30)

Executing commands

Run and wait

result = sandbox.exec("ls", "-la", "/tmp")
for line in result.stdout:
    print(line)
for line in result.stderr:
    print(f"ERR: {line}")
print(f"exit code: {result.exit_code}")

# Or get the full text at once
print(result.stdout_text)
print(result.stderr_text)

Stream output in real time

for event in sandbox.exec_stream("make", "build", workdir="/app"):
    if event.stdout:
        print(event.stdout, end="")
    if event.stderr:
        print(event.stderr, end="", file=sys.stderr)
    if event.is_exited:
        print(f"\nDone: exit code {event.exit_code}")

Interactive processes (stdin + signals)

process = sandbox.exec_start("bash")

process.write_stdin("echo hello\n")
process.write_stdin("exit\n")
process.close_stdin()

for event in process.output():
    if event.stdout:
        print(event.stdout, end="")

Send signals to running processes:

import signal

process = sandbox.exec_start("sleep", "300")
process.send_signal(signal.SIGTERM)
result = process.wait()

Options

All exec methods accept the same keyword arguments:

result = sandbox.exec(
    "python", "train.py",
    workdir="/app",                     # working directory
    timeout_secs=3600,                  # kill after 1 hour
    env={"CUDA_VISIBLE_DEVICES": "0"},  # environment variables
)

Examples

Clone a GitHub repo into a sandbox

from chalkcompute import Sandbox

sandbox = Sandbox(image="ubuntu:latest").run()

# Install git
sandbox.exec("apt-get", "update")
sandbox.exec("apt-get", "install", "-y", "git")

# Clone
result = sandbox.exec(
    "git", "clone", "https://github.com/chalk-ai/chalk.git", "/workspace/chalk"
)
if result.exit_code != 0:
    print(f"Clone failed: {result.stderr_text}")
else:
    # List what we got
    result = sandbox.exec("ls", "-la", "/workspace/chalk")
    for line in result.stdout:
        print(line)

Spawn an OpenCode agent in a sandbox

OpenCode is a terminal-based AI coding agent. You can run it inside a sandbox to give it an isolated environment to work in.

from chalkcompute import Sandbox

sandbox = Sandbox(
    image="ubuntu:latest",
    cpu="2",
    memory="4Gi",
    env={
        "ANTHROPIC_API_KEY": "sk-ant-...",
    },
).run()

# Install dependencies
sandbox.exec("apt-get", "update")
sandbox.exec("apt-get", "install", "-y", "git", "curl", "build-essential")

# Install Go (opencode is a Go binary)
sandbox.exec("bash", "-c", "curl -fsSL https://go.dev/dl/go1.26.3.linux-amd64.tar.gz | tar -C /usr/local -xz")
sandbox.exec("bash", "-c", "echo 'export PATH=$PATH:/usr/local/go/bin:/root/go/bin' >> /root/.bashrc")

# Install opencode
sandbox.exec("bash", "-c", "export PATH=$PATH:/usr/local/go/bin:/root/go/bin && go install github.com/opencode-ai/opencode@latest")

# Clone a repo to work on
sandbox.exec("git", "clone", "https://github.com/your-org/your-repo.git", "/workspace/repo")

# Run opencode non-interactively with a prompt
result = sandbox.exec(
    "bash", "-c",
    "export PATH=$PATH:/usr/local/go/bin:/root/go/bin && cd /workspace/repo && opencode -p 'fix the failing tests in pkg/auth'",
    timeout_secs=600,
)
print(result.stdout_text)

# Or run it interactively and feed it commands
process = sandbox.exec_start(
    "bash", "-c",
    "export PATH=$PATH:/usr/local/go/bin:/root/go/bin && cd /workspace/repo && opencode",
)

# Stream its output
for event in process.output():
    if event.stdout:
        print(event.stdout, end="")
    if event.stderr:
        print(event.stderr, end="", file=sys.stderr)
    if event.is_exited:
        break

Long-running build with real-time output

from chalkcompute import Sandbox

sandbox = Sandbox(image="node:25-trixie-slim").run()

sandbox.exec("git", "clone", "https://github.com/your-org/frontend.git", "/app")
sandbox.exec("npm", "install", workdir="/app")

# Stream the build output as it happens
for event in sandbox.exec_stream("npm", "run", "build", workdir="/app"):
    if event.stdout:
        print(event.stdout, end="")
    if event.stderr:
        print(event.stderr, end="", file=sys.stderr)
    if event.is_exited and event.exit_code != 0:
        print(f"Build failed with exit code {event.exit_code}")

sandbox.terminate()

CLI tools

sandbox_exec.py - Run a command

python sandbox_exec.py --target localhost:50051 --sandbox-id <id> --exec "ls -la"

sandbox_stdout.py - Interactive shell

echo "echo hello" | python sandbox_stdout.py --target localhost:50051 --sandbox-id <id> --exec "bash"

Regenerating proto stubs

If the proto definition changes, regenerate the Python stubs:

pip install grpcio-tools
./generate.sh

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

chalkcompute-2.3.8.tar.gz (281.1 kB view details)

Uploaded Source

Built Distributions

If you're not sure about the file name format, learn more about wheel file names.

chalkcompute-2.3.8-cp314-cp314-manylinux_2_28_x86_64.whl (5.0 MB view details)

Uploaded CPython 3.14manylinux: glibc 2.28+ x86-64

chalkcompute-2.3.8-cp314-cp314-macosx_11_0_arm64.whl (4.5 MB view details)

Uploaded CPython 3.14macOS 11.0+ ARM64

chalkcompute-2.3.8-cp313-cp313-manylinux_2_28_x86_64.whl (5.0 MB view details)

Uploaded CPython 3.13manylinux: glibc 2.28+ x86-64

chalkcompute-2.3.8-cp313-cp313-macosx_11_0_arm64.whl (4.5 MB view details)

Uploaded CPython 3.13macOS 11.0+ ARM64

chalkcompute-2.3.8-cp312-cp312-manylinux_2_28_x86_64.whl (5.0 MB view details)

Uploaded CPython 3.12manylinux: glibc 2.28+ x86-64

chalkcompute-2.3.8-cp312-cp312-macosx_11_0_arm64.whl (4.5 MB view details)

Uploaded CPython 3.12macOS 11.0+ ARM64

chalkcompute-2.3.8-cp311-cp311-manylinux_2_28_x86_64.whl (5.0 MB view details)

Uploaded CPython 3.11manylinux: glibc 2.28+ x86-64

chalkcompute-2.3.8-cp311-cp311-macosx_11_0_arm64.whl (4.5 MB view details)

Uploaded CPython 3.11macOS 11.0+ ARM64

File details

Details for the file chalkcompute-2.3.8.tar.gz.

File metadata

  • Download URL: chalkcompute-2.3.8.tar.gz
  • Upload date:
  • Size: 281.1 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for chalkcompute-2.3.8.tar.gz
Algorithm Hash digest
SHA256 182463965d2500c6c6f1a56b85cf40d215f59e768f76171cad67ac3d7636149b
MD5 94d72149312316e5ab750b391ff8a440
BLAKE2b-256 7b630c170a31e62cdca485ee1d920ebe1c89d536914d08bf07fcff3f1f02e2bd

See more details on using hashes here.

Provenance

The following attestation bundles were made for chalkcompute-2.3.8.tar.gz:

Publisher: release.yml on chalk-ai/chalk-sandbox-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file chalkcompute-2.3.8-cp314-cp314-manylinux_2_28_x86_64.whl.

File metadata

File hashes

Hashes for chalkcompute-2.3.8-cp314-cp314-manylinux_2_28_x86_64.whl
Algorithm Hash digest
SHA256 932cf6ea18b6d7879b65b620d41f1c2196666f8dfca8ad36d0778423bd86fdbe
MD5 f1052fd32628fb4b9883ca18db02f454
BLAKE2b-256 a5aa76e9ad86e108aa2ac32815e12a111daa788a778b6ce92fd12bc09e1ffc17

See more details on using hashes here.

Provenance

The following attestation bundles were made for chalkcompute-2.3.8-cp314-cp314-manylinux_2_28_x86_64.whl:

Publisher: release.yml on chalk-ai/chalk-sandbox-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file chalkcompute-2.3.8-cp314-cp314-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for chalkcompute-2.3.8-cp314-cp314-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 ef4ef51c7423e9c86bb2123a1fb808ccc560f918604abeff06c7ffaf6bca71b5
MD5 9381eb7850848e3e29c88c1ead50dcd0
BLAKE2b-256 c22a3250d7671484d1d78a630c3c0b7a70640dbf8d320754697d84aff49d10ee

See more details on using hashes here.

Provenance

The following attestation bundles were made for chalkcompute-2.3.8-cp314-cp314-macosx_11_0_arm64.whl:

Publisher: release.yml on chalk-ai/chalk-sandbox-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file chalkcompute-2.3.8-cp313-cp313-manylinux_2_28_x86_64.whl.

File metadata

File hashes

Hashes for chalkcompute-2.3.8-cp313-cp313-manylinux_2_28_x86_64.whl
Algorithm Hash digest
SHA256 dd3ead6bb28af150d81aec309d250144dbfa39f39c1e042c91d268c8c64fa91e
MD5 aa77fae5c81e3094c1178d9e27d34d9d
BLAKE2b-256 6091caffee100672a880ee69f95f27b3507fa824c51fd423ce12f609d06319a9

See more details on using hashes here.

Provenance

The following attestation bundles were made for chalkcompute-2.3.8-cp313-cp313-manylinux_2_28_x86_64.whl:

Publisher: release.yml on chalk-ai/chalk-sandbox-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file chalkcompute-2.3.8-cp313-cp313-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for chalkcompute-2.3.8-cp313-cp313-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 36f879a427d80b4755053e4783a9e0f9d0062625be12a054f205848e55d763cc
MD5 64d3e01daffcd578c687dc1261290b0f
BLAKE2b-256 e3e4a76a2e199214acbb2ba62d403d1c7282e533a8c3790ee8d34bf2c854f90b

See more details on using hashes here.

Provenance

The following attestation bundles were made for chalkcompute-2.3.8-cp313-cp313-macosx_11_0_arm64.whl:

Publisher: release.yml on chalk-ai/chalk-sandbox-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file chalkcompute-2.3.8-cp312-cp312-manylinux_2_28_x86_64.whl.

File metadata

File hashes

Hashes for chalkcompute-2.3.8-cp312-cp312-manylinux_2_28_x86_64.whl
Algorithm Hash digest
SHA256 50f9f0e58a7e61d358404ea75ecbd120cccdb8341354f3d17bb7d906c013de11
MD5 ed2b1d8ff58a6491e51604f57f5176c3
BLAKE2b-256 b8e6c9372e35f284775c7ba1b0639ae866cab10d849d9c0a7e152ac14071db24

See more details on using hashes here.

Provenance

The following attestation bundles were made for chalkcompute-2.3.8-cp312-cp312-manylinux_2_28_x86_64.whl:

Publisher: release.yml on chalk-ai/chalk-sandbox-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file chalkcompute-2.3.8-cp312-cp312-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for chalkcompute-2.3.8-cp312-cp312-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 a6505ccbf2762863dee2eb15cde0d522ab3929762333aa412068421740468f08
MD5 2fb10433f8f660033edba6aa790ff86e
BLAKE2b-256 1cdeadcd75a8dfe047050e6351cd1ab69ab859f325e201c0b9ee04e236ff2ad4

See more details on using hashes here.

Provenance

The following attestation bundles were made for chalkcompute-2.3.8-cp312-cp312-macosx_11_0_arm64.whl:

Publisher: release.yml on chalk-ai/chalk-sandbox-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file chalkcompute-2.3.8-cp311-cp311-manylinux_2_28_x86_64.whl.

File metadata

File hashes

Hashes for chalkcompute-2.3.8-cp311-cp311-manylinux_2_28_x86_64.whl
Algorithm Hash digest
SHA256 eef9f8d04f34448ec914073b6744f7b4075876d0477285f8e9d0954751c9c4a4
MD5 6119ae4a9935694adf2262e5faaea405
BLAKE2b-256 96fa8872fcbe14303ca9b1a0a9e01e61ea1d1c89a0b04b7da70c7641d3c8a6bb

See more details on using hashes here.

Provenance

The following attestation bundles were made for chalkcompute-2.3.8-cp311-cp311-manylinux_2_28_x86_64.whl:

Publisher: release.yml on chalk-ai/chalk-sandbox-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file chalkcompute-2.3.8-cp311-cp311-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for chalkcompute-2.3.8-cp311-cp311-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 04f1acf7242cba19119e595ed98f9f9bfb8577e0b7e33e7edddf1b23f0627064
MD5 c25c6fc608fa369e071b953f4df270a1
BLAKE2b-256 839dcbff843586529d961e7bc5b546d23acb240fa9a151ceafc44629e1c0ec52

See more details on using hashes here.

Provenance

The following attestation bundles were made for chalkcompute-2.3.8-cp311-cp311-macosx_11_0_arm64.whl:

Publisher: release.yml on chalk-ai/chalk-sandbox-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Release history Release notifications | RSS feed

2.11.8

13 files

2.11.7

13 files

2.11.6

13 files

2.11.5

13 files

2.11.4

13 files

2.11.3

13 files

2.11.2

13 files

2.11.1

13 files

2.9.8

13 files

2.9.7

13 files

2.9.6

13 files

2.9.5

13 files

2.9.4

13 files

2.9.3

13 files

2.9.2

13 files

2.9.1

13 files

2.9.0

13 files

2.8.1

13 files

2.8.0

13 files

2.7.0

13 files

2.6.2

13 files

2.6.1

9 files

2.5.3

9 files

2.5.2

9 files

2.5.1

9 files

2.5.0

9 files

2.4.1

9 files

2.3.9

9 files

This release

2.3.8 This release

9 files

2.3.7

9 files

2.3.6

9 files

2.3.5

9 files

2.3.4

9 files

2.3.3

9 files

2.3.2

9 files

2.3.1

9 files

2.3.0

9 files

2.2.0

9 files

2.1.8

9 files

2.1.3

9 files

2.1.2

9 files

2.1.1

9 files

2.1.0

9 files

2.0.1

9 files

2.0.0

9 files

1.5.17

9 files

1.5.16

9 files

1.5.15

9 files

1.5.14

9 files

1.5.13

9 files

1.5.12

9 files

1.5.11

9 files

1.5.10

9 files

1.5.9

5 files

1.5.6

5 files

1.5.5

2 files

1.5.3

2 files

1.5.2

2 files

1.5.1

2 files

1.5.0

2 files

1.4.2

2 files

1.4.1

2 files

1.4.0

2 files

1.3.0

2 files

1.2.0

2 files

1.1.1

2 files

1.1.0

2 files

1.0.0

2 files

0.1.1

2 files

0.1.0

2 files

0.0.0

9 files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page