Цикл событий
Исходный код: Lib/asyncio/events.py, Lib/asyncio/base_events.py
Предисловие
Цикл событий — основа каждого приложения asyncio. Циклы событий выполняют асинхронные задачи и обратные вызовы, выполняют операции сетевого ввода-вывода и запускают подпроцессы.
Разработчикам приложений обычно следует использовать высокоуровневые функции asyncio, например asyncio.run(), и редко обращаться к объекту цикла или вызывать его методы. Этот раздел предназначен преимущественно для авторов кода низкого уровня, библиотек и платформ, которым требуется более тонко управлять поведением цикла событий.
Получение цикла событий
Для получения, установки или создания цикла событий можно использовать следующие низкоуровневые функции:
-
asyncio.get_running_loop() -
Возвращает работающий цикл событий в текущем потоке ОС.
Вызывает
RuntimeError, если работающего цикла событий нет.Эту функцию можно вызывать только из сопрограммы или обратного вызова.
Добавлено в версии 3.7.
-
asyncio.get_event_loop() -
Получает текущий цикл событий.
При вызове из сопрограммы или обратного вызова (например, запланированного с помощью call_soon или аналогичного API) эта функция всегда возвращает работающий цикл событий.
Если работающий цикл событий не установлен, функция возвращает результат вызова
get_event_loop_policy().get_event_loop().Поскольку поведение этой функции достаточно сложно (особенно при использовании пользовательских политик цикла событий), в сопрограммах и обратных вызовах предпочтительнее использовать функцию
get_running_loop(), а неget_event_loop().Как отмечалось выше, рассмотрите возможность использования высокоуровневой функции
asyncio.run()вместо ручного создания и закрытия цикла событий с помощью этих низкоуровневых функций.Устарела с версии 3.12: Если текущего цикла событий нет, выдаётся предупреждение об устаревании. В одном из будущих выпусков Python это станет ошибкой.
-
asyncio.set_event_loop(loop) -
Устанавливает loop в качестве текущего цикла событий для текущего потока ОС.
-
asyncio.new_event_loop() -
Создаёт и возвращает новый объект цикла событий.
Обратите внимание, что поведение функций get_event_loop(), set_event_loop() и new_event_loop() можно изменить, установив пользовательскую политику цикла событий.
Содержание
Эта страница документации содержит следующие разделы:
- В разделе Методы цикла событий приведена справочная документация по API цикла событий;
- В разделе Объекты управления обратными вызовами описаны экземпляры
HandleиTimerHandle, возвращаемые методами планирования, такими какloop.call_soon()иloop.call_later(); - В разделе Объекты сервера описаны типы, возвращаемые методами цикла событий, например
loop.create_server(); - В разделе Реализации цикла событий описаны классы
SelectorEventLoopиProactorEventLoop; - В разделе Примеры показано, как работать с некоторыми API цикла событий.
Методы цикла событий
Циклы событий предоставляют низкоуровневые API для следующих задач:
- Запуск и остановка цикла
- Планирование обратных вызовов
- Планирование отложенных обратных вызовов
- Создание объектов Future и задач
- Открытие сетевых подключений
- Создание сетевых серверов
- Передача файлов
- Переход на TLS
- Отслеживание файловых дескрипторов
- Работа непосредственно с объектами сокетов
- DNS
- Работа с каналами
- Сигналы Unix
- Выполнение кода в пулах потоков или процессов
- API обработки ошибок
- Включение режима отладки
- Запуск подпроцессов
Запуск и остановка цикла
-
loop.run_until_complete(future) -
Выполняет цикл до завершения future (экземпляра
Future).Если аргументом является объект сопрограммы, его выполнение неявно планируется как
asyncio.Task.Возвращает результат Future или вызывает его исключение.
-
loop.run_forever() -
Выполняет цикл событий, пока не будет вызван
stop().Если
stop()вызван до вызоваrun_forever(), цикл один раз опросит селектор ввода-вывода с нулевым временем ожидания, выполнит все обратные вызовы, запланированные в ответ на события ввода-вывода (а также уже запланированные), а затем завершится.Если
stop()вызван во время работыrun_forever(), цикл выполнит текущую группу обратных вызовов, а затем завершится. Обратите внимание: новые обратные вызовы, запланированные другими обратными вызовами, в этом случае выполнены не будут; они запустятся при следующем вызовеrun_forever()илиrun_until_complete().
-
loop.stop() -
Останавливает цикл событий.
-
loop.is_running() -
Возвращает
True, если цикл событий в данный момент работает.
-
loop.is_closed() -
Возвращает
True, если цикл событий закрыт.
-
loop.close() -
Закрывает цикл событий.
При вызове этой функции цикл не должен работать. Все ожидающие обратные вызовы будут отброшены.
Этот метод очищает все очереди и завершает работу исполнителя, но не дожидается завершения исполнителя.
Этот метод идемпотентен и необратим. После закрытия цикла событий нельзя вызывать другие методы.
-
async loop.shutdown_asyncgens() -
Планирует закрытие всех открытых в данный момент объектов асинхронных генераторов с помощью вызова
aclose(). После вызова этого метода цикл событий выдаст предупреждение, если начнётся итерация нового асинхронного генератора. Этот метод следует использовать для надёжного завершения всех запланированных асинхронных генераторов.Обратите внимание: вызывать эту функцию не нужно, если используется
asyncio.run().Пример:
try: loop.run_forever() finally: loop.run_until_complete(loop.shutdown_asyncgens()) loop.close()Добавлено в версии 3.6.
-
async loop.shutdown_default_executor(timeout=None) -
Планирует закрытие исполнителя по умолчанию и дожидается завершения всех потоков в
ThreadPoolExecutor. После вызова этого метода использование исполнителя по умолчанию с помощьюloop.run_in_executor()приведёт к возникновениюRuntimeError.Параметр timeout задаёт время (в секундах
float), которое будет предоставлено исполнителю для завершения потоков. При значении по умолчаниюNoneисполнителю предоставляется неограниченное время.Если время ожидания timeout истечёт, будет выдано предупреждение
RuntimeWarning, а исполнитель по умолчанию будет завершён без ожидания завершения его потоков.Примечание
Не вызывайте этот метод при использовании
asyncio.run(), поскольку эта функция автоматически обрабатывает завершение работы исполнителя по умолчанию.Добавлено в версии 3.9.
Изменено в версии 3.12: Добавлен параметр timeout.
Планирование обратных вызовов
-
loop.call_soon(callback, *args, context=None) -
Планирует вызов callback — обратного вызова — с аргументами args при следующем проходе цикла событий.
Возвращает экземпляр
asyncio.Handle, который впоследствии можно использовать для отмены обратного вызова.Обратные вызовы вызываются в порядке регистрации. Каждый обратный вызов будет вызван ровно один раз.
Необязательный именованный аргумент только для ключевого слова context задаёт пользовательский
contextvars.Context, в котором будет выполняться callback. Если context не указан, обратные вызовы используют текущий контекст.В отличие от
call_soon_threadsafe(), этот метод не является потокобезопасным.
-
loop.call_soon_threadsafe(callback, *args, context=None) -
Потокобезопасный вариант
call_soon(). При планировании обратных вызовов из другого потока необходимо использовать именно эту функцию, посколькуcall_soon()не является потокобезопасным.Эту функцию безопасно вызывать из реентерабельного контекста или обработчика сигналов, однако использовать возвращённый объект управления в таких контекстах небезопасно и нецелесообразно.
Вызывает
RuntimeError, если вызвана для закрытого цикла. Это может произойти во вторичном потоке при завершении работы основного приложения.См. раздел документации параллелизм и многопоточность.
Изменено в версии 3.7: Добавлен параметр context, доступный только по ключевому слову. Подробности см. в PEP 567.
Примечание
Большинство функций планирования asyncio не позволяют передавать именованные аргументы. Для этого используйте functools.partial():
# will schedule "print("Hello", flush=True)"
loop.call_soon(
functools.partial(print, "Hello", flush=True))
Использовать частичные объекты обычно удобнее, чем лямбда-функции, поскольку asyncio лучше отображает частичные объекты в сообщениях отладки и об ошибках.
Планирование отложенных обратных вызовов
Цикл событий предоставляет механизмы планирования функций обратного вызова на определённый момент в будущем. Для отслеживания времени цикл событий использует монотонные часы.
-
loop.call_later(delay, callback, *args, context=None) -
Планирует вызов callback через заданное количество секунд delay (целое число или число с плавающей точкой).
Возвращается экземпляр
asyncio.TimerHandle, который можно использовать для отмены обратного вызова.callback будет вызван ровно один раз. Если два обратных вызова запланированы на одно и то же время, порядок их вызова не определён.
Необязательные позиционные аргументы args будут переданы обратному вызову при его вызове. Чтобы вызвать обратный вызов с именованными аргументами, используйте
functools.partial().Необязательный именованный аргумент только для ключевого слова context позволяет задать пользовательский
contextvars.Context, в котором будет выполняться callback. Если context не указан, используется текущий контекст.Примечание
Для повышения производительности обратные вызовы, запланированные с помощью
loop.call_later(), могут быть выполнены раньше на величину до одного разрешения часов (см.time.get_clock_info('monotonic').resolution).Изменено в версии 3.7: Добавлен параметр context, доступный только по ключевому слову. Подробности см. в PEP 567.
Изменено в версии 3.8: В Python 3.7 и более ранних версиях при реализации цикла событий по умолчанию значение delay не могло превышать одного дня. Это ограничение было устранено в Python 3.8.
-
loop.call_at(when, callback, *args, context=None) -
Планирует вызов callback в заданный момент времени when (целое число или число с плавающей точкой), используя ту же шкалу времени, что и
loop.time().Этот метод ведёт себя так же, как
call_later().Возвращается экземпляр
asyncio.TimerHandle, который можно использовать для отмены обратного вызова.Примечание
Для повышения производительности обратные вызовы, запланированные с помощью
loop.call_at(), могут быть выполнены раньше на величину до одного разрешения часов (см.time.get_clock_info('monotonic').resolution).Изменено в версии 3.7: Добавлен параметр context, доступный только по ключевому слову. Подробности см. в PEP 567.
Изменено в версии 3.8: В Python 3.7 и более ранних версиях при реализации цикла событий по умолчанию разница между when и текущим временем не могла превышать одного дня. Это ограничение было устранено в Python 3.8.
-
loop.time() -
Возвращает текущее время в виде значения
floatсогласно внутренним монотонным часам цикла событий.
Примечание
Изменено в версии 3.8: В Python 3.7 и более ранних версиях тайм-ауты (относительное значение delay или абсолютное значение when) не должны были превышать одного дня. Это ограничение было устранено в Python 3.8.
См. также
Функцию asyncio.sleep().
Создание объектов Future и задач
-
loop.create_future() -
Создаёт объект
asyncio.Future, привязанный к циклу событий.Это предпочтительный способ создания объектов Future в asyncio. Благодаря ему сторонние циклы событий могут предоставлять альтернативные реализации объекта Future (с более высокой производительностью или возможностями инструментирования).
Добавлено в версии 3.5.2.
-
loop.create_task(coro, *, name=None, context=None, **kwargs) -
Планирует выполнение сопрограммы coro. Возвращает объект
Task.Сторонние циклы событий могут использовать собственный подкласс
Taskдля обеспечения взаимодействия. В этом случае результат будет экземпляром подклассаTask.Полная сигнатура функции в основном совпадает с сигнатурой конструктора (или фабрики)
Task— все именованные аргументы этой функции передаются в этот интерфейс, за исключением name и context, если он равенNone.Если аргумент name указан и не равен
None, он устанавливается в качестве имени задачи с помощьюTask.set_name().Необязательный именованный аргумент только для ключевого слова context позволяет задать пользовательский
contextvars.Context, в котором будет выполняться coro. Если context не указан, создаётся копия текущего контекста.Изменено в версии 3.8: Добавлен параметр name.
Изменено в версии 3.11: Добавлен параметр context.
Изменено в версии 3.13.3: Добавлен
kwargs, передающий произвольные дополнительные параметры, включаяnameиcontext.Изменено в версии 3.13.4: Отменено изменение, при котором передавались name и context (если он равен None); при этом остальные произвольные именованные аргументы по-прежнему передаются (во избежание нарушения обратной совместимости с версией 3.13.3).
-
loop.set_task_factory(factory) -
Устанавливает фабрику задач, которая будет использоваться методом
loop.create_task().Если factory равен
None, будет установлена фабрика задач по умолчанию. В противном случае factory должен быть вызываемым объектом с сигнатурой, соответствующей(loop, coro, **kwargs), где loop — ссылка на активный цикл событий, а coro — объект сопрограммы. Вызываемый объект должен передавать все аргументы kwargs и возвращать объект, совместимый сasyncio.Task.Изменено в версии 3.13.3: Добавлено требование передавать все аргументы kwargs в
asyncio.Task.Изменено в версии 3.13.4: Аргумент name больше не передаётся фабрикам задач. Аргумент context также не передаётся фабрикам задач, если он равен
None.
-
loop.get_task_factory() -
Возвращает фабрику задач или
None, если используется фабрика по умолчанию.
Открытие сетевых подключений
-
async loop.create_connection(protocol_factory, host=None, port=None, *, ssl=None, family=0, proto=0, flags=0, sock=None, local_addr=None, server_hostname=None, ssl_handshake_timeout=None, ssl_shutdown_timeout=None, happy_eyeballs_delay=None, interleave=None, all_errors=False) -
Открывает потоковое транспортное подключение к адресу, заданному параметрами host и port.
Семейство сокета может быть
AF_INETилиAF_INET6в зависимости от host (или аргумента family, если он указан).Тип сокета будет
SOCK_STREAM.protocol_factory должен быть вызываемым объектом, возвращающим реализацию протокола asyncio.
Этот метод попытается установить соединение в фоновом режиме. В случае успеха он возвращает пару
(transport, protocol).Хронологический порядок выполнения операции следующий:
- Устанавливается соединение, и для него создаётся транспорт.
- Вызывается protocol_factory без аргументов; ожидается, что он вернёт экземпляр протокола.
- Экземпляр протокола связывается с транспортом вызовом метода
connection_made(). - В случае успеха возвращается кортеж
(transport, protocol).
Созданный транспорт представляет собой двунаправленный поток, конкретная реализация которого зависит от платформы.
Другие аргументы:
-
ssl: если задано и не равно false, создаётся транспорт SSL/TLS (по умолчанию создаётся обычный транспорт TCP). Если ssl — объект
ssl.SSLContext, для создания транспорта используется этот контекст; если ssl равноTrue, используется контекст по умолчанию, возвращаемый функциейssl.create_default_context().См. также
-
server_hostname задаёт или переопределяет имя хоста, с которым будет сравниваться сертификат целевого сервера. Этот аргумент следует передавать, только если ssl не равно
None. По умолчанию используется значение аргумента host. Если host пуст, значение по умолчанию отсутствует, и необходимо передать значение для server_hostname. Если server_hostname — пустая строка, проверка имени хоста отключается (это серьёзный риск для безопасности, поскольку допускает потенциальные атаки типа «человек посередине»). -
family, proto, flags — необязательные семейство адресов, протокол и флаги, передаваемые в getaddrinfo() для определения адреса host. Если они указаны, все они должны быть целыми числами из соответствующих констант модуля
socket. -
happy_eyeballs_delay, если указан, включает алгоритм Happy Eyeballs для этого соединения. Это число с плавающей точкой, задающее время ожидания в секундах завершения попытки соединения до начала следующей попытки параллельно. Это «задержка между попытками подключения», определённая в RFC 8305. Рекомендуемое RFC разумное значение по умолчанию —
0.25(250 миллисекунд). -
interleave управляет изменением порядка адресов, когда имени хоста соответствуют несколько IP-адресов. Если задано
0или значение не указано, порядок не меняется, и адреса проверяются в том порядке, в котором они возвращены функциейgetaddrinfo(). Если указано положительное целое число, адреса чередуются по семействам адресов, а это число трактуется как «количество адресов первого семейства», определённое в RFC 8305. По умолчанию используется0, если happy_eyeballs_delay не указан, и1, если он указан. -
sock, если указан, должен быть существующим уже подключённым объектом
socket.socket, который будет использоваться транспортом. Если указан sock, не следует задавать host, port, family, proto, flags, happy_eyeballs_delay, interleave и local_addr.Примечание
Аргумент sock передаёт созданному транспорту владение сокетом. Чтобы закрыть сокет, вызовите метод
close()транспорта. -
local_addr, если указан, — кортеж
(local_host, local_port), используемый для привязки сокета к локальному адресу. Значения local_host и local_port определяются с помощьюgetaddrinfo(), как и host и port. -
ssl_handshake_timeout — время в секундах ожидания завершения TLS-рукопожатия (для TLS-соединения) до прерывания соединения. Если задано
None(значение по умолчанию), используется60.0секунд. -
ssl_shutdown_timeout — время в секундах ожидания завершения отключения SSL до прерывания соединения. Если задано
None(значение по умолчанию), используется30.0секунд. -
all_errors определяет, какие исключения возбуждаются, если создать соединение не удаётся. По умолчанию возбуждается только одно исключение
Exception: первое, если исключение одно или все ошибки имеют одинаковое сообщение, либо одно исключениеOSErrorс объединёнными сообщениями об ошибках. Еслиall_errorsравноTrue, будет возбуждено исключениеExceptionGroup, содержащее все исключения (даже если оно всего одно).
Изменено в версии 3.5: Добавлена поддержка SSL/TLS в
ProactorEventLoop.Изменено в версии 3.6: Параметр сокета socket.TCP_NODELAY по умолчанию устанавливается для всех TCP-соединений.
Изменено в версии 3.7: Добавлен параметр ssl_handshake_timeout.
Изменено в версии 3.8: Добавлены параметры happy_eyeballs_delay и interleave.
Алгоритм Happy Eyeballs: успешная работа с узлами с поддержкой двух стеков. Если путь и протокол IPv4 сервера работают, а путь и протокол IPv6 — нет, клиентское приложение с поддержкой двух стеков сталкивается со значительной задержкой при подключении по сравнению с клиентом, использующим только IPv4. Это нежелательно, поскольку ухудшает взаимодействие с пользователем. В этом документе сформулированы требования к алгоритмам, уменьшающим такую заметную для пользователя задержку, и представлен один из таких алгоритмов.
Дополнительные сведения: https://datatracker.ietf.org/doc/html/rfc6555
Изменено в версии 3.11: Добавлен параметр ssl_shutdown_timeout.
Изменено в версии 3.12: Добавлен параметр all_errors.
См. также
Функция
open_connection()представляет собой высокоуровневую альтернативу этому API. Она возвращает пару (StreamReader,StreamWriter), которые можно напрямую использовать в коде с async/await.
-
async loop.create_datagram_endpoint(protocol_factory, local_addr=None, remote_addr=None, *, family=0, proto=0, flags=0, reuse_port=None, allow_broadcast=None, sock=None) -
Создаёт соединение для передачи датаграмм.
Семейство сокета может быть
AF_INET,AF_INET6илиAF_UNIXв зависимости от host (или аргумента family, если он указан).Тип сокета будет
SOCK_DGRAM.protocol_factory должен быть вызываемым объектом, возвращающим реализацию протокола.
В случае успеха возвращается кортеж
(transport, protocol).Другие аргументы:
-
local_addr, если указан, — кортеж
(local_host, local_port), используемый для привязки сокета к локальному адресу. Значения local_host и local_port определяются с помощьюgetaddrinfo().Примечание
В Windows при использовании цикла событий proactor с
local_addr=Noneво время выполнения будет возбуждено исключениеOSErrorсerrno.WSAEINVAL. -
remote_addr, если указан, — кортеж
(remote_host, remote_port), используемый для подключения сокета к удалённому адресу. Значения remote_host и remote_port определяются с помощьюgetaddrinfo(). -
family, proto, flags — необязательные семейство адресов, протокол и флаги, передаваемые в
getaddrinfo()для определения адреса host. Если они указаны, все они должны быть целыми числами из соответствующих констант модуляsocket. - reuse_port указывает ядру разрешить привязку этой конечной точки к тому же порту, что и у других существующих конечных точек, при условии, что при создании для всех них установлен этот флаг. Этот параметр не поддерживается в Windows и некоторых системах Unix. Если константа socket.SO_REUSEPORT не определена, эта возможность не поддерживается.
- allow_broadcast указывает ядру разрешить этой конечной точке отправлять сообщения на широковещательный адрес.
-
sock можно указать, чтобы транспорт использовал уже существующий подключённый объект
socket.socket. Если он указан, local_addr и remote_addr следует опустить (они должны быть равныNone).Примечание
Аргумент sock передаёт созданному транспорту владение сокетом. Чтобы закрыть сокет, вызовите метод
close()транспорта.
См. примеры протокола UDP-клиента эхо-сервера и протокола UDP-сервера эхо-сервера.
Изменено в версии 3.4.4: Добавлены параметры family, proto, flags, reuse_address, reuse_port, allow_broadcast и sock.
Изменено в версии 3.8: Добавлена поддержка Windows.
Изменено в версии 3.8.1: Параметр reuse_address больше не поддерживается, так как использование socket.SO_REUSEADDR представляет значительную угрозу безопасности для UDP. Явная передача
reuse_address=Trueвызовет исключение.Если несколько процессов с разными UID привязывают сокеты к одному адресу UDP-сокета с помощью
SO_REUSEADDR, входящие пакеты могут случайным образом распределяться между сокетами.На поддерживаемых платформах вместо аналогичной функциональности можно использовать reuse_port. При использовании reuse_port применяется socket.SO_REUSEPORT, который специально предотвращает привязку процессов с разными UID к одному адресу сокета.
Изменено в версии 3.11: Параметр reuse_address, отключённый начиная с Python 3.8.1, 3.7.6 и 3.6.10, полностью удалён.
-
-
async loop.create_unix_connection(protocol_factory, path=None, *, ssl=None, sock=None, server_hostname=None, ssl_handshake_timeout=None, ssl_shutdown_timeout=None) -
Создаёт соединение Unix.
Семейство сокета будет
AF_UNIX; тип сокета —SOCK_STREAM.В случае успеха возвращается кортеж
(transport, protocol).path — имя доменного сокета Unix. Этот аргумент обязателен, если не указан параметр sock. Поддерживаются абстрактные сокеты Unix, пути типа
str,bytesиPath.Сведения об аргументах этого метода см. в документации метода
loop.create_connection().Доступность: Unix.
Изменено в версии 3.7: Добавлен параметр ssl_handshake_timeout. Теперь в качестве параметра path можно передавать объект, подобный пути.
Изменено в версии 3.11: Добавлен параметр ssl_shutdown_timeout.
Создание сетевых серверов
-
async loop.create_server(protocol_factory, host=None, port=None, *, family=socket.AF_UNSPEC, flags=socket.AI_PASSIVE, sock=None, backlog=100, ssl=None, reuse_address=None, reuse_port=None, keep_alive=None, ssl_handshake_timeout=None, ssl_shutdown_timeout=None, start_serving=True) -
Создаёт TCP-сервер (тип сокета
SOCK_STREAM), прослушивающий порт port на адресе host.Возвращает объект
Server.Аргументы:
- protocol_factory должен быть вызываемым объектом, возвращающим реализацию протокола.
-
Параметру host можно присвоить значения нескольких типов, определяющие, на каких адресах будет прослушивать сервер:
- Если host — строка, TCP-сервер привязывается к одному сетевому интерфейсу, указанному в host.
- Если host — последовательность строк, TCP-сервер привязывается ко всем сетевым интерфейсам, указанным в последовательности.
- Если host — пустая строка или
None, предполагается, что используются все интерфейсы, и возвращается список из нескольких сокетов (скорее всего, один для IPv4 и другой для IPv6).
- Параметр port задаёт порт, который будет прослушивать сервер. Если он равен
0илиNone(значение по умолчанию), выбирается случайный свободный порт (обратите внимание: если host соответствует нескольким сетевым интерфейсам, для каждого интерфейса будет выбран свой случайный порт). -
Для параметра family можно задать
socket.AF_INETилиAF_INET6, чтобы принудительно использовать IPv4 или IPv6. Если параметр не задан, семейство family определяется по имени хоста (по умолчанию используетсяAF_UNSPEC). -
flags — битовая маска для
getaddrinfo(). -
sock можно указать, чтобы использовать уже существующий объект сокета. Если он указан, задавать host и port нельзя.
Примечание
Аргумент sock передаёт созданному серверу владение сокетом. Чтобы закрыть сокет, вызовите метод
close()сервера. -
backlog — максимальное число подключений в очереди, передаваемое в
listen()(по умолчанию 100). -
Параметру ssl можно присвоить экземпляр
SSLContext, чтобы включить TLS для принятых соединений. -
reuse_address указывает ядру повторно использовать локальный сокет в состоянии
TIME_WAIT, не дожидаясь окончания его естественного тайм-аута. Если параметр не указан, в Unix ему автоматически присваивается значениеTrue. - reuse_port указывает ядру разрешить привязку этой конечной точки к тому же порту, что и у других существующих конечных точек, при условии, что при создании для всех них установлен этот флаг. Этот параметр не поддерживается в Windows.
-
Если для keep_alive задано значение
True, соединения остаются активными благодаря периодической отправке сообщений.
Изменено в версии 3.13: Добавлен параметр keep_alive.
-
ssl_handshake_timeout — время в секундах ожидания завершения TLS-рукопожатия для TLS-сервера до прерывания соединения. Если задано
None(значение по умолчанию), используется60.0секунд. -
ssl_shutdown_timeout — время в секундах ожидания завершения отключения SSL до прерывания соединения. Если задано
None(значение по умолчанию), используется30.0секунд. -
Если для start_serving задано значение
True(значение по умолчанию), созданный сервер сразу начинает принимать соединения. Если задано значениеFalse, пользователь должен дождаться завершенияServer.start_serving()илиServer.serve_forever(), чтобы сервер начал принимать соединения.
Изменено в версии 3.5: Добавлена поддержка SSL/TLS в
ProactorEventLoop.Изменено в версии 3.5.1: Параметр host может быть последовательностью строк.
Изменено в версии 3.6: Добавлены параметры ssl_handshake_timeout и start_serving. Параметр сокета socket.TCP_NODELAY по умолчанию устанавливается для всех TCP-соединений.
Изменено в версии 3.11: Добавлен параметр ssl_shutdown_timeout.
См. также
Функция
start_server()представляет собой альтернативный API более высокого уровня, возвращающий пару изStreamReaderиStreamWriter, которые можно использовать в коде с async/await.
-
async loop.create_unix_server(protocol_factory, path=None, *, sock=None, backlog=100, ssl=None, ssl_handshake_timeout=None, ssl_shutdown_timeout=None, start_serving=True, cleanup_socket=True) -
Аналогичен
loop.create_server(), но работает с семейством сокетовAF_UNIX.path — имя доменного сокета Unix. Этот аргумент обязателен, если не указан аргумент sock. Поддерживаются абстрактные сокеты Unix, пути типа
str,bytesиPath.Если параметр cleanup_socket равен true, при закрытии сервера сокет Unix автоматически удаляется из файловой системы, если только после создания сервера он не был заменён.
Сведения об аргументах этого метода см. в документации метода
loop.create_server().Доступность: Unix.
Изменено в версии 3.7: Добавлены параметры ssl_handshake_timeout и start_serving. Теперь в качестве параметра path можно передавать объект
Path.Изменено в версии 3.11: Добавлен параметр ssl_shutdown_timeout.
Изменено в версии 3.13: Добавлен параметр cleanup_socket.
-
async loop.connect_accepted_socket(protocol_factory, sock, *, ssl=None, ssl_handshake_timeout=None, ssl_shutdown_timeout=None) -
Оборачивает уже принятое соединение в пару транспорт/протокол.
Этот метод можно использовать на серверах, которые принимают соединения вне asyncio, но обрабатывают их с помощью asyncio.
Параметры:
- protocol_factory должен быть вызываемым объектом, возвращающим реализацию протокола.
-
sock — существующий объект сокета, возвращённый вызовом
socket.accept.Примечание
Аргумент sock передаёт созданному транспорту владение сокетом. Чтобы закрыть сокет, вызовите метод
close()транспорта. -
Параметру ssl можно присвоить объект
SSLContext, чтобы включить SSL для принятых соединений. -
ssl_handshake_timeout — время в секундах ожидания завершения SSL-рукопожатия для SSL-соединения до прерывания соединения. Если задано
None(значение по умолчанию), используется60.0секунд. -
ssl_shutdown_timeout — время в секундах ожидания завершения отключения SSL до прерывания соединения. Если задано
None(значение по умолчанию), используется30.0секунд.
Возвращает пару
(transport, protocol).Добавлено в версии 3.5.3.
Изменено в версии 3.7: Добавлен параметр ssl_handshake_timeout.
Изменено в версии 3.11: Добавлен параметр ssl_shutdown_timeout.
Передача файлов
-
async loop.sendfile(transport, file, offset=0, count=None, *, fallback=True) -
Отправляет file через transport. Возвращает общее количество отправленных байтов.
Если доступна функция
os.sendfile(), метод использует её для высокопроизводительной передачи.file должен быть обычным файловым объектом, открытым в двоичном режиме.
offset указывает, откуда начинать чтение файла. Если параметр указан, count задаёт общее число байтов для передачи, а не передачу файла до достижения EOF. Позиция в файле обновляется всегда, даже если этот метод вызывает ошибку; фактическое количество отправленных байтов можно узнать с помощью
file.tell().Если для fallback задано значение
True, asyncio вручную читает и отправляет файл, когда платформа не поддерживает системный вызов sendfile (например, в Windows или при использовании SSL-сокета в Unix).Возбуждает исключение
SendfileNotAvailableError, если система не поддерживает системный вызов sendfile, а fallback равноFalse.Добавлено в версии 3.7.
Обновление TLS
-
async loop.start_tls(transport, protocol, sslcontext, *, server_side=False, server_hostname=None, ssl_handshake_timeout=None, ssl_shutdown_timeout=None) -
Обновить существующее соединение на основе транспорта до TLS.
Создать экземпляр кодировщика/декодировщика TLS и поместить его между транспортом и протоколом. Кодировщик/декодировщик реализует как протокол, взаимодействующий с транспортом, так и транспорт, взаимодействующий с протоколом.
Вернуть созданный экземпляр с двумя интерфейсами. После await протокол должен прекратить использовать исходный транспорт и взаимодействовать только с возвращённым объектом, поскольку кодировщик кэширует данные со стороны протокола и время от времени обменивается дополнительными пакетами сеанса TLS с транспортом.
В некоторых ситуациях (например, если переданный транспорт уже закрывается) может быть возвращено
None.Параметры:
-
Экземпляры transport и protocol, которые возвращают такие методы, как
create_server()иcreate_connection(). -
sslcontext: настроенный экземпляр
SSLContext. -
Для server_side передайте
True, если обновляется соединение на стороне сервера (например, созданное с помощьюcreate_server()). - server_hostname: задаёт или переопределяет имя узла, с которым будет сопоставляться сертификат целевого сервера.
-
ssl_handshake_timeout — время в секундах, в течение которого следует ожидать завершения TLS-рукопожатия, прежде чем прервать соединение.
60.0секунд, еслиNone(значение по умолчанию). -
ssl_shutdown_timeout — время в секундах, в течение которого следует ожидать завершения отключения SSL, прежде чем прервать соединение.
30.0секунд, еслиNone(значение по умолчанию).
Добавлено в версии 3.7.
Изменено в версии 3.11: Добавлен параметр ssl_shutdown_timeout.
-
Экземпляры transport и protocol, которые возвращают такие методы, как
Наблюдение за файловыми дескрипторами
-
loop.add_reader(fd, callback, *args) -
Начать отслеживать файловый дескриптор fd на предмет готовности к чтению и вызвать callback с указанными аргументами, когда fd будет доступен для чтения.
Любой ранее зарегистрированный для fd обратный вызов отменяется и заменяется на callback.
-
loop.remove_reader(fd) -
Прекратить отслеживать файловый дескриптор fd на предмет готовности к чтению. Возвращает
True, если ранее для fd отслеживалась готовность к чтению.
-
loop.add_writer(fd, callback, *args) -
Начать отслеживать файловый дескриптор fd на предмет готовности к записи и вызвать callback с указанными аргументами, когда fd будет доступен для записи.
Любой ранее зарегистрированный для fd обратный вызов отменяется и заменяется на callback.
Используйте
functools.partial(), чтобы передать именованные аргументы в callback.
-
loop.remove_writer(fd) -
Прекратить отслеживать файловый дескриптор fd на предмет готовности к записи. Возвращает
True, если ранее для fd отслеживалась готовность к записи.
Некоторые ограничения этих методов описаны в разделе Поддержка платформ.
Непосредственная работа с объектами сокетов
В целом реализации протоколов, использующие API на основе транспорта, например loop.create_connection() и loop.create_server(), быстрее реализаций, работающих непосредственно с сокетами. Однако бывают случаи, когда производительность не критична, а непосредственная работа с объектами socket удобнее.
-
async loop.sock_recv(sock, nbytes) -
Получить из sock до nbytes байт. Асинхронная версия
socket.recv().Вернуть полученные данные в виде объекта bytes.
sock должен быть неблокирующим сокетом.
Изменено в версии 3.7: Хотя этот метод всегда документировался как метод-корутина, выпуски до Python 3.7 возвращали
Future. Начиная с Python 3.7 это методasync def.
-
async loop.sock_recv_into(sock, buf) -
Получить данные из sock в буфер buf. Реализован по образцу блокирующего метода
socket.recv_into().Вернуть количество байтов, записанных в буфер.
sock должен быть неблокирующим сокетом.
Добавлено в версии 3.7.
-
async loop.sock_recvfrom(sock, bufsize) -
Получить из sock датаграмму размером до bufsize. Асинхронная версия
socket.recvfrom().Вернуть кортеж (полученные данные, удалённый адрес).
sock должен быть неблокирующим сокетом.
Добавлено в версии 3.11.
-
async loop.sock_recvfrom_into(sock, buf, nbytes=0) -
Получить из sock датаграмму размером до nbytes в buf. Асинхронная версия
socket.recvfrom_into().Вернуть кортеж (количество полученных байтов, удалённый адрес).
sock должен быть неблокирующим сокетом.
Добавлено в версии 3.11.
-
async loop.sock_sendall(sock, data) -
Отправить data через сокет sock. Асинхронная версия
socket.sendall().Этот метод продолжает отправлять данные в сокет, пока не будут отправлены все данные из data или не произойдёт ошибка. При успешном выполнении возвращается
None. В случае ошибки возбуждается исключение. Кроме того, невозможно определить, какой объём данных, если таковой имеется, был успешно обработан принимающей стороной соединения.sock должен быть неблокирующим сокетом.
Изменено в версии 3.7: Хотя этот метод всегда документировался как метод-корутина, до Python 3.7 он возвращал
Future. Начиная с Python 3.7 это методasync def.
-
async loop.sock_sendto(sock, data, address) -
Отправить датаграмму из sock по адресу address. Асинхронная версия
socket.sendto().Вернуть количество отправленных байтов.
sock должен быть неблокирующим сокетом.
Добавлено в версии 3.11.
-
async loop.sock_connect(sock, address) -
Подключить sock к удалённому сокету по адресу address.
Асинхронная версия
socket.connect().sock должен быть неблокирующим сокетом.
Изменено в версии 3.5.2:
addressбольше не требуется разрешать.sock_connectпопытается проверить, разрешён ли уже address, вызвавsocket.inet_pton(). Если нет, для разрешения address будет использованloop.getaddrinfo().См. также
-
async loop.sock_accept(sock) -
Принять соединение. Реализован по образцу блокирующего метода
socket.accept().Сокет должен быть привязан к адресу и прослушивать входящие соединения. Возвращаемое значение — пара
(conn, address), где conn — новый объект сокета, пригодный для отправки и получения данных по соединению, а address — адрес, к которому привязан сокет на другом конце соединения.sock должен быть неблокирующим сокетом.
Изменено в версии 3.7: Хотя этот метод всегда документировался как метод-корутина, до Python 3.7 он возвращал
Future. Начиная с Python 3.7 это методasync def.См. также
-
async loop.sock_sendfile(sock, file, offset=0, count=None, *, fallback=True) -
Отправить файл, по возможности используя высокопроизводительный вызов
os.sendfile. Вернуть общее количество отправленных байтов.Асинхронная версия
socket.sendfile().sock должен быть неблокирующим сокетом
socket.SOCK_STREAMsocket.file должен быть обычным файловым объектом, открытым в двоичном режиме.
offset указывает, с какого места начинать чтение файла. Если задан параметр count, он обозначает общее количество передаваемых байтов; в противном случае файл отправляется до достижения EOF. Позиция в файле обновляется всегда, даже если этот метод возбуждает ошибку; для получения фактического количества отправленных байтов можно использовать
file.tell().Если параметр fallback установлен в
True, asyncio вручную читает и отправляет файл, когда платформа не поддерживает системный вызов sendfile (например, в Windows или для SSL-сокета в Unix).Возбуждает
SendfileNotAvailableError, если система не поддерживает системный вызов sendfile, а fallback равенFalse.sock должен быть неблокирующим сокетом.
Добавлено в версии 3.7.
DNS
-
async loop.getaddrinfo(host, port, *, family=0, type=0, proto=0, flags=0) -
Асинхронная версия
socket.getaddrinfo().
-
async loop.getnameinfo(sockaddr, flags=0) -
Асинхронная версия
socket.getnameinfo().
Примечание
Методы getaddrinfo и getnameinfo внутри используют свои синхронные версии через исполнитель по умолчанию из пула потоков цикла. Если этот исполнитель перегружен, выполнение этих методов может задерживаться, что библиотеки более высокого уровня для работы с сетью могут отражать в виде увеличения времени ожидания. Чтобы уменьшить задержки, используйте для других задач пользователя собственный исполнитель или задайте исполнитель по умолчанию с большим количеством рабочих потоков.
Изменено в версии 3.7: Методы getaddrinfo и getnameinfo всегда документировались как возвращающие корутину, однако до Python 3.7 они фактически возвращали объекты asyncio.Future. Начиная с Python 3.7 оба метода являются корутинами.
Работа с каналами
-
async loop.connect_read_pipe(protocol_factory, pipe) -
Зарегистрировать читающий конец pipe в цикле событий.
protocol_factory должен быть вызываемым объектом, возвращающим реализацию протокола asyncio.
pipe — это файлоподобный объект.
Вернуть пару
(transport, protocol), где transport поддерживает интерфейсReadTransport, а protocol — это объект, созданный с помощью protocol_factory.В цикле событий
SelectorEventLoopдля pipe устанавливается неблокирующий режим.
-
async loop.connect_write_pipe(protocol_factory, pipe) -
Зарегистрировать записывающий конец pipe в цикле событий.
protocol_factory должен быть вызываемым объектом, возвращающим реализацию протокола asyncio.
pipe — это файлоподобный объект.
Вернуть пару
(transport, protocol), где transport поддерживает интерфейсWriteTransport, а protocol — это объект, созданный с помощью protocol_factory.В цикле событий
SelectorEventLoopдля pipe устанавливается неблокирующий режим.
Примечание
SelectorEventLoop не поддерживает указанные выше методы в Windows. В Windows вместо него используйте ProactorEventLoop.
См. также
Сигналы Unix
-
loop.add_signal_handler(signum, callback, *args) -
Назначить callback обработчиком сигнала signum.
Цикл событий loop вызовет обратный вызов наряду с другими ожидающими обратными вызовами и готовыми к выполнению корутинами этого цикла событий. В отличие от обработчиков сигналов, зарегистрированных с помощью
signal.signal(), обратному вызову, зарегистрированному этой функцией, разрешено взаимодействовать с циклом событий.Возбуждает
ValueError, если номер сигнала недопустим или сигнал нельзя перехватить. ВозбуждаетRuntimeError, если при настройке обработчика возникла проблема.Используйте
functools.partial(), чтобы передать именованные аргументы в callback.Как и
signal.signal(), эту функцию необходимо вызывать в главном потоке.
-
loop.remove_signal_handler(sig) -
Удалить обработчик сигнала sig.
Возвращает
True, если обработчик сигнала был удалён, илиFalse, если для указанного сигнала обработчик не был задан.Доступность: Unix.
См. также
Модуль signal.
Выполнение кода в пулах потоков или процессов
-
awaitable loop.run_in_executor(executor, func, *args) -
Запланировать вызов func в указанном исполнителе.
Аргумент executor должен быть экземпляром
concurrent.futures.Executor. Если executor равенNone, используется исполнитель по умолчанию. Исполнитель по умолчанию можно задать с помощьюloop.set_default_executor(); в противном случаеconcurrent.futures.ThreadPoolExecutorбудет создан по требованию и при необходимости использован методомrun_in_executor().Пример:
import asyncio import concurrent.futures def blocking_io(): # File operations (such as logging) can block the # event loop: run them in a thread pool. with open('/dev/urandom', 'rb') as f: return f.read(100) def cpu_bound(): # CPU-bound operations will block the event loop: # in general it is preferable to run them in a # process pool. return sum(i * i for i in range(10 ** 7)) async def main(): loop = asyncio.get_running_loop() ## Options: # 1. Run in the default loop's executor: result = await loop.run_in_executor( None, blocking_io) print('default thread pool', result) # 2. Run in a custom thread pool: with concurrent.futures.ThreadPoolExecutor() as pool: result = await loop.run_in_executor( pool, blocking_io) print('custom thread pool', result) # 3. Run in a custom process pool: with concurrent.futures.ProcessPoolExecutor() as pool: result = await loop.run_in_executor( pool, cpu_bound) print('custom process pool', result) if __name__ == '__main__': asyncio.run(main())Обратите внимание, что для варианта 3 необходима защита точки входа (
if __name__ == '__main__') из-за особенностейmultiprocessing, который используетсяProcessPoolExecutor. См. раздел Безопасный импорт главного модуля.Этот метод возвращает объект
asyncio.Future.Используйте
functools.partial(), чтобы передать именованные аргументы в func.Изменено в версии 3.5.3:
loop.run_in_executor()больше не задаётmax_workersсоздаваемого им исполнителя пула потоков, а оставляет выбор значения по умолчанию самому исполнителю пула потоков (ThreadPoolExecutor).
-
loop.set_default_executor(executor) -
Задать executor в качестве исполнителя по умолчанию, используемого методом
run_in_executor(). executor должен быть экземпляромThreadPoolExecutor.Изменено в версии 3.11: executor должен быть экземпляром
ThreadPoolExecutor.
API обработки ошибок
Позволяет настраивать обработку исключений в цикле событий.
-
loop.set_exception_handler(handler) -
Установить handler в качестве нового обработчика исключений цикла событий.
Если handler равен
None, будет установлен обработчик исключений по умолчанию. В противном случае handler должен быть вызываемым объектом с сигнатурой, соответствующей(loop, context), гдеloop— ссылка на активный цикл событий, аcontext— объектdict, содержащий подробную информацию об исключении (подробное описание контекста см. в документацииcall_exception_handler()).Если обработчик вызывается от имени
TaskилиHandle, он выполняется вcontextvars.Contextэтой задачи или дескриптора обратного вызова.Изменено в версии 3.12: Обработчик может вызываться в
Contextзадачи или дескриптора, в котором возникло исключение.
-
loop.get_exception_handler() -
Вернуть текущий обработчик исключений или
None, если пользовательский обработчик исключений не задан.Добавлено в версии 3.5.2.
-
loop.default_exception_handler(context) -
Обработчик исключений по умолчанию.
Вызывается при возникновении исключения, если обработчик исключений не задан. Его может вызвать пользовательский обработчик исключений, который хочет передать обработку обработчику по умолчанию.
Параметр context имеет то же значение, что и в
call_exception_handler().
-
loop.call_exception_handler(context) -
Вызвать текущий обработчик исключений цикла событий.
context — это объект
dict, содержащий следующие ключи (в будущих версиях Python могут появиться новые ключи):- ‘message’: сообщение об ошибке;
- ‘exception’ (необязательный): объект исключения;
- ‘future’ (необязательный): экземпляр
asyncio.Future; - ‘task’ (необязательный): экземпляр
asyncio.Task; - ‘handle’ (необязательный): экземпляр
asyncio.Handle; - ‘protocol’ (необязательный): экземпляр протокола;
- ‘transport’ (необязательный): экземпляр транспорта;
- ‘socket’ (необязательный): экземпляр
socket.socket; - ‘source_traceback’ (необязательный): трассировка стека источника;
- ‘handle_traceback’ (необязательный): трассировка стека дескриптора;
-
- ‘asyncgen’ (необязательный): асинхронный генератор, вызвавший
-
исключение.
Примечание
Этот метод не следует переопределять в подклассах циклов событий. Для пользовательской обработки исключений используйте метод
set_exception_handler().
Включение режима отладки
-
loop.get_debug() -
Получить значение режима отладки (
bool) цикла событий.Значение по умолчанию —
True, если переменная средыPYTHONASYNCIODEBUGустановлена в непустую строку, иFalseв противном случае.
-
loop.set_debug(enabled: bool) -
Установить режим отладки цикла событий.
Изменено в версии 3.7: Теперь для включения режима отладки также можно использовать новый режим разработки Python.
-
loop.slow_callback_duration -
Этот атрибут позволяет задать минимальную длительность выполнения в секундах, которая считается «медленной». Если режим отладки включён, «медленные» обратные вызовы записываются в журнал.
Значение по умолчанию — 100 миллисекунд.
См. также
Запуск подпроцессов
Методы, описанные в этом подразделе, являются низкоуровневыми. В обычном коде async/await рассмотрите возможность использования вместо них высокоуровневых удобных функций asyncio.create_subprocess_shell() и asyncio.create_subprocess_exec().
Примечание
В Windows цикл событий по умолчанию ProactorEventLoop поддерживает подпроцессы, а SelectorEventLoop — нет. Подробности см. в разделе Поддержка подпроцессов в Windows.
-
async loop.subprocess_exec(protocol_factory, *args, stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE, **kwargs) -
Создаёт подпроцесс из одного или нескольких строковых аргументов, заданных в args.
args должен быть списком строк, представленных в виде:
-
str; - или
bytes, закодированных с использованием кодировки файловой системы.
Первая строка задаёт исполняемую программу, а остальные строки — аргументы. Все строковые аргументы вместе образуют
argvпрограммы.Это похоже на вызов класса стандартной библиотеки
subprocess.Popenсshell=Falseи списком строк, переданным в качестве первого аргумента; однако, в отличие отPopen, который принимает один аргумент — список строк, subprocess_exec принимает несколько строковых аргументов.protocol_factory должен быть вызываемым объектом, возвращающим подкласс класса
asyncio.SubprocessProtocol.Другие параметры:
-
stdin может принимать одно из следующих значений:
- файлоподобный объект
- существующий файловый дескриптор (положительное целое число), например созданный с помощью
os.pipe() - константа
subprocess.PIPE(значение по умолчанию), которая создаст и подключит новый канал, - значение
None, при котором подпроцесс унаследует файловый дескриптор этого процесса - константа
subprocess.DEVNULL, указывающая на использование специального файлаos.devnull
-
stdout может принимать одно из следующих значений:
- файлоподобный объект
- константа
subprocess.PIPE(значение по умолчанию), которая создаст и подключит новый канал, - значение
None, при котором подпроцесс унаследует файловый дескриптор этого процесса - константа
subprocess.DEVNULL, указывающая на использование специального файлаos.devnull
-
stderr может принимать одно из следующих значений:
- файлоподобный объект
- константа
subprocess.PIPE(значение по умолчанию), которая создаст и подключит новый канал, - значение
None, при котором подпроцесс унаследует файловый дескриптор этого процесса - константа
subprocess.DEVNULL, указывающая на использование специального файлаos.devnull - константа
subprocess.STDOUT, которая подключит стандартный поток ошибок к стандартному потоку вывода процесса
-
Все остальные именованные аргументы без интерпретации передаются в
subprocess.Popen, за исключением bufsize, universal_newlines, shell, text, encoding и errors, которые указывать не следует.API подпроцессов
asyncioне поддерживает декодирование потоков в текст. Для преобразования байтов, возвращаемых потоком, в текст можно использоватьbytes.decode().
Если файлоподобный объект, переданный в качестве stdin, stdout или stderr, представляет собой канал, его другой конец следует зарегистрировать с помощью
connect_write_pipe()илиconnect_read_pipe(), чтобы использовать его с циклом событий.Документацию по другим аргументам см. в конструкторе класса
subprocess.Popen.Возвращает пару из
(transport, protocol), где transport соответствует базовому классуasyncio.SubprocessTransport, а protocol — это объект, созданный protocol_factory. -
-
async loop.subprocess_shell(protocol_factory, cmd, *, stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE, **kwargs) -
Создаёт подпроцесс из cmd, который может быть строкой
strили строкойbytes, закодированной с использованием кодировки файловой системы, с применением синтаксиса «оболочки» платформы.Это похоже на вызов класса стандартной библиотеки
subprocess.Popenсshell=True.protocol_factory должен быть вызываемым объектом, возвращающим подкласс класса
SubprocessProtocol.Подробные сведения об остальных аргументах см. в описании
subprocess_exec().Возвращает пару из
(transport, protocol), где transport соответствует базовому классуSubprocessTransport, а protocol — это объект, созданный protocol_factory.
Примечание
Приложение должно самостоятельно обеспечить правильное экранирование всех пробелов и специальных символов, чтобы избежать уязвимостей типа инъекция команд оболочки. Функцию shlex.quote() можно использовать для правильного экранирования пробелов и специальных символов в строках, из которых будут составляться команды оболочки.
Дескрипторы обратных вызовов
-
class asyncio.Handle -
Объект-обёртка обратного вызова, возвращаемый функциями
loop.call_soon()иloop.call_soon_threadsafe().-
get_context() -
Возвращает объект
contextvars.Context, связанный с дескриптором.Добавлено в версии 3.12.
-
cancel() -
Отменяет обратный вызов. Если обратный вызов уже отменён или выполнен, этот метод ничего не делает.
-
cancelled() -
Возвращает
True, если обратный вызов был отменён.Добавлено в версии 3.7.
-
-
class asyncio.TimerHandle -
Объект-обёртка обратного вызова, возвращаемый функциями
loop.call_later()иloop.call_at().Этот класс является подклассом
Handle.-
when() -
Возвращает запланированное время обратного вызова в секундах типа
float.Время представляет собой абсолютную временную метку, использующую ту же систему отсчёта времени, что и
loop.time().Добавлено в версии 3.7.
-
Объекты сервера
Объекты сервера создаются функциями loop.create_server(), loop.create_unix_server(), start_server() и start_unix_server().
Не создавайте экземпляры класса Server напрямую.
-
class asyncio.Server -
Объекты Server являются асинхронными менеджерами контекста. При использовании в операторе
async withгарантируется, что после завершения оператораasync withобъект Server будет закрыт и перестанет принимать новые подключения:srv = await loop.create_server(...) async with srv: # some code # At this point, srv is closed and no longer accepts new connections.Изменено в версии 3.7: Начиная с Python 3.7 объект Server является асинхронным менеджером контекста.
Изменено в версии 3.11: Этот класс стал общедоступным под именем
asyncio.Serverв Python 3.9.11, 3.10.3 и 3.11.-
close() -
Прекращает обслуживание: закрывает сокеты, ожидающие подключения, и присваивает атрибуту
socketsзначениеNone.Сокеты, представляющие уже установленные входящие подключения клиентов, остаются открытыми.
Сервер закрывается асинхронно; используйте корутину
wait_closed(), чтобы дождаться закрытия сервера (и завершения всех активных подключений).
-
close_clients() -
Закрывает все существующие входящие подключения клиентов.
Вызывает
close()для всех связанных транспортов.При закрытии сервера следует вызвать
close()передclose_clients(), чтобы избежать конфликтов при подключении новых клиентов.Добавлено в версии 3.13.
-
abort_clients() -
Немедленно закрывает все существующие входящие подключения клиентов, не дожидаясь завершения ожидающих операций.
Вызывает
abort()для всех связанных транспортов.При закрытии сервера следует вызвать
close()передabort_clients(), чтобы избежать конфликтов при подключении новых клиентов.Добавлено в версии 3.13.
-
get_loop() -
Возвращает цикл событий, связанный с объектом сервера.
Добавлено в версии 3.7.
-
async start_serving() -
Начинает принимать подключения.
Этот метод идемпотентен, поэтому его можно вызывать, даже если сервер уже принимает подключения.
Параметр start_serving, указываемый только по имени, в функциях
loop.create_server()иasyncio.start_server()позволяет создать объект Server, который изначально не принимает подключения. В этом случае можно использоватьServer.start_serving()илиServer.serve_forever(), чтобы сервер начал принимать подключения.Добавлено в версии 3.7.
-
async serve_forever() -
Начинает принимать подключения и продолжает это делать, пока корутина не будет отменена. Отмена задачи
serve_foreverприводит к закрытию сервера.Этот метод можно вызывать, если сервер уже принимает подключения. Для одного объекта Server может существовать только одна задача
serve_forever.Пример:
async def client_connected(reader, writer): # Communicate with the client with # reader/writer streams. For example: await reader.readline() async def main(host, port): srv = await asyncio.start_server( client_connected, host, port) await srv.serve_forever() asyncio.run(main('127.0.0.1', 0))Добавлено в версии 3.7.
-
is_serving() -
Возвращает
True, если сервер принимает новые подключения.Добавлено в версии 3.7.
-
async wait_closed() -
Ожидает завершения метода
close()и окончания всех активных подключений.
-
sockets -
Список объектов, подобных сокетам,
asyncio.trsock.TransportSocket, на которых сервер ожидает подключения.Изменено в версии 3.7: До Python 3.7
Server.socketsвозвращал напрямую внутренний список сокетов сервера. В версии 3.7 возвращается копия этого списка.
-
Реализации цикла событий
В asyncio входят две различные реализации цикла событий: SelectorEventLoop и ProactorEventLoop.
По умолчанию asyncio настроен на использование EventLoop.
-
class asyncio.SelectorEventLoop -
Подкласс
AbstractEventLoop, основанный на модулеselectors.Использует наиболее эффективный селектор, доступный для данной платформы. Можно также вручную настроить конкретную реализацию селектора:
import asyncio import selectors class MyPolicy(asyncio.DefaultEventLoopPolicy): def new_event_loop(self): selector = selectors.SelectSelector() return asyncio.SelectorEventLoop(selector) asyncio.set_event_loop_policy(MyPolicy())Доступность: Unix, Windows.
-
class asyncio.ProactorEventLoop -
Подкласс
AbstractEventLoopдля Windows, использующий «порты завершения ввода-вывода» (IOCP).Доступность: Windows.
-
class asyncio.EventLoop -
Псевдоним наиболее эффективного доступного подкласса
AbstractEventLoopдля данной платформы.В Unix это псевдоним
SelectorEventLoop, а в Windows —ProactorEventLoop.Добавлено в версии 3.13.
-
class asyncio.AbstractEventLoop -
Абстрактный базовый класс для циклов событий, совместимых с asyncio.
В разделе Методы цикла событий перечислены все методы, которые должны быть определены в альтернативной реализации
AbstractEventLoop.
Примеры
Обратите внимание, что во всех примерах этого раздела намеренно показано использование низкоуровневых API цикла событий, таких как loop.run_forever() и loop.call_soon(). Современные приложения asyncio редко требуется писать таким образом; рассмотрите возможность использования высокоуровневых функций, например asyncio.run().
Hello World с call_soon()
Пример использования метода loop.call_soon() для планирования обратного вызова. Обратный вызов выводит "Hello World", а затем останавливает цикл событий:
import asyncio
def hello_world(loop):
"""A callback to print 'Hello World' and stop the event loop"""
print('Hello World')
loop.stop()
loop = asyncio.new_event_loop()
# Schedule a call to hello_world()
loop.call_soon(hello_world, loop)
# Blocking call interrupted by loop.stop()
try:
loop.run_forever()
finally:
loop.close()
См. также
Похожий пример Hello World, созданный с помощью корутины и функции run().
Отображение текущей даты с помощью call_later()
Пример обратного вызова, отображающего текущую дату каждую секунду. Обратный вызов использует метод loop.call_later(), чтобы запланировать собственный повторный вызов через 5 секунд, а затем остановить цикл событий:
import asyncio
import datetime
def display_date(end_time, loop):
print(datetime.datetime.now())
if (loop.time() + 1.0) < end_time:
loop.call_later(1, display_date, end_time, loop)
else:
loop.stop()
loop = asyncio.new_event_loop()
# Schedule the first call to display_date()
end_time = loop.time() + 5.0
loop.call_soon(display_date, end_time, loop)
# Blocking call interrupted by loop.stop()
try:
loop.run_forever()
finally:
loop.close()
См. также
Похожий пример текущей даты, созданный с помощью корутины и функции run().
Отслеживание событий чтения для файлового дескриптора
Ожидание получения данных файловым дескриптором с помощью метода loop.add_reader() с последующим закрытием цикла событий:
import asyncio
from socket import socketpair
# Create a pair of connected file descriptors
rsock, wsock = socketpair()
loop = asyncio.new_event_loop()
def reader():
data = rsock.recv(100)
print("Received:", data.decode())
# We are done: unregister the file descriptor
loop.remove_reader(rsock)
# Stop the event loop
loop.stop()
# Register the file descriptor for read event
loop.add_reader(rsock, reader)
# Simulate the reception of data from the network
loop.call_soon(wsock.send, 'abc'.encode())
try:
# Run the event loop
loop.run_forever()
finally:
# We are done. Close sockets and the event loop.
rsock.close()
wsock.close()
loop.close()
См. также
- Похожий пример с использованием транспортов, протоколов и метода
loop.create_connection(). - Ещё один похожий пример с использованием высокоуровневой функции
asyncio.open_connection()и потоков.
Назначение обработчиков сигналов SIGINT и SIGTERM
(Этот пример signals работает только в Unix.)
Регистрация обработчиков сигналов SIGINT и SIGTERM с помощью метода loop.add_signal_handler():
import asyncio
import functools
import os
import signal
def ask_exit(signame, loop):
print("got signal %s: exit" % signame)
loop.stop()
async def main():
loop = asyncio.get_running_loop()
for signame in {'SIGINT', 'SIGTERM'}:
loop.add_signal_handler(
getattr(signal, signame),
functools.partial(ask_exit, signame, loop))
await asyncio.sleep(3600)
print("Event loop running for 1 hour, press Ctrl+C to interrupt.")
print(f"pid {os.getpid()}: send SIGINT or SIGTERM to exit.")
asyncio.run(main())
© 2001–2025 Python Software Foundation
Licensed under the PSF License.
https://docs.python.org/3.13/library/asyncio-eventloop.html