Skip to content

Conversation

@SamMorrowDrums
Copy link

Summary

Fixes #3708

The test suite hangs indefinitely when upgrading websockets from 13.x to 14.x or 15.x. This is because websockets 14.0 switched to a new asyncio implementation by default, which has different behavior around event loop handling.

Root Cause

The issue stems from how the TestServer manages event loops when running in a background thread:

  1. In TestServer.serve(): The deprecated asyncio.get_event_loop() + loop.create_task() pattern doesn't work correctly with websockets 14+'s new asyncio handling
  2. In serve_in_thread(): The server.run() method relies on asyncio.run() which doesn't play well with the threaded setup when websockets is involved

Changes

  1. TestServer.serve(): Replace deprecated asyncio.get_event_loop() pattern with asyncio.create_task() which is the modern way to create tasks when already inside an async context.

  2. serve_in_thread(): Instead of relying on server.run() which uses asyncio.run(), explicitly create a new event loop in the background thread with asyncio.new_event_loop() and asyncio.set_event_loop().

  3. server fixture: Remove loop="asyncio" from Config() since we now manage the event loop manually, avoiding conflicts with websockets' asyncio implementation.

Testing

Tested locally with websockets 15.0.1 - all 43 integration tests pass without hanging.

The test suite hangs after upgrading websockets from 13.x to 14.x/15.x
because websockets 14.0 switched to a new asyncio implementation by default.

Changes:
1. In TestServer.serve(): Replace deprecated asyncio.get_event_loop()
   pattern with asyncio.create_task() which is the modern way to create
   tasks when already inside an async context.

2. In serve_in_thread(): Instead of relying on server.run() which uses
   asyncio.run(), explicitly create a new event loop in the background
   thread with asyncio.new_event_loop() and asyncio.set_event_loop().

3. Remove loop="asyncio" from Config() since we now manage the event
   loop manually.

This approach is compatible with uvicorn 0.36+ (which removed the
deprecated setup_event_loop() method) and works with websockets 14+.

Fixes encode#3708
@karpetrosyan
Copy link
Contributor

Duplicate of #3693, but thank you very much for the contribution. I will mention you in the fix as a co author!

@mtelka
Copy link
Contributor

mtelka commented Jan 11, 2026

@SamMorrowDrums I applied this change on top of httpx 0.28.1 and testing still hangs for me with Python 3.9.25 and websockets 15.0.1. Any suggestion? Thank you.

@mtelka
Copy link
Contributor

mtelka commented Jan 11, 2026

When I uninstall websockets 15.0.1 then all tests pass.

@mtelka
Copy link
Contributor

mtelka commented Jan 11, 2026

Please note that I use uvicorn 0.39.0.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

3 participants