Back to Mise

Bootstrap

docs/bootstrap.md

2026.6.64.2 KB
Original Source

Bootstrap <Badge type="warning" text="experimental" />

mise bootstrap sets up the machine-level pieces around a mise config: OS packages, dotfiles, macOS defaults, the user's login shell, tools, and any final project-specific task.

Use bootstrap for things that are needed before a project or workstation is ready, but that do not belong in [tools]: native libraries, Homebrew formulae, shell rc files, editor config, macOS preferences, and one-time machine setup.

How it runs

mise bootstrap runs these steps in order:

  1. mise bootstrap packages install installs missing [bootstrap.packages].
  2. mise dotfiles apply applies [dotfiles].
  3. mise bootstrap macos-defaults apply writes [bootstrap.macos.defaults].
  4. mise bootstrap user apply applies [bootstrap.user].
  5. mise install installs missing [tools].
  6. mise run bootstrap runs a task named bootstrap, if one exists.

The declarative steps converge: if a package is already installed, a dotfile already matches, or a default is already set, mise skips it. The bootstrap task runs every time, so keep it idempotent.

Example

toml
[bootstrap.packages]
"apt:build-essential" = "latest"
"brew:postgresql@17" = "latest"

[dotfiles]
"~/.gitconfig" = { mode = "symlink" }
"~/.config/nvim" = { mode = "symlink" }
"~/.zshrc/activate" = { block = 'eval "$(mise activate zsh)"' }

[bootstrap.macos.defaults]
"com.apple.dock" = { autohide = true }

[bootstrap.user]
login_shell = "/bin/zsh"

[tools]
node = "lts"
python = "3.12"

[tasks.bootstrap]
run = "gh auth status || gh auth login"

Then run:

sh
mise bootstrap --yes

For a dry run:

sh
mise bootstrap --dry-run

Inspecting State

Use the narrower commands when you want to inspect one part of the bootstrap state:

sh
mise bootstrap packages status
mise dotfiles status
mise dotfiles apply --dry-run
mise dotfiles apply --dry-run --verbose
mise bootstrap macos-defaults status
mise bootstrap user status

mise bootstrap packages status --missing and mise dotfiles status --missing are useful CI checks when a repo expects machine setup to be in place but should not install anything during that check.

What Goes Where

ConfigUse for
[bootstrap.packages]OS packages from apt, dnf, pacman, or brew
[dotfiles]Whole-file dotfiles and small managed edits to existing files
[bootstrap.macos.defaults]macOS user preferences written through defaults write
[bootstrap.user]Current-user settings such as login_shell
[tools]Versioned dev tools managed by mise
[tasks.bootstrap]Anything custom that should run after tools are installed

Use declarative sections when mise can inspect and converge the state. Use [tasks.bootstrap] for imperative setup that does not fit those sections, such as cloning a private repository, running an auth flow, or seeding local data.

Common Workflows

New Machine

sh
mise trust
mise bootstrap --yes

Add A Package

sh
mise bootstrap packages use apt:libssl-dev

This writes [bootstrap.packages] and installs what is missing.

Capture An Edited Dotfile

sh
$EDITOR ~/.zshrc
mise dotfiles add ~/.zshrc

mise dotfiles add stores the live file under dotfiles.root and writes an explicit [dotfiles] entry with mode.

Edit A Managed Dotfile

sh
mise dotfiles edit ~/.zshrc
mise dotfiles apply ~/.zshrc

For symlinked dotfiles, edit opens the managed source, so it works with the default symlink mode.

Advanced: Self-Managing Config

You can manage the dotfiles repository and the mise global config as dotfiles:

toml
[settings]
dotfiles.root = "~/.dotfiles"

[dotfiles]
"~/.dotfiles" = "~/src/dotfiles"
"~/.config/mise/config.toml" = "~/.dotfiles/mise/config.toml"

The repo/source must exist before the first apply. Replacing the active global config affects future mise invocations, so use this pattern carefully.