Python開発環境の構築手順: pyenv+venvを使ってjupyterlabが使えるまで

プログラミングを学んだり、自分で何かしらのコードを書こうと思った際に、開発環境の構築に手間取るケースは意外と多いと思います。また、ある程度プログラミング慣れてくると、利用しているライブラリのバージョン不整合でつまづくケースも出てくると思います。

そこで本稿では、Pythonの開発環境構築の中で比較的シンプルな方法である、venvを使った開発環境構築手順を解説します。ここで解説する手順は、シンプルではありますが、プロジェクト毎に仮想環境を構築して作業するので、他のアプリケーションに影響を及ぼさない構成になっています。

開発環境の階層構造

Pythonに限らないですが開発環境としては2段階の階層構造になっていると捉えると良いです(下図)。

まず、実行するPython自体の選択です。Pythonに限らずバージョンによって機能が異なることが多く、どのPythonを使うかを選択します。2023年4月の時点での最新は3.11.3です。個人での小規模な開発では深く気にしないという選択も取れますが、新しい機能を試してみたり、Pythonのバージョンが指定されているライブラリなどを利用する際には、自由に切り替えられると嬉しいです。

次に、利用するライブラリ群の管理です。通常、プログラミングの際には公開されていたりする「ライブラリ」を利用していきます。このライブラリにもバージョンがあり、機能が変わってきます。また、ライブラリ自体も別のライブラリを利用するような関係を持っていたりします。このように依存関係があるため、ライブラリ群をプロジェクト毎に管理できると嬉しいです。

「開発環境」というと、Python自体とそこで利用されるライブラリを指します。これらはそれぞれ依存関係を持っていますので、プロジェクト(アプリケーションやデータ分析対象など)毎に切り替えられると嬉しいです。

Python自体の管理(切り替え)

Pythonの環境としてよく利用される構成としては以下のものがあると思います。

No.環境の管理概要
1システム標準OSに標準で搭載れるPython。システムで利用されているため、バージョンアップには注意が必要(変更しない方が安全)。
2Anacondaデータサイエンスをはじめとする科学技術計算のためのプラットフォーム。Pythonの実行環境、パッケージ管理など総合的に扱う。
3pyenvPythonのバージョン管理をするためのシンプルなツール。
4Dockerコンテナと呼ばれる仮想的な環境をコンピュータの中に構築するツール。

これらは厳密に同じ階層に位置する技術ではないものもありますが、Python環境というとこのような環境を使うことが多いと思います。

1はシステムで利用するPythonなので、切り替えはできないです。2~4の技術を利用することで、Python自体を切り替えることができます。

ライブラリ群の管理

パッケージ管理ツールとしては以下のツールがよく用いられると思います。

No.パッケージ管理概要
1venv+pipPython標準。venvで実行環境の管理をして、venvの中でpipを使ってライブラリのインストール、依存関係の管理を行う。
2Anacondaデータサイエンスをはじめとする科学技術計算のためのプラットフォーム。Pythonの実行環境、パッケージ管理など総合的に扱う。
3poetryパッケージの管理ツール。ライブラリの依存関係を明にファイルとして管理するので、全く同じ構成を再現できる。

Pythonの切り替えとパッケージ管理はそれぞれ独立していることが多いので、これらを組み合わせて開発環境を構築します。(Anacondaを使う場合は、他と併用できない)

開発環境の構成

前述の通りPythonの開発環境構築手段は複数あります。その中で本稿では下記の構成での環境構築手順を解説します。

Python管理パッケージ管理
pyenvvenv+pip

この構成の特徴は、python標準機能を使うことです。pyenv自体はPython標準ではありませんが、軽量なツールなので、全体としては軽い構成になっています。

Anacondaもよく利用されていますが、Anacondaを使うとpipが基本的には利用できなくなり、Python標準から外れる必要があります。

Dockerとpoetryを使った方法は、解説動画をYouTubeにあげていますが、この構成は環境の安定性という点では優れており、第三者に全く同じ構成を構築することが容易にできます。しかし、全体的に重たくトラブルが発生すると修正するのにある程度の知識や慣れが必要です。

構築手順

ここでは、各種ツールの導入解説、実際の環境構築手順解説をし、例としてjupyterlabを立てるところまでを解説します。

なお、本稿で紹介する手順をまとめて、githubにテンプレートリポジトリを作って公開しています。よければそちらも参考にしてください。

tok41/basic-dev-env

動作確認環境

以下の環境で確認をしています。Linux(Ubuntu等)でも似たような手順で進められると思います。筆者はWindows環境が手元にないので、動作手順は未確認です。公式ドキュメントに記載がありますのでそちらをご確認ください。

  • OS: macOS Ventura
  • チップ: Apple M1

pyenvの導入

ここで紹介する手順の中で最も難易度が高いのがこのpyenvの導入だと思います。難しいと思われる場合には、Pythonのバージョン切り替えはできないですが、本節を飛ばして「venvでの仮装環境構築」に進んでも大丈夫です。

pyenvの導入にあたっての詳細は公式githubリポジトリに記載されているので、そちらを確認してください。

https://github.com/pyenv/pyenv#installation

Macを利用している場合は、Macのパッケージ管理ツールであるHomebrewを使ってインストールできます。インストールした後に、PATHを設定する必要がありますが、Linuxの場合と同じ手順なので後述します。

brew update
brew install pyenv

UbuntuなどのLinux環境を利用している場合には、下記の通り、リポジトリをcloneして、PATHを通すだけで利用できます。

git clone https://github.com/pyenv/pyenv.git ~/.pyenv

次に、Pyenvを利用できるようにするためにPATHを通します。利用するシェルがbashであれば.bashrcに、zshであれば.zshrcに以下の文を追加します。

export PYENV_ROOT="$HOME/.pyenv
command -v pyenv >/dev/null || export PATH="$PYENV_ROOT/bin:$PATH
eval "$(pyenv init -)"

設定を追加した後は、ターミナルを立ち上げ直すなどして設定を反映させておきます。

Windowsの場合は、pyenv-winというツールの利用が推奨されています(公式ドキュメント参照)。

利用するPythonのインストール

pyenvを利用することで、システムにインストールされているものと異なるバージョンのPythonをインストールして切り替えることができます。

まず、以下のコマンドでインストールするPythonのバージョンを探します。

pyenv install --list

数字だけのものが公式版のPythonと思っていて良いです。このリストの中から利用するバージョンを選定し、下記のコマンドでインストールします。下記の例では3.11.0をインストールしています。

pyenv install 3.11.0

インストールが無事に終了すると、以下のコマンドでpyenvで切り替えることができるPythonのリストが表示されます。

pyenv versions

上記コマンドを実行すると以下のように表示されます。

* system (set by /Users/t41/.pyenv/version)
  3.11.0

*がついているものが現在利用しているPythonバージョンです(上記の例ではsystem標準のPythonが利用されています)。

インストールしたPythonを利用するには、以下のコマンドを実行します。

pyenv local 3.11.0

pyenvの次のlocalはカレントディレクトリ以下で利用するPythonを指定するという意味です。localの他に、globalを指定するとpyenv環境全体で利用するPythonが変更されます。通常のアプリケーション開発の場合には、localで該当のプロジェクト内だけで設定が閉じるようにした方が良いです。他にもshellというコマンドもありますが、これにするとセッション内だけでPythonの設定が反映されます。なので、ターミナルを閉じて再度開いた場合などは元の設定に戻っているはずです。

インストールlistが古い場合

pyenvにはlistをupdateするようなコマンドがありません。利用の環境によっては最新のバージョンがリストに出てこないケースがあります。

公式ドキュメントにはいくつか対策が記載されていますが、この中でもpyenv-updateというプラグインを導入するのが良いと思います。

導入手順は以下の通り、gitリポジトリをcloneしてくるだけです。

git clone https://github.com/pyenv/pyenv-update.git $(pyenv root)/plugins/pyenv-update

これでupdateコマンドが使えるようになっているはずです。

pyenv update

リストを確認すると最新のバージョンが出てくると思います。

venvでの仮装環境構築

次にvenvを使って仮想環境を構築します。venvPythonの標準モジュールなので、インストール作業等は不要で、以下のコマンドを実行するだけです。

python -m venv kasou

このコマンドは、pythonのモジュールであるvenvを実行し、その時の引数としてkasouを渡すという意味です。kasouは仮想環境の名称なので任意の名前で良いです。

仮想環境の有効化

次に構築した仮想環境を有効化して、実際に使っていきます。

source venv/bin/activate

上記のコマンドで仮想環境が有効化されます。

仮想環境を終了するには、以下のコマンドを実行します。

deactivate

仮想環境にパッケージのインストール

構築したばかりの仮想環境は外部パッケージが何もインストールされていないまっさらな環境です。ここにpipコマンドで必要なパッケージをインストールしていきます。

python -m pip install matplotlib

requirements.txtが用意されている場合は、以下のコマンドで一度にインストールできます。

python -m pip install -r requirements.txt 

jupyterlabの起動

jupyterlabは、Python(だけではないですが)のインタラクティブな実行環境です。利用方法など詳しくは下記ページで取り扱ったので、そちらを参照してください。

上述の手順で仮想環境を有効にしておけば、下記コマンドを実行することでjupyterlabが立ち上がります。

jupyter lab --port 58888

シェルスクリプト利用のススメ

jupyter labは上記のコマンドで立ち上げることができます。

しかし、パラメータの指定などする場合、いちいちパラメータ名を記憶しておくのは面倒です。また、複数の環境を立ち上げているような場合はポート番号が重複する問題に悩まされることも少なくありません。

そこで、環境変数に必要なパラメータを設定しておき、シンプルなコマンドで実行できるようにスクリプトを用意することをお勧めします。

具体的には、下記のテキストファイルを用意します。

# PORT設定: 環境変数が空なら58888を設定する
JUPYTER_PORT="${JUPYTER_PORT}"

if [ -z "$JUPYTER_PORT" ]; then
  JUPYTER_PORT="58888"
fi

# jupyter lab 起動
jupyter lab --allow-root \
    --NotebookApp.token='' \
    --ip=0.0.0.0 --port $JUPYTER_PORT \
    --no-browser --autoreload

シェルスクリプトの詳細はここでは割愛させていただきます。

上記のファイルを実行することで、環境変数(JUPYTER_PORT)に指定のポート番号でjupyterlabが起動します。環境変数を設定していない場合は、5888で起動します。

bash bin/run_jupyter.sh

環境変数の指定を合わせて実行する場合は以下のようにします。環境変数を一時的に指定したい場合にはこの起動方法が便利です。

JUPYTER_PORT=48888 bash bin/run_jupyter.sh

上記のコマンドで48888番ポートでjupyterlabに接続できます。

まとめ

本稿では、pyenvvenvを利用したPython環境の構築について書きました。環境は、MacOS環境での動作確認結果でありますが、Linuxの場合は大きく変わらない手順で作業できるかと思います。Windowsの環境は未確認です。

様々なライブラリに依存して開発が進んでいる現状では、仮想環境の利用は必須だと思います。よほどシンプルなプロジェクトであれば別ですが、ライブラリの依存関係という余計な悩みに振り回されないためにも仮想環境については慣れておくと良いと思います。

dockerを利用するべきかpyenv+venvを利用するべきかは、それぞれの技術の習得状況によって異なるとは思います。個人で開発するような小規模な場合は、今回紹介した方法が軽くて良いのではないかと考えます。

参考