Skip to content

Python 3.10で発生する「ImportError: cannot import name 'Mapping' from 'collections'」の解決方法

問題の概要

Python 3.10にアップグレードした後に、プログラムの実行時に以下のエラーが発生する場合があります:

python
ImportError: cannot import name 'Mapping' from 'collections' (/path/to/python3.10/collections/__init__.py)

このエラーは一般的に、サードパーティのライブラリ(この例ではJinja2)がcollectionsモジュールからMappingをインポートしようとして発生します。

WARNING

このエラーはPython 3.10の変更によるもので、Python 3.3以降では非推奨とされていたcollectionsからのABC(抽象基底クラス)のインポートが、Python 3.10で完全に削除されたことに起因しています。

根本原因

Python 3.9以前では、以下のコードは警告を出力しながらも動作していました:

python
>>> from collections import Mapping
<stdin>:1: DeprecationWarning: Using or importing the ABCs from 'collections' instead of from 'collections.abc' is deprecated since Python 3.3, and in 3.10 it will stop working

Python 3.10ではこの非推奨機能が削除され、Mappingやその他の抽象基底クラス(SequenceMutableMappingなど)はcollections.abcモジュールからのみインポート可能になりました。

解決方法

方法1: ライブラリのアップデート(推奨)

最も効果的な解決策は、問題を引き起こしているライブラリを最新バージョンにアップデートすることです:

bash
pip install <package-name> --upgrade

特定のケースでは以下のライブラリの更新が有効な場合があります:

  • Jinja2 (Flaskテンプレートエンジン)
  • PyJWT (JWTトークン処理)
  • Requests (HTTPリクエストライブラリ)
  • python-docx (Word文書処理)

INFO

多くの主要ライブラリは既にPython 3.10互換のバージョンをリリースしているため、アップデートが最善の解決策です。

方法2: インポート文の修正

問題が自身のコードで発生している場合、インポート文を修正します:

python
# 変更前(非推奨)
from collections import Mapping

# 変更後(推奨)
from collections.abc import Mapping

後方互換性を保つ場合

古いPythonバージョンとの互換性が必要な場合は、以下のように例外処理を使用します:

python
try:
    from collections.abc import Mapping
except ImportError:
    from collections import Mapping

方法3: Pythonバージョンの切り替え

一時的な解決策として、互換性のあるPythonバージョン(3.9以下)を使用する方法もあります。

pipenvを使用する場合

bash
pipenv --rm        # 仮想環境を削除
vim Pipfile        # Pythonバージョンを '3.9' に変更
pipenv shell       # 新しい仮想環境を作成
pipenv install     # 依存関係をインストール

virtualenvを使用する場合

bash
virtualenv --python="/path/to/python3.9" "env_name"

方法4: すべてのパッケージを更新

依存関係をすべて最新版に更新する:

bash
pip3 list --outdated --format=freeze | grep -v '^\-e' | cut -d = -f 1 | xargs -n1 pip3 install -U

よくある質問

Q: どのライブラリがこの問題を引き起こしますか?

A: Jinja2、PyJWT、Requests、python-docxなど、多くのライブラリで発生する可能性があります。トレースバックを確認して問題のライブラリを特定してください。

Q: Python 3.10.2では修正されましたか?

A: いいえ、これはPythonの設計上の変更であり、バグ修正ではありません。Python 3.10系全体でこの動作は変わりません。

非推奨の回避策

collections/__init__.pyファイルを直接修正する方法は強く非推奨です。これはシステムの整合性を損ない、将来の更新で問題が再発する可能性があります。

まとめ

Python 3.10でcollectionsからのインポートエラーが発生した場合の解決策は、優先順位に応じて:

  1. 問題のライブラリを最新版に更新する
  2. 自身のコードのインポート文をcollections.abcに修正する
  3. 一時的にPython 3.9以下のバージョンを使用する

ライブラリの更新は最もクリーンな解決策であり、長期的な互換性を確保できます。サードパーティライブラリを使用する場合は、常に最新バージョンの使用を心がけましょう。