A service for running containerized workloads on Docker or Kubernetes, in two shapes:
- Jobs — run a container to completion, with file artifacts in and out, and CloudEvents callbacks reporting progress and results.
- Deployments — run a container as a long-lived HTTP service behind a gateway, with immutable revisions, traffic splitting, concurrency-based autoscaling, scale-to-zero, and optional warm-pool pod acquisition.
The same API works against both backends (ORCHESTRATOR_BACKEND=docker|kubernetes): Docker for development, Kubernetes for production. The backend is the source of truth — the services are stateless, survive restarts, and any replica can serve any request.
The compose file runs the all-in-one orchestrator image — every control plane in one container — against your local Docker daemon:
docker compose up -d
# Run a job to completion
curl -X POST http://localhost:8080/v1/jobs \
-H "Content-Type: application/json" \
-d '{"id": "hello", "image": "alpine:latest", "command": "echo hello world"}'
curl http://localhost:8080/v1/jobs/hello
# {"id":"hello","status":"completed","exitCode":0}
# Deploy an HTTP service
curl -X POST http://localhost:8080/v1/deployments \
-H "Content-Type: application/json" \
-d '{"id": "web", "image": "traefik/whoami", "port": 80}'
# 201 {"id":"web","status":"pending","url":"http://web.localhost/", ...}
# Once ready, it serves on its host via the data port:
curl -H "Host: web.localhost" http://localhost:8081/Production is the other shape: the Helm chart runs each plane as its own image and Deployment, so they scale and fail independently. The monolith is for compose and local development.
(Contributors can also run the jobs service from source with hot reload: task dev.)
| Guide | What it covers |
|---|---|
| Jobs | Run-to-completion workloads: the jobs API, artifacts (download, write, archive, mount, …), dependency ordering |
| Deployments | Long-lived HTTP services: revisions, canary traffic, autoscaling, scale-to-zero, async requests |
| Pools | Pre-warmed capacity for deployment revisions and its burst policy |
| Sandboxes | Live workspaces: the sandbox API, the in-sandbox exec/files contract, extra ports, sandbox pools, isolation tiers |
| Callbacks | CloudEvents delivery: every event type, payload schemas, HMAC signature verification |
| Operations | Deploying the orchestrator: Helm install, prerequisites, configuration reference, hardening |
| Observability | Metrics, logging, and tracing |
| Development | Building, testing, and the local dev loop |
Proposals for work not yet built live in docs/design/.
All request and response bodies are JSON; every error is {"error": "..."} with a meaningful status code. Requests with unknown fields are rejected with 400 naming the field — a typo never silently deploys defaults. When an API key is configured, send Authorization: Bearer <key>.
POST /v1/jobs # 202 — run a container to completion
GET /v1/jobs/{id} # status + exit code
DELETE /v1/jobs/{id} # cancel
POST /v1/deployments # 201 created / 200 updated (declarative apply)
GET /v1/deployments/{id} # status, revisions, traffic, mode
POST /v1/deployments/{id}/traffic # canary / rollback; empty targets = back to auto
DELETE /v1/deployments/{id} # tear down
A Helm chart lives at charts/orchestrator/ — see the operations guide for prerequisites (K8s 1.29+; Gateway API for deployments) and the full configuration reference.
helm install orchestrator oci://ghcr.io/open-runtimes/charts/orchestrator \
--version <X.Y.Z> \
--namespace orchestrator --create-namespace \
--set jobs.enabled=true --set deployments.enabled=true \
--set deployments.activator.enabled=trueLocal dev loop (requires kind + tilt):
task tools # install pinned ko, golangci-lint, helm into ./bin/
task kind:up # create the kind-orchestrator-dev cluster
task dev:k8s # tilt up: live-reload the chart on source changeMIT