A collection of reusable Nix development environments that I use on NixOS.
The goal of this repository is to keep my development shells in one place, making it easy to start a project with the tools I need without installing development dependencies globally.
.
├── core/
│ └── shell.nix
├── go/
│ └── shell.nix
├── pi/
│ └── shell.nix
├── Makefile
├── README.md
└── shell.nix
Each directory contains a development shell for a particular language, toolchain, or use case.
The root shell.nix is used to maintain this repository itself and provides
the formatting and linting tools used by the Makefile.
Some development environments require system-level NixOS configuration that
cannot be provided by a shell.nix alone.
To use Docker, enable the Docker service and add your user to the docker
group in /etc/nixos/configuration.nix:
virtualisation.docker.enable = true;
users.users.<username>.extraGroups = [
"docker"
];If you already define extraGroups for your user, simply add "docker" to
the existing list:
users.users.<username> = {
isNormalUser = true;
extraGroups = [
"networkmanager"
"wheel"
"docker"
];
};Apply the configuration:
sudo nixos-rebuild switchYou may need to log out and back in for the new group membership to take effect.
Verify Docker is working:
docker run --rm hello-worldSome development tools distribute pre-compiled dynamically linked binaries that may not run directly on NixOS.
Enable nix-ld in /etc/nixos/configuration.nix:
programs.nix-ld.enable = true;Then apply the configuration:
sudo nixos-rebuild switchThis can be useful when using externally distributed binaries, including tools installed outside of Nix.
uvitself does not requirenix-ldwhen installed through Nix. This configuration is primarily useful when running pre-compiled binaries that expect a conventional Linux dynamic linker.
General-purpose development environment containing commonly used tools such as git, neovim, jq, fastfetch, and lolcat.
nix-shell core/shell.nixGo development environment containing the Go toolchain, gopls, and
additional Go tools.
nix-shell go/shell.nixThe shell also creates project-local Go directories for development caches and installed binaries.
Node.js environment for running the Pi coding agent.
nix-shell pi/shell.nixThe environment keeps globally installed npm packages local to the project instead of installing them into the system.
Clone the repository:
git clone <repository-url>
cd <repository-name>Enter a development shell directly:
nix-shell go/shell.nixOr enter its directory first:
cd go
nix-shellCopy the desired shell.nix into your project:
cp /path/to/nix-shells/go/shell.nix ~/projects/my-project/shell.nix
cd ~/projects/my-project
nix-shellThe project then has its own development environment that can be modified independently.
The root shell.nix provides all tools required to maintain the Nix files in
this repository.
Enter the development environment:
nix-shellFormat all Nix files and clean whitespace:
make fmtmake fmt:
- normalizes excessive indentation
- removes trailing whitespace
- formats Nix code with
nixfmt
Run all checks:
make checkOr run them individually:
make fmt-check
make lint
make deadnix
make whitespaceThe repository uses:
nixfmt— Nix code formattingstatix— Nix linting and anti-pattern detectiondeadnix— detection of unused Nix codegit diff --check— whitespace error detection
Run:
make helpto see all available Makefile targets.
A typical workflow when changing or adding a development shell is:
nix-shell
# Make changes...
make fmt
make check
git diff
git add .
git commitBefore committing, make check should complete without errors.
Create a directory for the new environment:
rust/
└── shell.nix
A minimal shell looks like:
{ pkgs ? import <nixpkgs> { } }:
pkgs.mkShell {
packages = with pkgs; [
# Development tools go here
];
shellHook = ''
echo "Development shell ready!"
'';
}Then verify it:
nix-shell rust/shell.nixand format/check the repository:
make fmt
make checkOn NixOS, I prefer keeping development dependencies out of the global system configuration whenever possible.
Development shells provide:
- isolated development environments
- reproducible toolchains
- fewer globally installed packages
- easy switching between development stacks
- reusable starting points for new projects
Instead of remembering which packages are required whenever I start a new project, I can reuse one of the environments from this repository.
These shells are primarily maintained for my own development workflow on NixOS.
They may also work on other systems running Nix, but compatibility outside my setup is not guaranteed.
Feel free to use, modify, or adapt them for your own projects.
