Sorry for any grammatical errors, i’m not as good at english as i would like to be ^^
tl;dr
Devbox feels more like the “classic” dev workflow, you are more flexible in your tool choice and you have less overhead both mentally and resource wise.
But you should keep in mind that if you depend on non free software devbox doesn’t has pre build binaries for this, so it would be build on your machine.
DevPod
Ive worked with devcontainers with devpod for nearly a year, in a team where everyone uses a unique distro, editor and workflow.
While devbox makes it normally more easily to setup a dev environment for a new project, because everything runs on a common base, at the same time it brings a lot of overhead and complexity to this environment.
For example networking, when you develop without all the fancy stuff you probably install all your dependencies simply with your method of choice and bind the program ports on localhost, if you use devcontainer, you need to know how to expose ports in devcontainers or when you need to install a new dependency you will need to find a devcontainer feature that installs this and rebuild the container or maintain your own custom scripts. We had the problem that some of the devcontainer features we have used where no longer maintained, so it was not possible to build our dev environments.
Then is there the editor part… vscode has a really good integration with devcontainers, but with sublime text or nvim you pretty much locked out of the workflow, sure you can install nvim in the devcontainer but you need to maintain your own install scripts for setup and it takes a bit longer to rebuild the container and you have a couple of annoying graphic bugs in nvim when it is used inside a devcontainer.
Devbox
With devbox on the other hand you install your dependencies on your local machine, isolated on a directory basis. Because devbox uses nix under the hood you have access to a large number of packages and it can be used on linux, windows and macos.
Another cool thing is, that you can install packages globally. I layer only necessary system packages (docker, kvm, kitty) with rpm-ostree, all other packages (jq, nvim, fzf, starship prompt, kubectl etc.) can be installed via devbox globally. You simple need to add a line to your shell config to load the environment.
For project specific packages you run devbox init
in your git repo and install packages with devbox add
. With devbox shell
you can load the devbox environment, if you use direnv you can generate a direnv config with devbox generate direnv
and the environment gets automatically loaded if you cd into the directory. Devbox also creates a devbox.json
and devbox.lock
file to track the installed dependencies in git similar so other package managers.
Because devbox is simply a shell with paths to your dependencies you can start your editor of choice in this environment and all dependencies are available. And you have access to podman/docker without setting up docker in docker.
One thing if worth noticing, when you install non free software such as hashicorps vault, nix builds the package on your machine which can take a while depending on your hardware.
Devbox also caches your packages locally so when you setup a new project with the same dependencies it does not need to download or rebuild every package.
Example - Python
Initialize a devbox env in your git repo or project directory
devbox init
Add python and your package manager of choice
devbox add python3@3.13 poetry
load your environment
devbox shell
To automatically load the python env with the devbox shell you can add an init script to your devbox.json
devbox.json
{
"$schema": "https://raw.githubusercontent.com/jetify-com/devbox/0.12.0/.schema/devbox.schema.json",
"packages": [
"python3@3.12",
"poetry@latest"
],
"shell": {
"init_hook": "if [[ $- == *i* ]]; then poetry shell; else source $(poetry env info --path)/bin/activate; fi",
"scripts": {}
}
}
Example - direnv/global packages
Install direnv as global package
devbox global add direnv
Load the global devbox env on shell startup
~/.zshrc
eval "$(devbox global shellenv --init-hook)"
In your project directory generate a direnv config
devbox generate direnv
Now the devbox and python env should be loaded automatically when you cd into the project directory