Dev Containers & Reproducible Dev Environments

Standardizing development environments with Dev Containers spec, Devbox, Nix shells, and cloud IDEs to eliminate "works on my machine" problems.

Overview

Ending "it works on my machine"

"It works on my machine" is one of the most persistent problems in software development. Reproducible development environments close the gap between a developer's local setup and CI or production. That removes whole categories of bugs that exist only in specific configurations.

Three approaches

  • Dev Containers — Open JSON spec (from Microsoft, used by VS Code, GitHub Codespaces, JetBrains); devcontainer.json at the repo root declares the base image, extensions, port forwarding and lifecycle scripts — Everyone gets the same runtime, tools and extensions in seconds
  • Devbox (Jetify, built on Nix) — devbox.json lists packages (Node 20, Python 3.12, go 1.22, postgresql 15); devbox shell drops you into exactly those versions — No Docker, no VM, instant activation; strong for polyglot repos and systems work where container overhead is unwanted
  • Cloud IDEs (GitHub Codespaces, Gitpod, Daytona, Google Cloud Workstations) — The whole environment runs in the cloud — Zero to running code in under 60 seconds

Nix: the engine underneath

Nix, the package manager and functional language, is what makes Nix shells and Devbox possible. It gives bit-for-bit reproducibility.

> [!TIP] Two projects using different versions of the same library coexist in the Nix store without conflict.

Cloud IDE trade-offs

  • Onboarding from zero to running code in under 60 seconds — Per-user cloud compute billing
  • No local compute requirements — Latency for developers used to local IDEs
  • Enterprise security: code never leaves the cloud
  • Instant branch switching without a local checkout

Why platform teams care

  • Onboarding time — From days to hours
  • Cross-platform bugs (Windows vs macOS vs Linux) — Eliminated
  • Contributing to any service — No manual installation of language runtimes and toolchains

Key concepts

Dev Containers spec
Open standard for defining development environments as Docker containers via devcontainer.json. Supported by VS Code, GitHub Codespaces, JetBrains, and Daytona. Specifies image, extensions, ports, and lifecycle scripts.
Devbox
CLI tool by Jetify that creates reproducible development shells using Nix under the hood. devcontainer.json equivalent is devbox.json — lists packages by name and version. No Docker required for the dev shell.
Nix flakes
Reproducible, composable Nix expressions with a lock file (flake.lock) that pins every dependency's exact cryptographic hash. The foundation of bit-for-bit reproducible builds and environments.
GitHub Codespaces
Cloud-hosted VS Code development environments running on Azure VMs. Opens any repo as a dev container in <60 seconds. Billed per compute-hour; pre-builds speed up launch time.
Gitpod
Cloud development environment platform (open-source self-hostable). Defines environments in .gitpod.yml. Supports VS Code, JetBrains Gateway, and browser-based Theia IDE.
Pre-build
A pre-computed dev container image that runs setup steps (npm install, go build, etc.) ahead of time so developers start with a warm environment. GitHub Codespaces prebuilds are triggered on push to main branches.

When to use it

  • Platform engineering initiative to standardize developer environments across a polyglot engineering org
  • Interview questions about reducing "works on my machine" problems at scale
  • Evaluating GitHub Codespaces vs local dev containers vs Devbox for your team's needs
  • Designing a fast onboarding experience for a complex microservices repository
  • Ensuring CI environment parity with local development to eliminate environment-specific bugs

Interview questions

  • How do you standardize development environments across a 500-person engineering org?

Sign up free to read the full topic

More DevOps topics

Start free on Cariara · Coding problems · System design studio