macOSとHomebrewで作るpyenv+pipenvを使った複数pythonバージョンの仮想実行環境

表題通りですが、割と悩んでしまったのでとりあえずメモです。

なおまだしっくり来てるわけではないので、他にいい方法があれば教えてほしいです。

homebrew-versionsがdeprecatedしてた

すっかり忘れていたのですが、Homebrewにあるリポジトリ内の複数のバージョンを管理できる、homebrew-versionsがいつの間にか廃止(deprecated)されていました。1年前に終わってたようです。全く気がついてなかった。。

Homebrew/homebrew-versions: Homebrew/versions (deprecated)

💀 Homebrew/versions (deprecated)

だそうです。骸骨。。

表題のPythonですが、今まで3.4, 3.5, ...といったマイナーバージョンの管理はhomebrew-versionsを使っていたのですが、tapしたリポジトリは意味をなさなくなり、最近ではbrew upgradeするとhomebrew/coreのFomulaで定義されている最新版が入ってしまいます。

このブログの記事を公開してる現在では3.7がリリースされたので有無言わずに3.7がインストールされます。

homebrew-core/python.rb at master · Homebrew/homebrew-core

(ちなみに2.7はpython@2でインストールできます。こちらも現在は2.7.15が入ります。)

macOSで作る複数Pythonバージョンの仮想環境

一応PyPiに出しているパッケージを作って利用している身としては、pythonの各バージョンでテストできないと困りました。また仕事で利用した古い環境をまた扱うときもあるので、そのときに当時の環境がそのまま動かないと確認が大変そうです。

Pythonのマイナーバージョンを利用するときには公式のインストーラーを各バージョンごとインストールするでも良いのですが、homebrewに慣れきってしまったのでCLIライクにやりたいものです。いろいろ調べてみたのですが、pyenv+pipenvを仮想環境作成に利用することにしてみました。やり方を残しておきます。

セットアップ方法

pyenvのインストール

PyenvはPython実行環境のバージョンを複数保持して切り替えて利用することができます。といってもあんまりいい話も聞いてなかったのもあって pyenv local, pyenv global を使う予定はありません。

インストール方法は基本的にpyenvの公式ドキュメントに沿っています。

pyenv/pyenv: Simple Python version management

$ brew update
$ brew install pyenv

# .bash_profileにpyenvの設定を書く
$ echo 'export PYENV_ROOT="$HOME/.pyenv"' >> ~/.bash_profile
$ echo 'export PATH="$PYENV_ROOT/bin:$PATH"' >> ~/.bash_profile

このときに、環境変数のPATHにPYENV_ROOTの記載がされて、実質pyenvからpythonが呼ばれるようになります。pyenv側で操作しない限りはPATHの次に上がっているpythonが呼ばれるっぽい?

pipenvのインストール

Pipenvも公式ドキュメントに従いますが、homebrweなら $ brew install pipenv です。

Pipenv: 人間のためのPython開発ワークフロー — pipenv 2018.7.1 ドキュメント

ワークフロー

箇条書きで書いておくとこうなります。

  1. ほしいpythonのバージョンを pyenv install する
  2. 仮想環境を作りたいディレクトリを作成, 移動(git initするなど)
  3. Pipfileを先に作成→ http://pipenv-ja.readthedocs.io/ja/translate-ja/basics.html#example-pipfile-pipfile-lock を参照
  4. Pipfileの[requires] セクションに python_full_versionを書く :Pipenvの進んだ使い方 — pipenv 2018.7.1 ドキュメント
  5. pipenv install で仮想環境を作る

コマンドラインで叩くとこんな感じかな

1と2 を作業して

$ pyenv install 3.5.5

python-build: use openssl from homebrew
python-build: use readline from homebrew
Downloading Python-3.5.5.tar.xz...
-> https://www.python.org/ftp/python/3.5.5/Python-3.5.5.tar.xz
Installing Python-3.5.5...
python-build: use readline from homebrew
Installed Python-3.5.5 to /Users/hiroshi/.pyenv/versions/3.5.5

$ mkdir ~/.pyenv_test_3.5.5
$ cd ~/.pyenv_test_3.5.5
# optional: git initなど

3ですが、Pipfileを先に作ります。テンプレ的なのはこれです。

[[source]]
url = "https://pypi.python.org/simple"
verify_ssl = true

[dev-packages]

[packages]
requests = "*"

Pipenvの基本的な使い方 | Pipfileの例— pipenv 2018.7.1 ドキュメント

またはこちらを参照に用意します。 [dev-packages]にpytestが入ってる以外は変わりないです。

4で3のPipfileに [requires]セクションを追加します。python_versionで3.5を入れると3.5系の最新バージョンが入りますが、細かく指定するためにpython_full_versionをつかいました。

[[source]]
url = "https://pypi.python.org/simple"
verify_ssl = true

[dev-packages]

[packages]
requests = "*"

[requires]
python_full_version = "3.5.5"

5 で最後に pipenv install を叩きます。

:pyenv_test_3.5.5 hiroshi$ pipenv install

Creating a virtualenv for this project...
Pipfile: /Users/hiroshi/pyenv_test_3.5.5/Pipfile
Using /Users/hiroshi/.pyenv/versions/3.5.5/bin/python3.5m (3.5.5) to create virtualenv...
⠋Running virtualenv with interpreter /Users/hiroshi/.pyenv/versions/3.5.5/bin/python3.5m
Using base prefix '/Users/hiroshi/.pyenv/versions/3.5.5'
New python executable in /Users/hiroshi/.local/share/virtualenvs/pyenv_test_3.5.5-6bkiLy3V/bin/python3.5m
Also creating executable in /Users/hiroshi/.local/share/virtualenvs/pyenv_test_3.5.5-6bkiLy3V/bin/python
Installing setuptools, pip, wheel...done.
Setting project for pyenv_test_3.5.5-6bkiLy3V to /Users/hiroshi/pyenv_test_3.5.5

Virtualenv location: /Users/hiroshi/.local/share/virtualenvs/pyenv_test_3.5.5-6bkiLy3V
Pipfile.lock not found, creating...
Locking [dev-packages] dependencies...
Locking [packages] dependencies...
Updated Pipfile.lock (ea3f76)!
Installing dependencies from Pipfile.lock (ea3f76)...
  🐍   ▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉ 5/5  00:00:01
To activate this project's virtualenv, run pipenv shell.
Alternatively, run a command inside the virtualenv with pipenv run.

最後に pipenv shell でpythonのバージョンを確認してみます。

pyenv_test_3.5.5 hiroshi$ pipenv shell
Launching subshell in virtual environment…
bash-3.2$  . /Users/hiroshi/.local/share/virtualenvs/pyenv_test_3.5.5-6bkiLy3V/bin/activate
(pyenv_test_3.5.5-6bkiLy3V) bash-3.2$ python
Python 3.5.5 (default, Jul 15 2018, 10:34:31)
[GCC 4.2.1 Compatible Apple LLVM 9.1.0 (clang-902.0.39.2)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>>

注意点

homebrewのpythonは消していいの?→消すのは面倒なのでそのまま

pyenvのPythonを入れると、MacのシステムPython(2.7系), homebrewのpython(2系, 3系)と3種類のpython実行環境があります。

このときに、homebrewのpythonっていらないのではと思っていましたが、pythonを依存ライブラリの一部に利用しているFomulaはいくつかあって(httpieやaws-cliなどなどのCLIツール系は結構使ってます)完全に消すと色々と面倒だったので、homebrewのpythonはそのまま残してみました。

仮想環境を使わないならhomebrewのpythonを普段から使うでも良いと思います。

まとめ

macOS とHomebrewで作るPython複数バージョンの仮想環境作成方法をまとめてみました。仮想環境を作成するときにPyhtonのバージョンを切り替えて試すことは難しくなくなりました。

pyenvはPATHを使ってシステムのpython, homebrewのpythonを隠匿してしまうことにもなるので(PYENV_ROOTを追加したPATHには ~/.pyenv/shim/bin が追加されていますが、binの中にあるpython関係は全部シェルスクリプトです)、雰囲気的にだめな人はだめかもしれません。

ただ正直この方法がベストなのかがいまいちわからないので、どなたかに教えてほしいです。。 あとWindowsはpyenvは対応していなかったので、公式のインストーラーですべて入れるか、Chocolateyなどを使う事になりそうです(かね?)

参考

エキスパートPythonプログラミング 改訂2版 (アスキードワンゴ)
B079Z2GX64

ASIN : B079Z2GX64
Amazonで詳しく見る
Powered by Amazon Quick Affiliate (JP)

Pythonプロフェッショナルプログラミング第3版
B07DN6LZH5

ASIN : B07DN6LZH5
Amazonで詳しく見る
Powered by Amazon Quick Affiliate (JP)

About Me

買ったり作ったり考えたり試したの日々の記録です