歩いたら休め

If the implementation is easy to explain, it may be a good idea.

【Python】pip installで突如UnicodeDecodeErrorが出始めたので対処した

Github上にアップした自作のPythonモジュールをインストールしようとしたところ、UnicodeDecodeErrorが出てしまいました。

$ pip install --upgrade git+https://github.com/takeshi0406/twlist_to_urllist
Exception:
Traceback (most recent call last):
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/basecommand.py", line 215, in main
    status = self.run(options, args)
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/commands/install.py", line 272, in run
    with self._build_session(options) as session:
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/basecommand.py", line 72, in _build_session
    insecure_hosts=options.trusted_hosts,
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/download.py", line 329, in __init__
    self.headers["User-Agent"] = user_agent()
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/download.py", line 93, in user_agent
    from pip._vendor import distro
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/_vendor/distro.py", line 1051, in <module>
    _distro = LinuxDistribution()
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/_vendor/distro.py", line 594, in __init__
    if include_lsb else {}
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/_vendor/distro.py", line 922, in _lsb_release_info
    stdout, stderr = stdout.decode('ascii'), stderr.decode('ascii')
UnicodeDecodeError: 'ascii' codec can't decode byte 0xe3 in position 22: ordinal not in range(128)
Traceback (most recent call last):
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/bin/pip", line 11, in <module>
    sys.exit(main())
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/__init__.py", line 233, in main
    return command.main(cmd_args)
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/basecommand.py", line 251, in main
    timeout=min(5, options.timeout)) as session:
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/basecommand.py", line 72, in _build_session
    insecure_hosts=options.trusted_hosts,
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/download.py", line 329, in __init__
    self.headers["User-Agent"] = user_agent()
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/download.py", line 93, in user_agent
    from pip._vendor import distro
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/_vendor/distro.py", line 1051, in <module>
    _distro = LinuxDistribution()
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/_vendor/distro.py", line 594, in __init__
    if include_lsb else {}
  File "/home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages/pip/_vendor/distro.py", line 922, in _lsb_release_info
    stdout, stderr = stdout.decode('ascii'), stderr.decode('ascii')
UnicodeDecodeError: 'ascii' codec can't decode byte 0xe3 in position 22: ordinal not in range(128)

「Anacondaを使っているせいでは?」「サーバーの文字コードの設定がおかしいのでは?」とも疑ったのですが、以前は同じサーバーで動作していたし、そもそも通常のPythonでも同様の現象が置きており、pip自体のバグのようでした。

エラー文に従い、site-packages/pip/_vendor/distro.pyの922行目を

        stdout, stderr = stdout.decode('ascii'), stderr.decode('ascii') 

から

        stdout, stderr = stdout.decode('utf-8'), stderr.decode('utf-8') 

に書き換えたところ、動作するようになりました。(標準出力や標準エラー出力を処理している箇所のようでした。)

どうやら、pipのバージョンを上げた際に動作しなくなっていたようです。

$ pip --version
pip 9.0.0 from /home/takeshi/.pyenv/versions/anaconda3-2.5.0/lib/python3.5/site-packages (python 3.5)

11月8日追記

issueとして報告しようと確認したところ、既にpip9.0.1のバージョンでこの問題は解決されていました。

github.com