Skip to main content

Minimal Stack Smoke Test (5 minutes)

:::tip First time with Cordum? This page is the minimal plumbing smoke test — it starts the stack and runs an empty approval workflow to confirm every service is reachable.

If you want to see governance actually catch something (a prompt-injection attempt, a policy-denied tool call, a real approval gate) start here instead: Guardrails Demo →. It's also ~5 minutes and it's the tutorial most people want to see first. :::

Time estimate: First run takes ~3 minutes (Docker image builds). Subsequent starts take ~30 seconds.

This walkthrough starts a local stack and runs a minimal approval-only workflow without any external workers.

Want the fastest path? Run:

export CORDUM_API_KEY="$(openssl rand -hex 32)"
export CORDUM_TENANT_ID=default
./tools/scripts/quickstart.sh

quickstart.sh brings up the stack and runs the approval smoke test for you.

Prerequisites

  • Docker Desktop v4+ or Docker CLI v20.10+ with Compose v2 (4GB+ RAM allocated)
  • curl
  • jq (recommended, for parsing API responses in this guide)
  • Go 1.24+ (optional, only if using cordumctl)

Step 1: Set API key + tenant

Set an API key and tenant before starting:

export CORDUM_API_KEY="$(openssl rand -hex 32)"
export CORDUM_TENANT_ID=default

Docker Compose reads .env automatically; the helper scripts read environment variables from your shell, so keep the export lines when running scripts.

Step 2: Start the stack

go run ./cmd/cordumctl up

Or:

docker compose build
docker compose up -d

Step 3: Confirm the gateway is healthy

API_KEY=${CORDUM_API_KEY:?set CORDUM_API_KEY}
TENANT_ID=${CORDUM_TENANT_ID:-default}
curl -sS http://localhost:8081/api/v1/status \
-H "X-API-Key: ${API_KEY}" \
-H "X-Tenant-ID: ${TENANT_ID}" | jq

Step 4: Create a workflow

API_KEY=${CORDUM_API_KEY:?set CORDUM_API_KEY}
ORG_ID=${CORDUM_ORG_ID:-default}
TENANT_ID=${CORDUM_TENANT_ID:-${ORG_ID}}
workflow_id=$(curl -sS -X POST http://localhost:8081/api/v1/workflows \
-H "X-API-Key: ${API_KEY}" \
-H "X-Tenant-ID: ${TENANT_ID}" \
-H "Content-Type: application/json" \
-d '{
"name": "hello-world",
"org_id": "'"${ORG_ID}"'",
"steps": {
"approve": {
"type": "approval",
"name": "Approve"
}
}
}' | jq -r '.id')

echo "workflow: ${workflow_id}"

Step 5: Start a run

run_id=$(curl -sS -X POST http://localhost:8081/api/v1/workflows/${workflow_id}/runs \
-H "X-API-Key: ${API_KEY}" \
-H "X-Tenant-ID: ${TENANT_ID}" \
-H "Content-Type: application/json" \
-d '{}' | jq -r '.run_id')

echo "run: ${run_id}"

Step 6: Approve the workflow gate job

# Find the gate job for this run in the approvals queue
job_id=$(curl -sS http://localhost:8081/api/v1/approvals \
-H "X-API-Key: ${API_KEY}" \
-H "X-Tenant-ID: ${TENANT_ID}" | \
jq -r --arg run_id "${run_id}" '.items[] | select(.workflow_run_id == $run_id) | .job.id' | head -n1)

curl -sS -X POST http://localhost:8081/api/v1/approvals/${job_id}/approve \
-H "X-API-Key: ${API_KEY}" \
-H "X-Tenant-ID: ${TENANT_ID}" \
-H "Content-Type: application/json" \
-d '{}' >/dev/null

Step 7: Check status

curl -sS http://localhost:8081/api/v1/workflow-runs/${run_id}?org_id=${ORG_ID} \
-H "X-API-Key: ${API_KEY}" \
-H "X-Tenant-ID: ${TENANT_ID}" | jq -r '.status'

Expected output: succeeded.

Step 8: Clean up

curl -sS -X DELETE http://localhost:8081/api/v1/workflow-runs/${run_id}?org_id=${ORG_ID} \
-H "X-API-Key: ${API_KEY}" \
-H "X-Tenant-ID: ${TENANT_ID}" >/dev/null
curl -sS -X DELETE http://localhost:8081/api/v1/workflows/${workflow_id}?org_id=${ORG_ID} \
-H "X-API-Key: ${API_KEY}" \
-H "X-Tenant-ID: ${TENANT_ID}" >/dev/null

Troubleshooting

IssueFix
Port already in useChange ports in .env or stop the conflicting service (lsof -i :8081 to find it)
API key missing / 401 errorsGenerate one with openssl rand -hex 32 and export as CORDUM_API_KEY, or use quickstart.sh which handles this automatically
Dashboard shows emptyNormal on a fresh install. Create a workflow first (Step 4 above) or run the smoke test
TLS / certificate errorsquickstart.sh generates self-signed certs. Your browser will show a warning -- this is expected for local dev. Delete ./certs/ and re-run to regenerate
Docker out of memoryAllocate at least 4 GB RAM to Docker Desktop

For more, see troubleshooting.md.

Next steps

  • If you did not run quickstart.sh, run the built-in smoke test: bash ./tools/scripts/platform_smoke.sh
  • Install the hello pack: examples/hello-pack + examples/hello-worker-go
  • Explore the dashboard: http://localhost:8082