環境管理ツール「mise」について

記事タイトルとURLをコピーする

こんにちは!

サービス開発部の木伏と申します。

突然ですが皆さん、日々の開発環境はどのツールで管理していますか?

僕は今までNode.jsならばnvm、Pythonならばpyenvを使用していましたがそれぞれ単独の場合はまだしも、複合的な仮想環境を作成したい場合少し煩わしさを感じていました。

Dockerを使えばいいという話でもありますが、そこまでしなくとも……という場面は往々にしてあったりします。

そんなある日、mise(正式名称はmise-en-place)という環境管理ツールに出会って使用感が結構良いものだったので少し紹介させて頂ければと思います。

mise.jdx.dev

何のためのツールなのか?

複数環境の開発環境管理ツール、pyenvやnvmが集合した感じをイメージしてください。

もちろんPythonやNode.jsに限らず例えばGoとかも管理できます。

この手のツールではasdfというツールが有名でしたが、その次世代型という印象です。

(asdfについて書かれた弊社ブログはこちら)

blog.serverworks.co.jp

asdfとのざっくりとした違いは

  • Rustで書かれているためasdfに比べてパフォーマンス良い(ただし、最近asdfもGoで書き直されたようで以前ほど明確な違いはないそう)

  • プロジェクトごとに個別に環境変数を設定できる

  • Windowsがサポートされている

  • セキュリティ基準がasdfに比べて厳格である

といったところにあります。

最後の部分についてですがこちらは機能拡張のためのプラグインに関する部分で、asdfはプラグインの公開にあたって特に審査もないため、誰がツールのベンダーではないランダムな開発者から悪意のあるコードの混入が否定しきれない部分やプラグインがメンテナンスされていない場合があるといった問題があったのですが、それに対してmiseは

  • PublicなPull request経由以外でのアクセス権は@jdxさん(コア開発者)1人しか持たない(ただし、不慮の事故に備えてアカウントの引き継ぎ候補は何人かいる)ことでのキーの漏洩リスクを下げる

  • asdfをバックエンドとするプラグインの排除(上述した審査されないプラグイン類)やそれらのプラグインのインストールに関する警告

  • プラグインレビューのコミット権限の限定化(@jdxさんのみ)

とセキュリティ部分にも配慮されていることが伺えるため移行者が最近増えているそうです。

asdfとの違いについて詳細は以下を参照してください。

mise.jdx.dev

セキュリティポリシー

github.com

導入

基本的な手順としては以下の通りになります。

僕の場合だとこの記事を書いた時点では

  • OS: macOS 15.1.1
  • Shell: zsh

で導入をしています。

使用しているOSやShellによって導入の方法が違いますのでドキュメントを参考に必要な部分は置き換えてください。

mise.jdx.dev

  1. brew install mise
  2. 1が完了したら.zshrc等にPathを通す(miseではactivateと呼称している)
    • echo 'eval "$(/opt/homebrew/bin/mise activate zsh)"' >> ~/.zshrc
  3. mise -v などでインストールされていることが確認できたら任意の環境をインストールする
    • mise ls-remote pythonmise ls-remote node でインストールできるバージョンを一覧で出せる
    • 例えばmise latest python とするとPythonの最新版を出せる
  4. バージョンを決めたらmise install python@3.13.0 といった感じでインストールする
    • nodeの場合はmise install node@lts としてLTSでインストールすることもできます
  5. 使うバージョンはmise use python@3.13.0 といった感じで切り替え可能
    • グローバルにしたい場合はmise use —global python@3.13.0 みたいにする
  6. 今インストールしている環境一覧はmise list で見ることができる

グローバルではなく、プロジェクト毎にPoetryとnode入れるまでの手順サンプル

  1. 対象Projectのルートディレクトリでmise use node@ltsを実行
  2. そのままnpm init で対象のProjectのルートディレクトリにnode_modulesを入れて適宜npm iで必要なライブラリを入れていく
    • Tips: 入れたライブラリを使用するときはコマンドにnpx を接頭辞としてつけないとエラーになるので注意
  3. mise plugin add poetry でプラグイン導入
    • 初回導入時のみ、Poetryのプラグインの出典はこちら
  4. poetry config virtualenvs.in-project true でプロジェクトの配下に.venv 作るように指定
  5. mise.tomlにpoetryのバージョン指定 ex.(poetry = { version = "1.8.5", pyproject = "pyproject.toml" })
    • 先に記述をしておかないとPoetryのインストールに失敗するので注意
  6. mise installを実行(ここでPoetryがインストールされます) ‐ mise installはmise.toml
  7. poetry init 後に適宜poetry add
  8. 必要に応じてエディタ側でnode及びpoetryのPathをエディターのインタープリターに指定してやる
    1. poetryの場合はpoetry env info
    2. nodeの場合はnpm root

プラグインに関してはこちらを参照してみてください。

mise.jdx.dev

miseのプラグインのリポジトリが纏まっているのはこちら。

github.com

Repositoriesから検索できます。 例えばpoetryなら下記の通りです。

mise.tomlファイルについて

mise.jdx.dev

詳細は上記のドキュメントを参照してください。

mise.tomlファイルはmiseに関わる設定を記述するためのファイルになります。

.mise.tomlとして隠しファイルとしても大丈夫です。

プロジェクトのルートディレクトリに置くべきファイルですが、何もない状態でmise useですると自動的に作られます。 例えば

  • Node.jsのLTS

  • Pythonの3.12.0

  • Poetryの1.8.5

という環境を作りたい場合(あるいは作った場合)、 ファイルの内容は以下の通りになります。

[tools]
node = "lts"
python = "3.12.0"
poetry = { version = "1.8.5", source = "pyproject.toml" }

mise installはtomlに則って、必要なものをmiseにインストールしてくれます。

例えば上記のtomlの場合、かつNode.jsとPythonはmise useで先にインストールしていた場合結果的にPoetry のバージョン1.8.5がインストールされるということになります。

バージョンファイルでの指定について

既にプロダクトで.python-version等のバージョンファイルがありそれに依存した環境構築をする必要があるかと思います。

その場合、各種バージョンファイルがルートにあり、mise自体がインストールしてあればmise use(とそこで出来上がるmise.toml)での管理に依存せずとも対応するバージョンで環境が作れます(miseがバージョンファイルに基づいて判断してくれる)

ただし、miseに対象のバージョンがないといけないのでpython --versionnode -vでの対象のバージョンであるかを確認をした上で、バージョンが無い場合はmise installしましょう。 .tool-versionsも同様です。

留意点としてはmise useをしてしまうとmise.tomlが作成されてしまいます。

.gitignoreの更新が許容される、またはGitの管理にmise.tomlを載せることが許容される場合は問題ないですがそうでない場合は気をつけましょう。

このとき例えばPoetryに関してはmise.tomlを使用しないとなるとプラグイン経由での導入ができないため(mise.tomlに使用バージョンとpyproject.tomlのPathを指定する必要があるため)、pipでやるかグローバルインストール での導入を検討してください。

Tips

各環境はshimsで管理されているのでそこにPathを通してやる

miseのバージョン切り替えは仕組み的には環境ごとにmiseが該当する環境にPathを書き換えているということになります。

これは下記の通り、which pythonmise useでバージョンの切り替え前後でそれぞれ実行してみるとよくわかります。

これはターミナルのような対話型のシェル上では特に問題ないのですが、VSCodeなどでうまくPathを拾ってこれないということがあります。

VScode側でデフォルトのPathを設定するのも良いですが、.zprofile及び.zshrcに以下を追加しておくことで解決できます。

.zprofile

    # IDEからの場合はshimsを使うようにする
    if command -v mise 1>/dev/null 2>&1; then
    eval "$(mise activate --shims)"
    fi

.zshrc

    eval "$(mise activate zsh)"
    export PATH="$HOME/.local/share/mise/shims:$PATH"

詳しくはドキュメントの以下の項目を参照ください。

swx-kibushi サービス開発部。ポルノグラフィティが好きです。