コマンドラインのイントロスペクションツール

ソースコード: Lib/asyncio/tools.py


asyncio モジュールは python -m asyncio でスクリプトとして実行でき、実行中の別の Python プロセスを変更したり再起動したりせずに、そのタスクグラフを調べられます。 このインターフェースは asyncio.tools サブモジュールが実装しています。

次のコマンドは、PID で指定したプロセスを調べます。

$ python -m asyncio pstree [--retries N] PID
$ python -m asyncio ps [--retries N] PID

これらのコマンドは、対象プロセス内でコードを実行せずに、その状態を読み取ります。 サポートされているプラットフォームでのみ利用でき、別のプロセスを調べるための権限が必要な場合があります。 詳しくは 必要な権限 を参照してください。

参考

呼び出しグラフのイントロスペクション

現在のプロセス内の Task や Future の非同期呼び出しグラフを、プログラムから調べるための API です。

以下のコマンド例では、調査用のタスク階層を作成してプロセス ID を表示する次のプログラムを使います。

example.py
import asyncio
import os

async def play(track):
    await asyncio.sleep(3600)
    print(f"🎵 Finished: {track}")

async def album(name, tracks):
    async with asyncio.TaskGroup() as tg:
        for track in tracks:
            tg.create_task(play(track), name=track)

async def main():
    print(f"PID: {os.getpid()}")
    async with asyncio.TaskGroup() as tg:
        tg.create_task(
            album("Sundowning", ["TNDNBTG", "Levitate"]),
            name="Sundowning",
        )
        tg.create_task(
            album("TMBTE", ["DYWTYLM", "Aqua Regia"]),
            name="TMBTE",
        )

asyncio.run(main())

1 つの端末でプログラムを起動し、実行したままにします。

$ python example.py
PID: 12345

次に、表示されたプロセス ID を、別の端末からコマンドに渡します。 スレッド ID、タスク ID、ファイルパス、行番号は、実行時やソースコードの配置によって異なります。

Added in version 3.14.

コマンドラインオプション

pstree PID

タスクとコルーチンの関係をツリーとして表示します。 各タスクはコルーチンのスタック全体とともに表示され、そのタスクを await しているタスクがあれば、その下に入れ子で配置されます。 このサブコマンドは、タスク階層のどの枝がブロックしていて、コルーチンのスタックのどこで実行が止まっているかを素早く把握するのに役立ちます。

$ python -m asyncio pstree 12345
└── (T) Task-1
    └──  main example.py:12
        └──  TaskGroup.__aexit__ Lib/asyncio/taskgroups.py:75
            └──  TaskGroup._aexit Lib/asyncio/taskgroups.py:124
                ├── (T) Sundowning
                │   └──  album example.py:7
                │       └──  TaskGroup.__aexit__ Lib/asyncio/taskgroups.py:75
                │           └──  TaskGroup._aexit Lib/asyncio/taskgroups.py:124
                │               ├── (T) TNDNBTG
                │               │   └──  play example.py:4
                │               │       └──  sleep Lib/asyncio/tasks.py:702
                │               └── (T) Levitate
                │                   └──  play example.py:4
                │                       └──  sleep Lib/asyncio/tasks.py:702
                └── (T) TMBTE
                    └──  album example.py:7
                        └──  TaskGroup.__aexit__ Lib/asyncio/taskgroups.py:75
                            └──  TaskGroup._aexit Lib/asyncio/taskgroups.py:124
                                ├── (T) DYWTYLM
                                │   └──  play example.py:4
                                │       └──  sleep Lib/asyncio/tasks.py:702
                                └── (T) Aqua Regia
                                    └──  play example.py:4
                                        └──  sleep Lib/asyncio/tasks.py:702

await の関係を表すグラフに循環がある場合、pstree はツリーを表示せずにエラーを報告します。 このグラフに循環があるのはまれで、通常はプログラムの誤りを示します。

$ python -m asyncio pstree 12345
ERROR: await-graph contains cycles - cannot print a tree!

cycle: Task-2 → Task-3 → Task-2
ps PID

プロセス PID 内の未完了のタスクをすべて、階層のない表で表示します。 各行には、イベントループのスレッド ID、タスクの ID と名前、コルーチンのスタックを表示します。 そのタスクを await しているタスクがあれば、そのスタック、名前、ID も表示します。

このサブコマンドは、await の関係を表すグラフに循環があるかどうかにかかわらず、すべてのタスクを表示します。

$ python -m asyncio ps 12345
tid        task id              task name            coroutine stack                                    awaiter chain                                      awaiter name    awaiter id
------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
18445801   0x10a456060          Task-1               TaskGroup._aexit -> TaskGroup.__aexit__ -> main                                                                       0x0
18445801   0x10a439f60          Sundowning           TaskGroup._aexit -> TaskGroup.__aexit__ -> album   TaskGroup._aexit -> TaskGroup.__aexit__ -> main    Task-1          0x10a456060
18445801   0x10a439d70          TMBTE                TaskGroup._aexit -> TaskGroup.__aexit__ -> album   TaskGroup._aexit -> TaskGroup.__aexit__ -> main    Task-1          0x10a456060
18445801   0x10a2a3a80          TNDNBTG              sleep -> play                                      TaskGroup._aexit -> TaskGroup.__aexit__ -> album   Sundowning      0x10a439f60
18445801   0x10a2a38a0          Levitate             sleep -> play                                      TaskGroup._aexit -> TaskGroup.__aexit__ -> album   Sundowning      0x10a439f60
18445801   0x10a2d7150          DYWTYLM              sleep -> play                                      TaskGroup._aexit -> TaskGroup.__aexit__ -> album   TMBTE           0x10a439d70
18445801   0x10a6bdaa0          Aqua Regia           sleep -> play                                      TaskGroup._aexit -> TaskGroup.__aexit__ -> album   TMBTE           0x10a439d70
--retries N

対象プロセスの調査に失敗した場合、最大 N 回再試行します。 状態の読み取り中に対象プロセスが変化する場合に役立ちます。

Added in version 3.15.