Skip to content
tezvyn:

asyncio Event Loop Policies: A Deprecated Pattern

Source: docs.python.orgHardHow cards are made

asyncio Event Loop Policies: A Deprecated Pattern

Think of an event loop policy as the global factory for asyncio's event loops, controlling which loop is created and how it's retrieved. It was used to swap implementations, but the entire API is deprecated in Python 3.14 and will be removed in 3.16.

Why it exists

Asyncio needed a centralized, configurable way to manage the creation and retrieval of event loops across a process. Policies provided a global switch to change the default loop implementation or add cross-cutting logic without modifying every call site that needed a loop.

The mental model

Think of the event loop policy as the "foreman" for your async code. When a new thread needs an event loop (a "workspace"), it asks the foreman. The foreman decides what kind of workspace to provide (e.g., a standard SelectorEventLoop or a high-performance uvloop) and keeps track of which thread is using which workspace. This global control is powerful but also fragile, which is why it's being replaced.

How it works

An event loop policy is a class that implements the AbstractEventLoopPolicy interface. The key methods are new_event_loop() to create a loop, get_event_loop() to retrieve the current context's loop, and set_event_loop() to assign a loop to the current context. You set a single, process-wide policy using asyncio.set_event_loop_policy(). By default, Python uses DefaultEventLoopPolicy, which provides SelectorEventLoop on Unix and ProactorEventLoop on Windows.

When to use it

In legacy code (Python < 3.14), you would use a custom policy to globally install a different event loop implementation, such as uvloop, for a performance boost. You might also use it to wrap event loops with monitoring or debugging logic that you want applied consistently everywhere a loop is created or accessed.

When not to use it

Do not use this pattern in new code. The entire policy API is deprecated in Python 3.14 and will be removed in Python 3.16. Global state modification is fragile and can lead to unexpected behavior in complex applications or libraries. The modern, preferred approach is to explicitly manage loop creation using asyncio.Runner(loop_factory=...) or asyncio.run(loop_factory=...), which provides local, explicit control instead of global, implicit side effects.

One canonical example

A common historical use was installing the uvloop policy. You would create a custom policy class that overrides new_event_loop to return a uvloop.new_event_loop() instance. Then, at your application's entry point, you would call asyncio.set_event_loop_policy(MyUvloopPolicy()). This globally replaced the default event loop with the higher-performance uvloop for all subsequent asyncio operations. This is now an anti-pattern.

Interview question

Which of the following best describes the primary historical use case that led to the creation and adoption of custom asyncio event loop policies?

  • a.To enforce strict isolation of event loops between different threads within the same process.
  • b.To allow individual asynchronous functions to specify their preferred event loop type.
  • c.To globally substitute the default event loop implementation with a custom or higher-performance alternative.Correct
  • d.To provide a mechanism for dynamically pausing and resuming event loops based on system resource availability.
Why?

The card explicitly states that a primary use case for custom policies was "to globally install a different event loop implementation, such as uvloop, for a performance boost." Option A is a function of how policies manage loops, but the *custom* policy's main historical motivation was changing the *type* of loop.

Just read this? Test yourself on what you have been reading.

Read the original → docs.python.org

You just looked this up. Could you explain it out loud?

That is the part interviews actually test. Tezvyn takes questions like this one and gives you what the interviewer is really checking, the answer that lands, and the mistake that ends the conversation, in the four minutes before your next meeting.

The iPhone app is on the way

We are building it. Until it lands, nothing here is held back from you: every interview card, your saved cards, streaks and the job board all work in Safari, plus hundreds of free practice quizzes of thirty questions each. Sign in and it all carries over to the app the day it arrives.

Want it as an icon? Tap Share at the bottom of Safari, then Add to Home Screen. It opens full screen and the cards you have read stay available offline.

Get it on Google PlayiPhone app coming soon

We are hiring for this. Open roles that interview on python — each one lists the topics its interview covers.

See open roles