#1811·tqdm

`tqdm.asyncio.as_completed` 拒绝由 `asyncio.as_completed` 支持的生成器

作者: yayong3创建于 2026年9月3日更新于 2026年9月3日
  • I have marked all applicable categories:
    • exception-raising bug
    • visual output bug
  • I have visited the [source website], and in particular read the [known issues]
  • I have searched through the [issue tracker] for duplicates
  • I have mentioned version numbers, operating system and environment, where applicable:
    python
    import tqdm, sys
    print(tqdm.__version__, sys.version, sys.platform)

Summary

Since Python 3.12, asyncio.as_completed accepts generators that yield tasks. The tqdm wrapper rejects the same input when total is omitted because it calls len(fs) unconditionally:

Reproduction

python
import asyncio
from tqdm.asyncio import tqdm_asyncio


async def main():
    tasks = (
        asyncio.create_task(asyncio.sleep(0, result=value))
        for value in range(3)
    )
    results = []
    for future in tqdm_asyncio.as_completed(tasks):
        results.append(await future)
    print(results)
asyncio.run(main())

On Python 3.12.3 Output:

Traceback (most recent call last):
  File "/home/test.py", line 17, in <module>
    asyncio.run(main())
  File "/usr/lib/python3.12/asyncio/runners.py", line 194, in run
    return runner.run(main)
           ^^^^^^^^^^^^^^^^
  File "/usr/lib/python3.12/asyncio/runners.py", line 118, in run
    return self._loop.run_until_complete(task)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/lib/python3.12/asyncio/base_events.py", line 687, in run_until_complete
    return future.result()
           ^^^^^^^^^^^^^^^
  File "/home/test.py", line 12, in main
    for future in tqdm_asyncio.as_completed(tasks):
  File "/home/tqdm/tqdm/asyncio.py", line 67, in as_completed
    total = len(fs)
            ^^^^^^^
TypeError: object of type 'generator' has no len()

Passing the same generator directly to asyncio.as_completed works. A list works with either implementation, and explicitly passing total=3 also avoids the failure.