Getting Started
Start from a Python project directory. uv still owns Python package metadata, dependency groups, lockfiles, and virtualenv sync.
What to expect
robo shellis the main command. It prepares the runtime, then opens your normal interactive shell with a[robo]prompt prefix.- On first use,
robo shellmay createflake.nix,robo.nix, and.robo-nix/. After that,robo.nixis yours to edit. robo run [--profile <name>] [--sync] [--] <command> [args...]uses the same runtime preparation path for one command without keeping a shell open.robo search <library>helps find Nix package candidates for missing shared libraries, such aslibassimp.so. It only prints suggestions.robo refreshclears robo-owned runtime state under.robo-nix/. In an active runtime shell, the shell updates at the next prompt.robo updateupdates the projectrobo-nixflake input, reinstalls theroboCLI binary from that updated input, and clears runtime cache state. It does not update Python dependencies orrobo.nix.robo --help,robo --version, androbo -Vare available as standard CLI utilities.- Active
robo shellsessions refresh at the next prompt when runtime inputs change. This includes the selected runtime profile,flake.nix,flake.lock,.python-version,pyproject.toml,uv.lock,robo.nix, and local.nixfiles imported byrobo.nixor the project flake. - Refreshing exports a re-evaluated shell environment. It does not run
uv syncand does not rewriterobo.nix. - First-bootstrap inference reads direct dependencies, optional dependencies, dependency groups, local
[tool.uv.sources]path dependencies, and package names from an existinguv.lockwhen available. - Every runtime attempt writes
.robo-nix/last-run.jsonwith redacted runtime facts, including typed host CUDA and graphics probe summaries. When setup fails,roboalso writes.robo-nix/last-error.logwith context you can paste into an issue.
1. Install robo
The installer installs the robo CLI through Nix profiles. If Nix is missing, it uses the Determinate Nix installer first.
curl --proto '=https' --tlsv1.2 -fsSL https://raw.githubusercontent.com/ausbxuse/robo-nix/master/scripts/install.sh | shWhen testing from a local checkout:
ROBO_NIX_FLAKE="path:$PWD" ./scripts/install.shManual profile install from a local checkout:
nix profile remove robo || true
nix profile add .#roboUse .#robo instead of .# so the profile entry is named robo and future nix profile remove robo commands keep working.
Newly generated project flake.nix files point at github:ausbxuse/robo-nix/master by default, even when robo was installed from a local checkout. To test a project against local robo-nix source, set ROBO_NIX_DEFAULT_SOURCE_URL=path:/path/to/robo-nix before first bootstrap. After changing that override, rebootstrap the test project by removing generated runtime files such as flake.nix, flake.lock, robo.nix, and .robo-nix/, then running robo shell again.
Installer overrides:
ROBO_NIX_FLAKEchanges the flake installed by the script.ROBO_NIX_NIX_INSTALLER_URLchanges the Nix installer URL used when Nix is not already installed.
2. Pin Python
uv python pin <version>robo reads .python-version and does not choose a default Python version. For example:
uv python pin 3.113. Enter the runtime
robo shell --syncOn first bootstrap, robo shell may create:
flake.nix: minimal Nix plumbing that delegates to robo-nix.robo.nix: the project runtime manifest..gitignore: in Git worktrees, an entry for.robo-nix/when missing.
With --sync, robo runs uv sync --locked in the prepared runtime before entering your default interactive shell with a [robo] prompt prefix. Set ROBO_NIX_SHELL only when you need to override shell selection.
4. Sync Python packages
uv syncYou can also run uv sync manually inside the prepared shell. Native Python extensions can then see the runtime libraries and headers exposed by Nix. In profile-based projects, robo sets UV_PROJECT_ENVIRONMENT to a profile-specific virtualenv under .robo-nix/venvs/<profile>/, so different runtime profiles can stay installed side by side.
5. Adjust runtime components
After first bootstrap, edit robo.nix for project runtime choices such as native build tools, Linux headers, desktop graphics, Qt, or CUDA build tooling.
For example, a project using evdev and GLFW-style windows usually needs:
{
defaultProfile = "default";
profiles = {
default = {
components = [
"python-uv"
"native-build"
"linux-headers"
"desktop-gl"
];
pythonExtras = [];
pythonGroups = [];
extraPackages = pkgs: [
];
extraRuntimeLibraries = pkgs: [
];
hostGraphics = "auto";
};
};
}Projects that contain multiple deployable surfaces can define more profiles in the same robo.nix:
{
defaultProfile = "workstation";
profiles = {
workstation = {
components = [ "python-uv" "native-build" "linux-headers" "desktop-gl" ];
pythonExtras = [ "workstation" ];
pythonGroups = [ "dev" ];
hostGraphics = "auto";
};
tianji-driver = {
components = [ "python-uv" "native-build" "linux-headers" ];
pythonExtras = [ "tianji-driver" ];
pythonGroups = [];
hostGraphics = null;
};
};
}Use a non-default profile with:
robo shell --profile tianji-driver --syncIf runtime inputs change while robo shell is open, the prompt hook refreshes the shell environment at the next prompt. Refreshing does not rewrite user-managed robo.nix.
If an error names a missing shared library, search for Nix package candidates:
robo search libassimp.soUse one command inside the runtime without staying in an interactive shell:
robo run [--profile <name>] [--sync] [--] <command> [args...]Use the optional -- when the command name starts with -. Any later -- belongs to the command being run. With --sync, robo runs uv sync --locked before launching the child command.
Clear local robo runtime state and rebuild the active shell environment at the next prompt:
robo refreshUpdate the version of robo-nix pinned by the project:
robo updateThis updates the robo-nix input in flake.lock, reinstalls the robo CLI binary from that updated input, and clears runtime cache state. The next robo shell or robo run uses the updated lock.
What robo does not do
robo does not create pyproject.toml, run uv sync unless --sync is explicitly requested, resolve Python packages, update project dependencies, or rewrite robo.nix after first creation.