← All decisions jacob@stephens.page
Decision Record

Docker over bare-metal for per-tenant isolation

ADR 0001 · Accepted ยท in production · ~262 words

Context

I needed to give each of several non-technical business managers their own AI-assisted instance of an internal app - each able to run an autonomous coding agent that could read a copy of production data and even edit code, without any tenant being able to see or damage another's data, the host, or production. Running all tenants as processes on one host (bare-metal, shared filesystem, shared DB) would have meant enforcing isolation purely through application-level conventions, which is exactly the kind of boundary an autonomous agent erodes.

Decision

Run each tenant as its own container (Docker), behind a single reverse proxy that routes by hostname. Each container gets its own named volume, its own database user scoped to its own database, its own resource limits, and a read-only mount of its agent configuration.

Consequences

When I'd revisit

If tenants needed stronger isolation than namespaces give (hostile multi-tenant, untrusted code from outside the org), I'd move to per-tenant VMs or microVMs. If they needed less (fully trusted, no agent), bare-metal with per-user accounts would be simpler.

Narrative writeup: Sandboxing AI Agents per Business Role. One of a set of architecture decision records. Source markdown lives in the infrastructure-patterns repo, which is the canonical copy.