前回の記事でApple シリコンCPUの環境から特定バージョン未満のTerraformを無理やり動かせる方法を書きましたが、他にも幾つかIntelプロセッサ用にしかバイナリが提供されていないものが出てきたり、前回の方法がかなり無茶な内容だった事もあり、「流石に毎回その場凌ぎ対応で乗り切るのは無理がある」ということで、改めてM1 Macでのローカル開発環境を作り直してみた内容のメモです。
前提
1. AppleシリコンCPUへの世の中的な対応は追いついておらず、arm64バイナリが提供されていないものはまだ多い
かなり普及してきたM1 Macですが、2022年2月現在ではまだ周辺の対応が追いついていない状態で、同環境から開発時に必要となるものをダウンロードしようとするとApple シリコン用のバイナリが提供されていないケースがまだ結構発生します。
時間の経過とともに徐々に改善されていくとは思いますが、まだしばらくは開発時に必要となるものでApple シリコン用バイナリが存在しないケースが発生することはある程度想定しておく必要がありそうです。
2. 恒久対応は、対応バージョン以上までVUPする方法
Appleシリコン用が存在しないものもまだ多い現状ですが、少しずつ対応は進んできておりarm64のバイナリが提供されているものもかなり多いです。
ですが、前回の記事で書いたTerraformを含む多くはバージョンxxx以上でのみ対応というケースが多く、同バージョン未満では提供されていない場合が多いです。
ですので、恒久対応は使用するバージョンをバイナリが提供されているバージョン以上まで上げることです。
バージョンアップが難しい場合もありますが、可能な限りバージョンアップができないかを検討してみるのをお勧めします。
3. バイナリが提供されていないバージョンでの対応は、無理やりな暫定対応に頼らざるを得ない
これはもう仕方ない面が大きいですが、バイナリが提供されていない状態で無理やり使えるようにする方法は、どうしても無理やりな暫定対応になります。
Appleシリコン環境にIntelプロセッサ用のバイナリを手動でダウンロードしてきてシンボリックリンクを無理やり貼ったりなどがそうですね。
とは言っても、諸々の事情ですぐにバージョンアップは難しかったり、そもそもバージョンに関係なくバイナリが提供されていないなんて場合もあります。
今回対応するのはそんなケースにも対応できる方法で、M1 MacなどのAppleシリコンCPU環境で今後開発していく上で有効な選択肢の一つになると思います。
対応方針
どうやって対応するかですが、今回は以下の方針で対応することにしました。
同一マシン上に二つの環境を作って管理を完全に分離した形で共存させる
違うCPU用のバイナリを無理やり動かすのはどうやっても無理があるのですっぱりと諦めて、それぞれのCPU用の環境を同一マシン上に二つ作る形です。
また、同一ホスト上に仮想環境を二つ作るまでやると少し大変な為、今回はそこまで大がかりなものではなく、各種バイナリをダウンロードするターミナル環境と、ダウンロードしたものの管理場所を分けるだけの以下のようなイメージです。
Macのアプリケーションなどマシン一台につき一つしか入れられないものは共通で使い、Homebrewや各種バージョン管理用のenvなどはそれぞれの環境用に分離して別で管理する形です。
Macのアプリケーションも複製すると一つのアプリケーションを複数個に分けて持てますが、バージョンアップで複製したアプリケーションが消えてしまったりなど無理に分けるのは止めた方が良さそうです。
Appleシリコン/Intelプロセッサ用の環境用意
方針が決まったところで、それぞれの環境の用意を進めていきます。
1. 作業前環境のお掃除
二つの環境の用意を始める前に、作業前の環境にAppleシリコン用とIntelプロセッサ用のバイナリがごちゃ混ぜに共存している場合は、一度環境を掃除します。
この手順はSKIP可ですが、異なる環境用のバイナリが同一パスにごちゃ混ぜになっている状態だと今後予期せぬトラブルにハマってしまわないようにする為にも、一度綺麗にしておくことをお勧めします。
以下の手順ですぐに終わるのと、基本的には全て復元可能です。
- 作業前に使用していたHomebrewの内容をメモ
- Homebrew を一度アンイントール
1 |
$ brew list |
表示された一覧をどこかにメモしておきます。
1 2 3 4 |
$ ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/uninstall)" Warning: This script will remove: ... You may wish to remove them yourself. |
途中で一度本当に消すか聞かれるので、yesで進ませます。
2. 普段使っているターミナルアプリをRosettaを非有効化して起動
Mac純正のターミナルやiTermなどターミナル用のアプリは複数ありますが、普段使用しているターミナルアプリをRosettaを非有効化した状態で起動します。
Rosettaは、特定のアーキテクチャのプログラムコードを持つバイナリを、別のアーキテクチャ用のアーキテクチャ用に適宜変換してバイナリの互換性を維持するAppleの技術で、Appleシリコン用の実行環境のターミナルアプリをIntelプロセッサ用の実行環境で開かせたりなどができます。
また、各アプリケーション毎の設定で有効化/非有効化を切り替えられます。
自分は普段iTermをメインで使用している為、iTermをメインのターミナルアプリとして話を進めます。
開発メイン用のターミナルはRosettaを非有効化して起動するので、Appleシリコン用として動作します。
1 2 |
$ uname -m arm64 |
ハイスペックなM1 Macを使っている以上、AppleシリコンのCPUではバイナリが存在せず操作が実行できないなどの場合を除き、可能な限りこの環境を使用して普段の開発を行なっていきます。
3. arm64環境にHomebrewインストール
Homebrewのアンインストールを飛ばした場合は、この手順もSKIPしてください。
Homebrewのインストールは、公式に載っている以下コマンドを打つだけです。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
$ /bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)" ... ==> Installation successful! ==> Homebrew has enabled anonymous aggregate formulae and cask analytics. Read the analytics documentation (and how to opt-out) here: https://docs.brew.sh/Analytics ==> Homebrew is run entirely by unpaid volunteers. Please consider donating: https://github.com/Homebrew/brew#donations ==> Next steps: - Run `brew help` to get started - Further documentation: https://docs.brew.sh |
arm64用のHomebrewは、 /opt/homebrew/ 配下にインストールされます。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
/ └── opt └── homebrew ├── CHANGELOG.md ├── CONTRIBUTING.md ├── Dockerfile ├── LICENSE.txt ├── Library ├── README.md ├── SECURITY.md ├── bin ├── completions ├── docs └── manpages |
インストールが完了したらパスを通すところまでやっておきます。
1 2 3 4 |
$ export PATH="$PATH:/opt/homebrew/bin" >> ~/.zshrc $ source ~/.zshrc $ which brew /opt/homebrew/bin |
M1 Macデフォルトのzsh用にパスを追記していますが、ログインシェルに別のものを使用している場合は追記する設定ファイルを適宜置き換えてください。
上記に同じく、Homebrewアンインストールを飛ばした場合はSKIPしてください。 ここでAppleシリコン用のバイナリが提供されていないバイナリを無理やり手動でダウンロードするなどは絶対に行わないようにしてください。 arm64環境が一旦できたので、続いてIntelプロセッサ用の環境を作成していきます。 今度はRosettaを有効化して起動するので、Intelプロセッサ用として動作します。 Intelプロセッサ用の環境はAppleシリコン用のバイナリが提供されていないものを動かす時にだけ使用するもので、普段は起動させない環境です。 Intelプロセッサ用にもHomebrewをインストールしていきますが、普通に入れるとAppleシリコン用のHomebrewとパスが被ってしまうので、別のインストール先を用意して手動で入れる形を取ります。 インストール完了後のディレクトリ構成は以下のようになります。 Intelプロセッサ用のHomebrewを/opt/homebrew-x86_64 に手動インストールしましたが、ログインシェルの環境変数にパスを通していないのでこの段階ではまだ認識されません。 起動中のターミナルの実行環境(Appleシリコン環境 or Intelプロセッサ環境)により設定する環境変数のパスを切り替える必要があるので、ログインシェルの設定ファイルを以下のように変更します。 上記のようにIntelプロセッサ用のHomebrewの環境変数を書くと、/opt/homebrew-x86_64/bin がHomebrewのパスとして認識されるようになります。 念のために、Appleシリコン環境のメインのターミナルで再度Homebrewのパスを確認しておきます。 実行環境によりHomebrewのパスが制御できているのが確認できます。 Intelプロセッサ環境のHomebrewにもパッケージをインストールします。 また、バージョン管理用の各種env用に設定する環境変数のパスについても、Homebrewと同じくAppleシリコン用のHomebrewで入れたenvで設定しているパスとは完全に分けたパスを設定します。 pyenvのパス設定を例に出すと、ログインシェルの設定ファイルへの記載は以下のようになります。 それぞれのパスが効いているのを確認します。
長くなりましたが、以上で全ての設定が完了です。 今回は以上になります。
4. アンインストール前にメモしたHomebrewパッケージの再インストール
また、バージョン管理用の各種envパッケージをインストールした場合のログインシェルの設定ファイルへのパス追記なども必要に応じて行なってください。
Intelプロセッサ用のバイナリをAppleシリコン用の管理環境に混入してしまうと、環境を分けた意味が無くなってしまいます。5. 普段使っているターミナルアプリとは別のアプリでRosettaを有効化して起動
普段使っているターミナルのアプリとは別のアプリケーションを、Rosettaを有効化した状態で起動します。
自分はメインターミナルがiTermだったので、Mac純正のターミナルアプリをサブとして使用します。
6. Intelプロセッサ用環境にHomebrewインストール
今回は、/opt/homebrew-x86_64/配下に入れることにします。
7. Appleシリコン環境とIntelプロセッサ環境でHomebrewの環境変数パスを変更させる
この段階で which brew を打つと、Appleシリコン用のHomebrewのパスが表示されます。
8. Intelプロセッサ環境のHomebrewにパッケージインストール
こちらの環境にインストールするのは、Appleシリコン用のバイナリが提供されていないものなど必要最小限のパッケージだけです。
Appleシリコン用のバイナリが存在しない問題はM1 Macで長く開発をしていくと避けては通れないので、多少面倒でも最初に開発環境を作っておくと後々便利です。参考