/var/www/yatta47.log

/var/www/yatta47.log

やったのログ置場です。スクラップみたいな短編が多いかと。

mise の使い方: *env系ツールをconfig.toml 1つに統一する

mise(ミーズ)を調べてたら、pyenv・nvm・tfenv あたりを全部まとめて管理できるツールだったんですよね。

config.toml に書いて mise install するだけで全部入る、というのが想像以上にシンプルだったので、その仕組みと使い始めるときのポイントをまとめます。

何を調べたか

以前 rtx という名前だった頃に一度試したことがあって、そのときはあまり馴染まずにそのままにしてた。

しばらく経ってから mise に改名されて成熟してきたという話を聞いて、改めて使い始めた感じです。

どういうことか

ツール管理がバラバラな状態

Python は pyenv、Node は nvm、Terraform は tfenv、fzf や jq は手動インストール……みたいな状態になりがちですよね。

pyenv   → Python      (.python-version)
nvm     → Node.js     (.nvmrc / .node-version)
tfenv   → Terraform   (.terraform-version)
手動    → fzf, jq, ripgrep, gh ...

ツールごとにインストール方法が違って、設定ファイルの場所も違って、バージョン切替のコマンドも違う。

管理対象が増えてくると「この環境、何で入れたんだっけ」ってなるやつです。

mise のアプローチ

mise はこれを config.toml 1 ファイルに統一します。

# ~/.config/mise/config.toml
[tools]
node      = "22"
python    = "3.12"
terraform = "latest"
fzf       = "latest"
ripgrep   = "latest"
gh        = "latest"

これを書いておいて mise install を叩くと全部入ります。

ランタイム(Node.js, Python)と CLI ツール(fzf, ripgrep)が同じ書き方で管理できる、というのが地味に便利で。

asdf と何が違うのか

asdf に似た思想のツールですが、いくつか改善されています。

asdf はシェル起動時に shim スクリプトを経由するので、コマンド実行のたびに少しオーバーヘッドがかかります。

mise の activate 方式はプロンプト表示時に PATH を直接書き換えるので、shim 経由のオーバーヘッドがない。

加えて、設定を有効化すれば .node-version / .nvmrc / .python-version / .terraform-version / .tool-versions を読めるようになります(idiomatic_version_file はデフォルト無効なので、使いたいツールごとに mise settings add idiomatic_version_file_enable_tools node のように有効化が必要です)。

セットアップ手順

activate モードで使う

まず mise をインストールして、.zshrc(または .bashrc)に activate を追加します。

# mise のインストール
curl https://mise.run | sh

# .zshrc に追加
echo 'eval "$(mise activate zsh)"' >> ~/.zshrc

あとは config.toml にツールを書いて mise install するだけです。

mise install

既存プロジェクトとの共存

idiomatic_version_file を有効化していれば、チームのプロジェクトに .node-version が置いてあっても読んでくれます。

~/repos/project-a/
  .node-version: 18.20.0   ← チームは nvm で管理

cd するだけでバージョンが切り替わるので、自分だけ mise を使っていても摩擦にならない。

dotfiles に入れると再現性が上がる

config.toml を dotfiles に入れておくと、新しいマシンのセットアップが楽になります。

git clone https://github.com/yourname/dotfiles ~/dotfiles
ln -s ~/dotfiles/config/mise/config.toml ~/.config/mise/config.toml
mise install   # 全部一発で入る

環境の定義が 1 ファイルに収まるので、「あのツール何で入れたっけ」問題がなくなります。

注意点

activate モードは 3 ステップ全部やらないとコマンドが見つからない

ここがハマりポイントで、知らなかったら詰まるやつです。

  1. config.toml にツールを追記する
  2. mise install を実行する
  3. シェルを再起動する(exec zsh または新しいターミナル)

3 番目のシェル再起動が必要なのは、.zshrcmise activate zsh を初めて追加した直後だけです。

それ以降は mise install した後にプロンプトが表示されるタイミング(Enter を押す、cd するなど)で PATH が自動更新されるので、毎回の再起動は不要です。初回だけ忘れがちなポイント。

レジストリに登録されていないツール

mise のレジストリは広いですが、全ツールが載っているわけではないです。

その場合は aqua:owner/repo 形式で aqua registry 経由のツールを取得できます。aqua registry(aquaproj/aqua-registry)に登録されているツールならこの記法で使えます。

[tools]
# mise レジストリにあるツール
fzf    = "latest"

# mise レジストリにないが aqua registry にはあるツール
"aqua:dalance/procs" = "latest"

これは AI に聞いて初めて知ったんですよね。dalance/procs が動くのは aqua registry に登録されているからです。任意の GitHub Releases を直接取得したい場合は github:owner/repo という別の記法もあります。

Python のビルド依存について

mise の Python バックエンドはデフォルトで precompiled binary(python-build-standalone)を使うので、多くの環境ではビルド用パッケージは不要です。

ただし python.compile = true を設定した場合や、precompiled binary が対象環境向けに提供されていない場合はソースビルドになります。その場合は以下のパッケージが必要です。

sudo apt -y install build-essential libssl-dev zlib1g-dev \
  libbz2-dev libreadline-dev libsqlite3-dev libffi-dev liblzma-dev tk-dev

まとめ

mise を使い始めて、管理ツールのバラつきが解消されたのが一番大きかったです。

config.toml に追加して mise install する、という手順に統一されると、覚えることが減る。

dotfiles と組み合わせると「新しい環境でも mise install 1 発で揃う」状態になるので、再現性という観点でも気に入っています。

参考