[Python 3.10の課題] 非推奨
By manhnv, at: 2025年8月12日21:12
Estimated Reading Time: __READING_TIME__ minutes


1) collections から X のインポート (Mapping/MutableMapping/Iterable など) が失敗します
症状
-
ImportError: cannot import name 'Mapping' from 'collections'
-
MutableMapping
、Iterable
、Sequence
などに対する同様のエラー。
理由
ABCs は 3.10 で collections からの再エクスポートを停止しました。collections.abc
からインポートする必要があります。これは長年警告されていましたが、3.10 でついに変更されました。
修正 (ドロップイン)
# 旧
from collections import Mapping, MutableMapping, Iterable
# 新
from collections.abc import Mapping, MutableMapping, Iterable
次回の予防策
-
コードとテンプレートを
from collections import
で grep します。
-
linter ルールまたは CI チェックを追加して、
from collections import (Mapping|MutableMapping|Iterable|...).
で失敗するようにします。
-
依存関係がまだ
from collections をインポート
している場合は、それをアップグレードするか、ローカルでパッチを適用します。
2) parser モジュールの削除
症状
-
ModuleNotFoundError: No module named 'parser'
-
古い LL(1) パーサーの内部に依存していたツールが機能しなくなります。
理由
CPython は 3.9 でPEG パーサーに切り替えました。レガシーパーサーモジュールと関連する C API は3.10 で削除されました。
修正 / Migration パス
-
Python コードを解析していた場合: ast または LibCST / Parso のようなモダンなライブラリを使用します。
-
lib2to3/pgen2 スタイルの文法に依存していた場合、移行を計画してください。それらは将来の文法変更を確実に解析しません。
次回の予防策
-
文書化されていない内部に依存することを避け、ast とよくメンテナンスされた解析ライブラリを優先します。
-
アップグレードする前に、各 What’s New の「削除されたもの」セクションをざっと読みます。
3) asyncio の loop= パラメータの削除
症状
-
TypeError: ... got an unexpected keyword argument 'loop'
-
asyncio.Queue(loop=loop)、asyncio.Lock(loop=loop)、asyncio.gather(..., loop=loop) のような失敗するコード。
理由
loop= は非推奨でしたが、3.10 ではほとんどのハイレベル API から削除されました。イベントループは、asyncio.get_running_loop() を介して検出されるか、asyncio.run() によって管理されます。
修正 (一般的なパターン)
# 旧
loop = asyncio.get_event_loop()
q = asyncio.Queue(loop=loop)
lock = asyncio.Lock(loop=loop)
# 新
async def main():
q = asyncio.Queue()
lock = asyncio.Lock()
asyncio.run(main())
-
ループオブジェクトが必要ですか? コルーチンの内部で:
loop = asyncio.get_running_loop().
-
タスクの作成: 実行中のコード内で
asyncio.create_task()
を優先します。
次回の予防策
-
非同期スタイルを「モダン」に保ちます: asyncio.run、create_task、get_running_loop は必要な場合にのみ使用します。
-
ライブラリでは、ループの管理をユーザーに公開しないようにします。
4) distutils の非推奨警告
症状
-
次のような警告: distutils は非推奨であり、Python 3.12 で削除される予定です。
理由
PEP 632: distutils は3.10 で非推奨となり、3.12 で完全に削除されました。
修正 (モダンなビルドバックエンド)
-
pyproject.toml ビルドに Setuptools/Flit/Hatch を使用して移行します。
例:
# pyproject.toml
[build-system]
requires = ["setuptools>=64", "wheel"]
build-backend = "setuptools.build_meta"
-
from distutils... のインポートを Setuptools または packaging の同等のものに置き換えます。
次回の予防策
-
PyPA および PEP の更新を追跡し、削除が予定されている標準ライブラリのパッケージング API を避けます。
5) 小さいが注目すべき落とし穴
-
importlib の移行 (find_module → find_spec): pkgutil.find_loader/imp.find_module を使用する古いパターンは importlib.util.find_spec に移動する必要があります。
-
C API / 埋め込みの変更: C 拡張機能をメンテナンスしている場合は、Python 3.10 C API の変更を読んでください。
アップグレードプレイブック
-
早期に 3.10 でテストを実行します (tox/CI マトリックスを使用)。
-
非推奨で失敗:
pytest -W error::DeprecationWarning
-
修正を自動化: from collections import を collections.abc に置き換え、asyncio で loop= を削除します。
-
pyproject.toml でパッケージングを最新化します。
-
依存関係をピン留めしてアップグレードします。
-
ロールアウト前に 3.10 の新機能を読みます。