pyenv global が効かなくなった(?)話

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

結論

pyenv global しても何も起きないときはこの警告がないか確認すべし( exec -l $SHELL とか実行する)。

WARNING: `pyenv init -` no longer sets PATH.
Run `pyenv init` to see the necessary changes to make to your configuration.

出ていたら、以下のコマンドを実行すべし。

$ echo 'export PYENV_ROOT="$HOME/.pyenv"' >> ~/.bashrc
$ echo 'export PATH="$PYENV_ROOT/bin:$PATH"' >> ~/.bashrc
$ echo 'eval "$(pyenv init --path)"' >> ~/.bashrc
$ echo -e 'if command -v pyenv 1>/dev/null 2>&1; then\n  eval "$(pyenv init -)"\nfi' >> ~/.bashrc
$ source ~/.bashrc

anyenv 経由で pyenv を導入した人はこちら( 1行目 PYENV_ROOT のパスだけ違います)を実行すべし。

$ echo 'export PYENV_ROOT="$HOME/.anyenv/envs/pyenv"' >> ~/.bashrc
$ echo 'export PATH="$PYENV_ROOT/bin:$PATH"' >> ~/.bashrc
$ echo 'eval "$(pyenv init --path)"' >> ~/.bashrc
$ echo -e 'if command -v pyenv 1>/dev/null 2>&1; then\n  eval "$(pyenv init -)"\nfi' >> ~/.bashrc
$ source ~/.bashrc

はじめに

こんにちは。ディベロップメントサービス課の保田(ほだ)です。
自分の所属の名前をまだスラスラ発音できません。精進します。

導入

Amazon Linux 2 の EC2 を開発環境として Python で開発するのはよくあることだと思います。 Python 自体は元から入っていますが、それは Python 2.7.18 であり、少なくとも開発では(ほぼ)使いません。

python3 を入れて python3 コマンドを使う形でも良いかと思いますが、 pyenv を導入する方がより汎用的です。 さらに pyenv を入れるなら anyenv を導入して xenv 系を統一的に管理するともっと汎用的になります。

これは anyenv と pyenv を導入して開発環境を構築していた時の話です。

(※ 本記事では anyenv の導入は本題ではないため省略します。 GitHub の README.md に完結な手順がありますので、ご参照ください。)

起きた事象

anyenv を導入した上で pyenv を導入するときは次のようなコマンドを実行します。

[ec2-user@ip-xx-xx-xx-xx ~]$ anyenv install pyenv
/tmp/pyenv.20210512122420.3691 ~
Cloning https://github.com/pyenv/pyenv.git master to pyenv...
Cloning into 'pyenv'...
remote: Enumerating objects: 19491, done.
remote: Counting objects: 100% (409/409), done.
remote: Compressing objects: 100% (232/232), done.
remote: Total 19491 (delta 214), reused 281 (delta 138), pack-reused 19082
Receiving objects: 100% (19491/19491), 3.99 MiB | 8.12 MiB/s, done.
Resolving deltas: 100% (13145/13145), done.
~

Install pyenv succeeded!
Please reload your profile (exec $SHELL -l) or open a new session.

出力の最終行にある通りのコマンド(新しいセッションを開く)を実行します。

[ec2-user@ip-xx-xx-xx-xx ~]$ exec $SHELL -l
WARNING: `pyenv init -` no longer sets PATH.
Run `pyenv init` to see the necessary changes to make to your configuration.

ん?

ERROR ではないみたいなので一旦スルーして、欲しい Python のバージョンをインストールします。

[ec2-user@ip-xx-xx-xx-xx ~]$ pyenv install 3.8.9
Downloading Python-3.8.9.tar.xz...
-> https://www.python.org/ftp/python/3.8.9/Python-3.8.9.tar.xz
Installing Python-3.8.9...
Installed Python-3.8.9 to /home/ec2-user/.anyenv/envs/pyenv/versions/3.8.9

[ec2-user@ip-xx-xx-xx-xx ~]$ pyenv versions
* system (set by /home/ec2-user/.anyenv/envs/pyenv/version)
  3.8.9

無事インストール出来たのでグローバルでの Python のバージョンを 3.8.9 に変更します。

[ec2-user@ip-xx-xx-xx-xx ~]$ python --version
Python 2.7.18

タイトルにもある pyenv global コマンドです。

[ec2-user@ip-xx-xx-xx-xx ~]$ pyenv global 3.8.9
[ec2-user@ip-xx-xx-xx-xx ~]$ python --version
Python 2.7.18

おや?

[ec2-user@ip-xx-xx-xx-xx ~]$ pyenv versions
  system
* 3.8.9 (set by /home/ec2-user/.anyenv/envs/pyenv/version)

おやおや?

警告をよく読む

という訳で警告をちゃんと読みます。

WARNING: `pyenv init -` no longer sets PATH.
Run `pyenv init` to see the necessary changes to make to your configuration.

警告: pyenv init - はもう PATH を設定しなくなったよ
pyenv init を実行して設定に必要な変更を見てね

早速実行してみます。

[ec2-user@ip-xx-xx-xx-xx ~]$ pyenv init
# Add pyenv executable to PATH by adding
# the following to ~/.profile:
 
export PYENV_ROOT="$HOME/.pyenv"
export PATH="$PYENV_ROOT/bin:$PATH"
 
# Load pyenv automatically by appending
# the following to ~/.bashrc:
 
eval "$(pyenv init -)"
 
# and the following to ~/.profile:
 
eval "$(pyenv init --path)"
 
# If your ~/.profile sources ~/.bashrc,
# the lines should be inserted before the part
# that does that.
 
# Make sure to restart your entire logon session
# for changes to ~/.profile to take effect.

なるほど分からん。 実は README.md にはこの辺りの手順が載っています。 2 と 3 のところです。

README の通りの手順を実行すれば良いわけですが、 ~/.profile ではなく ~/.bashrc への追記でも大丈夫です。 実行すべきコマンドは以下の通りです。

$ echo 'export PYENV_ROOT="$HOME/.pyenv"' >> ~/.bashrc
$ echo 'export PATH="$PYENV_ROOT/bin:$PATH"' >> ~/.bashrc
$ echo 'eval "$(pyenv init --path)"' >> ~/.bashrc
$ echo -e 'if command -v pyenv 1>/dev/null 2>&1; then\n  eval "$(pyenv init -)"\nfi' >> ~/.bashrc

もし、 anyenv 経由で pyenv を扱っている場合は PYENV_ROOT が異なり、1行目のコマンドはこうなります。

$ echo 'export PYENV_ROOT="$HOME/.anyenv/envs/pyenv"' >> ~/.bashrc

最終的に ~/.bashrc に追記される内容はこうなります( anyenv 使っている版)。

export PYENV_ROOT="$HOME/.anyenv/envs/pyenv"
export PATH="$PYENV_ROOT/bin:$PATH"
eval "$(pyenv init --path)"
if command -v pyenv 1>/dev/null 2>&1; then
  eval "$(pyenv init -)"
fi

ここまで出来たら ~/.bashrc を読み込み直します。

$ source ~/.bashrc

これで警告は出なくなり、 Python のバージョンも無事切り替わるようになっています。

やったね。

おわりに

2週間前に同様の手順で pyenv を導入した際はこのようなことが起きなかったため、割と最近(2021/05/12 執筆時点)の pyenv の仕様変更と思われます。

参考