osモジュールが提供するenviron属性やgetenv/putenv関数などを使って、Pythonプログラム中で環境変数の値を取得/変更/削除する方法を紹介する。
この記事は会員限定です。会員登録(無料)すると全てご覧いただけます。
# 環境変数SOME_ENV_VARの値が"Deep Insider"になっているとする
# Windows(コマンドプロンプト):
# set SOME_ENV_VAR=Deep Insider
# macOS(zsh):
# export SOME_ENV_VAR="Deep Insider"
# os.environ属性による環境変数の取得
import os
value = os.environ['SOME_ENV_VAR']
print(value) # Deep Insider
value = os.environ['NOT_EXISTS_ENV_VAR'] # KeyError
# os.getenv関数による環境変数の値の取得
value = os.getenv('SOME_ENV_VAR')
print(value) # Deep Insider
value = os.getenv('NOT_EXISTS_ENV_VAR')
print(value) # None
# os.environ属性による環境変数の設定
os.environ['SOME_ENV_VAR'] = 'atmarkit'
value = os.environ['SOME_ENV_VAR']
print(value) # atmarkit
# os.putenv関数による環境変数の設定はos.environ属性には影響を及ぼさない
os.putenv('SOME_ENV_VAR', 'Windows Insider')
value = os.getenv('SOME_ENV_VAR')
print(value) # Deep Insider
# os.putenv関数で設定した環境変数は子プロセスに影響を及ぼす
# Windows(コマンドプロンプト):
# _ = os.system('echo %SOME_ENV_VAR%') → Windows Insider
# macOS(zsh):
# _ = os.system('echo $SOME_ENV_VAR') → Windows Insider
# 環境変数の削除
os.environ['FOO'] = 'foo' # 削除用に環境変数を設定
os.environ['BAR'] = 'bar'
os.environ['BAZ'] = 'baz'
del os.environ['FOO'] # del文で削除
value = os.getenv('FOO')
print(value) # None:削除されていることを確認
os.environ.pop('BAR') # os.environ.popメソッドで削除
value = os.getenv('BAR')
print(value) # None:削除されていることを確認
os.unsetenv('BAZ') # os.unsetenv関数で削除
value = os.getenv('BAZ')
print(value) # baz:os.unsetenv関数はos.environ属性に影響を及ぼさない
# os.environ属性で環境変数の値を変更/削除しても影響があるのはプログラム内のみ
# Windows(コマンドプロンプト):
# echo %SOME_ENV_VAR% → Deep Insider
# py -c "import os; os.environ['SOME_ENV_VAR'] = 'atmarkit'; print(os.environ['SOME_ENV_VAR'])" → atmarkit
# echo %SOME_ENV_VAR% → Deep Insider
# macOS(zsh):
# echo $SOME_ENV_VAR → Deep Insider
# python3 -c "import os; os.environ['SOME_ENV_VAR'] = 'atmarkit'; print(os.environ['SOME_ENV_VAR'])" → atmarkit
# echo $SOME_ENV_VAR → Deep Insider
Pythonを実行している環境で設定されている環境変数の値を取得/変更/削除するには以下の表に示すようにosモジュールのenviron属性や関数を使用する。
操作 | 方法 | 備考 |
---|---|---|
環境編集の取得 | os.environ['環境変数名'] os.getenv('環境変数名') |
os.environ['環境変数名']は指定した環境変数がなければ例外を発生させる os.getenv関数は指定した環境変数がなければ既定の値を返す |
環境変数の設定 | os.environ['環境変数名'] = 値 os.putenv('環境変数名', '値') |
os.putenv関数は現在のos.environ属性には影響を及ぼさない |
環境変数の削除 | del os.environ['環境変数名'] os.environ.pop('環境変数名') os.unsetenv('環境変数名') |
os.unsetenv関数は現在のos.environ属性に影響を及ぼさない |
環境変数の取得/設定/削除 |
備考にもある理由から、基本的にはos.environ属性を直接操作するのが推奨される。
以下では、これらの方法と注意点を順に見ていこう。なお、ここではスクリプトを実行する環境で「Deep Insider」という値の環境変数SOME_ENV_VARが設定されているものとする。
例えば、Windowsのコマンドプロンプトを使っているのであれば、次のようにsetコマンドで環境変数の値を設定できる。
> set SOME_ENV_VAR=Deep Insider
また、macOSのzshを使っているのであれば、次のようにexportコマンドで環境変数を設定できる(Linuxでzshなどのシェルを使っている場合も同様だろう)。
% export SOME_ENV_VAR="Deep Insider"
環境変数を取得するには次の2つの方法がある。
os.environ属性は辞書のような環境変数名をキーとするマッピングオブジェクトであり、角かっこ「[]」に環境変数名を指定することで、その値を取得できる。os.getenv関数は引数に環境変数名を指定して呼び出すと、その値が返送される。
以下はos.environ属性の使用例だ。
import os
value = os.environ['SOME_ENV_VAR']
print(value) # Deep Insider
ここでは環境変数SOME_ENV_VARの値を取得するものだ。上で述べたようにその値は「Deep Insider」としているので、ここではこれが得られる。
なお、存在しない環境変数の名前を指定すると、KeyError例外が発生する。以下は存在しない環境変数NOT_EXISTS_ENV_VARの値を取得しようとするコード例だ。このコードを実行するとKeyError例外となる。
value = os.environ['NOT_EXISTS_ENV_VAR'] # KeyError
これに対して、os.getenv関数は指定した名前の環境変数が存在しなかったときには、例外を発生させるのではなく第2引数の値が返送される。第2引数のデフォルト値はNoneになっているので、特に指定をしなければ、指定した名前の環境変数がないときにはNoneが返送される。
以下に例を示す。
value = os.getenv('SOME_ENV_VAR')
print(value) # Deep Insider
value = os.getenv('NOT_EXISTS_ENV_VAR')
print(value) # None
最初の例では環境変数名にSOME_ENV_VARを指定している。そのため、戻り値は上と同じ「Deep Insider」となる。次の例では存在しない環境変数の名前としてNOT_EXISTS_ENV_VARを指定しているが、このときには第2引数のデフォルト値であるNoneが返送されている。
環境変数を設定するには以下の方法がある。
このとき新しい値には文字列値を指定すること。また、os.putenv関数は現在のos.environ属性には影響を及ぼさないことにも注意が必要だ(もうひとつ、環境変数の上書きや新規作成はあくまでもPython内でのみ有効である点にも注意されたい。後述)。
以下はos.environ['SOME_ENV_VAR']に新しい値として文字列'atmarkit'を代入する例だ。
os.environ['SOME_ENV_VAR'] = 'atmarkit'
value = os.environ['SOME_ENV_VAR']
print(value) # atmarkit
これを見ると、環境変数SOME_ENV_VARの値が変更されていることが確認できる。次に、os.putenv関数を使って、この環境変数の値を'Windows Insider'に変更してみよう。
os.putenv('SOME_ENV_VAR', 'Windows Insider')
value = os.getenv('SOME_ENV_VAR')
print(value) # Deep Insider
この例を見ると、os.putenv関数で環境変数SOME_ENV_VARの値を'Windows Insider'に変更しているのにもかかわらず、os.environ['SOME_ENV_VAR']を参照しても、その値は変更前のままとなっている。では、変更した影響はどこに出ているのかというと、このスクリプトから起動する子プロセスの環境変数となる。
例えば、以下のコードはmacOS上で実行されているPython環境からzshを子プロセスで起動して、echoコマンドを実行するものだ(先頭の「_ = …‥」は戻り値の表示を抑制するため)。
_ = os.system('echo $SOME_ENV_VAR')
これを実行すると、コンソールに「Windows Insider」と表示される。実際の実行結果を以下に示す(os.putenv関数が現在のos.environ属性に影響を及ぼさない点も確認されたい)。
同じことをWindowsのコマンドプロンプトで行った結果も以下に示しておく。
このようなことから、環境変数の値を変更するにはos.putenv関数を使うのではなく、os.environ属性を使うことが推奨される。
また、os.putenv関数のドキュメントには「FreeBSD と macOS を含む一部のプラットフォームでは、 environ の値を変更するとメモリリークの原因になる場合があります。システムの putenv() に関するドキュメントを参照してください」とある。環境変数の値を書き換えるときにはこうした点にも留意しよう。
環境変数を削除するには以下の方法がある。
ここではまず次のようにして、環境変数を3つ作成しておこう。
os.environ['FOO'] = 'foo'
os.environ['BAR'] = 'bar'
os.environ['BAZ'] = 'baz'
そして、上で見た3つの方法でこれらを削除していくことにする。以下はdel文とpopメソッドを使って、環境変数を削除するコード例だ。
del os.environ['FOO'] # del文で削除
value = os.getenv('FOO')
print(value) # None:削除されていることを確認
os.environ.pop('BAR') # os.environ.popメソッドで削除
value = os.getenv('BAR')
print(value) # None:削除されていることを確認
del文とpopメソッドを使う場合は、os.environ属性からも該当する環境変数が削除されていることが分かる。
次にos.unsetenv関数を使う例を示す。
os.unsetenv('BAZ') # os.unsetenv関数で削除
value = os.getenv('BAZ')
print(value) # baz:os.unsetenv関数はos.environ属性に影響を及ぼさない
os.unsetenv関数を使った場合は、os.putenv関数と同様に環境変数の削除が現在のos.environ属性には反映されない。よって、現在の環境に対して削除を行うのであれば、del文やpopメソッドを使う方がよいだろう。
os.putenv関数やos.unsetenv関数による変更のみならず、os.environ['環境変数名']への値の代入、del文やpopメソッドによる削除による変更についても注意しておくべきことがある。それはPythonプログラム内での環境変数の変更はそれを起動したプロセスとは無関係であるということだ。
つまり、Pythonプログラム内で環境変数の値を変更しても、Pythonプログラムを起動した側で該当する環境変数の値が変更されるわけではない。
このことは以下のようなスクリプトをシェルやコマンドプロンプトで実行してみると分かるだろう(以下はmacOS上で動作するzshで実行するもの)。
% echo $SOME_ENV_VAR
% python3 -c "import os; os.environ['SOME_ENV_VAR'] = 'atmarkit'; print(os.environ['SOME_ENV_VAR'])"
% echo $SOME_ENV_VAR
1行目では環境変数SOME_ENV_VARの値を表示している。次にワンライナーのPythonプログラムを実行して、Python環境内でその環境変数の値を変更している。最後にもう一度、シェルで定義されている環境変数の値を表示している。
実行結果は以下の通りだ。
このように、Pythonプログラムを起動した環境では、Pythonプログラム内での変更は反映されない。逆にPythonプログラム起動時に環境変数が読み込まれた後に、システム側で環境変数の値が変更されても、それらがPythonプログラム側に反映されることはない。
Copyright© Digital Advantage Corp. All Rights Reserved.