これは何?
WSL(windows subsystem for linux)でpipenv installが失敗する症状への対処方法。
たまに遭遇し、忘れて調べ直すことが多いので書いておく。ちなみにWSL1での症状。
症状
こんな感じでOSErrorが出る。
/mnt/c/User/%USERNAME%/AppData/Local/Microsoft/WindowsApps/python.exe
と、Windows側のWindowsAppsディレクトリにあるpython.exeが呼ばれてしまって失敗している。
対処法
windowsスタートメニュー>設定>アプリ>アプリ実行エイリアス>アプリインストーラーのpython.exeを(念の為python3.exeも)オフにする。
対策後はpipenv install に成功する。
⚠注意事項⚠
このアプリ実行エイリアスをオフにしたままだと、なぜかMicrosoftストアでUbuntuのインストールできなくなる(「入手する」を押しても一向にインストールが始まらなくなる1)ので注意。なのでpipenv installが成功したらオンに戻しておくと良いかも。
WSL本体のインストールにはアプリ実行エイリアスの有効化が必要で、WSL側のpipenv installでは無効化が必要とか意地が悪い状態になってしまっている。。。
不具合の要因
Windowsの仕様が悪さしていると思われる。
参考Tweet:
Windows 10 puts a fake python/3 executable in the path, ahead of the actual python. This breaks scripts and has caused me problems on nearly every cross-platform project I work on.
— Morgan McGuire (@CasualEffects) May 3, 2020
The fake executable redirects to the Windows store:https://t.co/SlooMH8JHF
解決策をみつけたGitHubのIssue:
ざっと上記リンクに目を通したところ、C:\Users\%USERNAME%\AppData\Local\Microsoft\WindowsApps\
に置かれているpython.exeとpython3.exeはPython本体でなく、MicrosoftストアのPython入手画面へ飛ばす機能になっているようだ。
Microsoftは「Pythonをインストールしていない人がターミナルでPythonを実行しようとしたらインストールを促してあげよう」と考えたのか、このおせっかいな便利機能(?)をpython.exe/python3.exeと、”Python本体と同じ名前”で追加した模様。
この”偽のPython”がアプリ実行エイリアスでオンオフできるpython/python3の正体らしい。
このおせっかい機能がWindowsアップデートで配信された後、この機能へのパス(WindowsAppsへのパス)がpython本体のパスより上位になっている場合、Pythonがインストール済みでもPython本体を実行できなくなる(毎回Microsoftストアに飛ばされる)という問題が起きていた2。
この問題に関しては、(前述のアプリ実行エイリアスの無効化以外に)Python本体へのパスをWindowsAppsへのパスよりも上位に置くことで対策ができた…のだが、なぜかWSL側のpipenvではパスの優先順位にかかわらず、この”偽のPython”へのパスを最優先で参照してしまう、という症状があるようだ。
よって、前述の方法によってアプリ実行エイリアス自体を無効化しない限り3、pipenv installに失敗する、という話らしい。
まとめ
WSL側のPythonで、/Microsoft/WindowsApps/python.exe
絡みのエラーが起きたら、アプリ実行エイリアスを無効化する。
ただし、WSL本体のインストールで問題が起きるかもしれないので、エラーが解消したらアプリ実行エイリアスをオンに戻す。
-
この症状になる。WSL の Ubuntu 18.04 がインストールできない
↩ -
このアップデートは既存のプロジェクトにめちゃくちゃ悪影響を与えたようで、この変更を含んだWindowsアップデートを告知するブログ記事には批判コメントが殺到していた。
↩ -
WSL側にpyenvを導入し、pyenv globalでpyhonコマンドの参照先を任意verのPyhonに変えてもこの問題は回避でなかった…
↩