Last updated on 4th August 2026

mise: One Tool for Runtimes, Tasks, and Environments

Most projects accumulate a small pile of tooling just to get a developer started: one manager for the Node version, another for Python, a .env file for configuration, and a scattering of npm run scripts and shell aliases for common tasks. Each has its own config file and its own quirks.

mise collapses that pile into one tool and one file. It manages language runtimes (the way nvm or pyenv do), runs your project's tasks (the way a Makefile or npm run does), and loads environment variables per directory (the way direnv does) — all from a single .mise.toml. This guide covers what mise does, how to set it up, and how to keep it aligned with your DeployHQ deployments.

What is mise?

mise (pronounced "meez," from the French mise en place) is a fast, Rust-based developer environment manager. It began as a drop-in replacement for asdf — it reads the same .tool-versions files — and grew into three tools in one:

  1. Runtime version manager — install and switch between versions of Node, Python, Ruby, Go, and hundreds of other tools, per project.
  2. Task runner — define build, test, and deploy tasks in config and run them with mise run.
  3. Environment manager — set environment variables (and load .env files) automatically when you enter a project directory.

If you've used asdf, mise is a faster, more capable successor that still understands your existing .tool-versions. If you've been stitching together nvm + pyenv + direnv + a Makefile, mise replaces all four.

Installing mise

# macOS / Linux
curl https://mise.run | sh

# Homebrew
brew install mise

Then activate mise in your shell so it can manage versions and env automatically:

# ~/.bashrc
eval "$(mise activate bash)"

# ~/.zshrc
eval "$(mise activate zsh)"

Activation is what lets mise swap runtime versions and load environment variables the moment you cd into a project.

Managing runtimes

Add tools to a project with mise use, which installs the version and records it in your config:

mise use node@20
mise use python@3.12
mise use go@1.22

This writes a .mise.toml at the project root:

[tools]
node = "20"
python = "3.12"
go = "1.22"

Anyone who clones the repo and runs mise install gets the exact same toolchain. Because mise also reads .tool-versions, teams migrating from asdf can adopt it without changing a single file.

mise install          # install everything listed in the config
mise ls               # show installed and active versions
mise use node@22      # bump a version — updates .mise.toml

Running tasks

Instead of a separate Makefile or a wall of package.json scripts, mise lets you define tasks right in .mise.toml:

[tasks.build]
run = "npm run build"

[tasks.test]
run = "npm test"

[tasks.deploy]
depends = ["build", "test"]
run = "echo 'ready to deploy'"

Run them by name, and mise resolves dependencies for you:

mise run build
mise run deploy       # runs build and test first

Tasks inherit the runtime versions and environment from the same file, so a task never runs against the wrong Node version or a missing variable.

Managing environment variables

mise can set environment variables per project and load values from a .env file — the job you'd otherwise hand to direnv:

[env]
NODE_ENV = "development"
DATABASE_URL = "postgres://localhost/myapp"
_.file = ".env"        # load additional values from .env

When you enter the directory, those variables are set automatically; when you leave, they're unset. No more manually source-ing files or leaking one project's config into another.

For secrets you don't want in plaintext, keep them out of .mise.toml and encrypt them instead — you can encrypt your .env files with dotenvx and load the decrypted values at runtime, so nothing sensitive lands in your committed config.

A complete .mise.toml

Here's how the three pieces fit together in one file:

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

[env]
NODE_ENV = "development"
_.file = ".env"

[tasks.build]
run = "npm install && npm run build"

[tasks.test]
depends = ["build"]
run = "npm test"

One file now defines the runtimes, the environment, and the commands for the whole project. A new developer runs mise install and is ready to work.

Using mise with DeployHQ

mise gives your team a consistent local environment — but your build server needs the same runtime versions, and it's worth knowing exactly how that hand-off works.

DeployHQ's build pipeline intentionally ignores version-manager files, including .tool-versions, renaming them during a build so they can't override your project's configured version and restoring them afterward. This keeps builds predictable regardless of which dotfiles are in the repo — the same behavior described in how DeployHQ's build pipeline handles version files. In other words, .mise.toml and .tool-versions drive your local environment; you set the build runtime explicitly in DeployHQ.

The clean way to keep them aligned:

  1. Set the runtime version in your project's build pipeline configuration (or a .deploybuild.yaml), matching the versions in your [tools] block.
  2. Reuse your task definitions as build steps. The commands inside your mise tasks — npm install && npm run build, npm test — are exactly what your build pipeline should run. Defining them once in .mise.toml means your local mise run build and your deployment build command stay identical, so what passes locally is what ships.

Then enable automatic deployments so every push builds with the configured runtime and runs the same steps you run locally — no drift between your machine and production.

When mise is the right choice

Reach for mise when:

  • Your stack spans more than one language and you're tired of a separate manager per runtime.
  • You want tasks, versions, and environment described in one committed file instead of three.
  • You're already on asdf and want a faster tool that reads your existing .tool-versions.

If your project is Node-only, dedicated Node.js version managers like fnm and Volta may be all you need — they're lighter and purpose-built for that single job. mise earns its keep the moment a second runtime, a task runner, or per-project env enters the picture.

Ready to ship with the same toolchain your team develops on? Create a free DeployHQ account and connect your repository in minutes.