Политика

Политика событийного цикла - это глобальный объект для каждого процесса, управляющая событийным циклом. Каждый событийный цикл имеет политику по умолчанию, которую можно изменить и настроить с помощью API политики.

Политика определяет контекст и управляет отдельным событийный цикл по контексту. Политика по умолчанию определяет контекст как текущий поток.

Используя пользовательскую политику цикла событий, поведение функций get_event_loop(), set_event_loop() и new_event_loop() могут быть настроены.

Объекты политики должны реализовывать API, определенные в абстрактном базовом AbstractEventLoopPolicy классом.

Получение и настройка политики

Для получения и установки политики для текущего процесса можно использовать следующие функции:

asyncio.get_event_loop_policy()

Возврат текущей политики в рамках всего процесса.

asyncio.set_event_loop_policy(policy)

Установка для текущей политики в рамках процесса значение policy.

Если для policy установлено значение None, политика по умолчанию восстанавливается.

Объекты политик

Политики абстрактного событийного цикла определяется базовым классом следующим образом:

class asyncio.AbstractEventLoopPolicy

Абстрактный базовый класс для asyncio политик.

get_event_loop()

Получение событийного цикла для текущего контекста.

Возвращает объект событийный цикл, реализующий интерфейс AbstractEventLoop.

Этот метод никогда не должен возвращаться None.

Изменено в версии 3.6.

set_event_loop(loop)

Задайте для событийный цикл текущего контекста значение loop.

new_event_loop()

Создание и возврат нового объекта событийный цикл.

Этот метод никогда не должен возвращать None.

get_child_watcher()

Получение дочернего объекта мониторига за процессами.

Возвращает объект наблюдения, реализующий интерфейс AbstractChildWatcher.

Эта функция специфична для Unix.

set_child_watcher(watcher)

Установите текущий дочерний монитор процессов на watcher.

Эта функция специфична для Unix.

asyncio поставляется со следующими встроенными политиками:

class asyncio.DefaultEventLoopPolicy

Политика asyncio по умолчанию. Использует SelectorEventLoop в Unix и ProactorEventLoop в Windows.

Нет необходимости устанавливать политику по умолчанию вручную. asyncio настроен на автоматическое использование политики по умолчанию.

Изменено в версии 3.8: В Windows ProactorEventLoop теперь используемый по умолчанию.

class asyncio.WindowsSelectorEventLoopPolicy

Альтернативная событийный цикл политика, использующая SelectorEventLoop событийный цикл реализации.

Availability: Windows.

class asyncio.WindowsProactorEventLoopPolicy

Альтернативная политика событийныого цикла, использующая реализацию ProactorEventLoop событийного цикла.

Availability: Windows.

Вотчеры процесса

Вотчер процессов позволяет настроить мониторинг дочерних процессов событийного цикла в Unix. В частности, событийный цикл должен знать, когда завершается дочерний процесс.

В asyncio дочерние процессы создаются с create_subprocess_exec() и loop.subprocess_exec() функциями.

asyncio определяет AbstractChildWatcher абстрактные базовые класс, которые должны быть реализованы дочерними вотчерами, и имеет четыре различных реализации: ThreadedChildWatcher (настроенные для используемый по умолчанию), MultiLoopChildWatcher, SafeChildWatcher и FastChildWatcher.

См. также раздел Subprocess and Threads.

Следующие две функции могут быть используемый для настройки реализации дочернего вотчера процессов, используемый asyncio событийный цикл:

asyncio.get_child_watcher()

Возвращает текущий вотчер дочерних элементов для текущей политики.

asyncio.set_child_watcher(watcher)

Установите для текущего дочернего вотчера значение watcher для текущей политики. watcher должны реализовывать методы, определенные в базовом AbstractChildWatcher классе.

Примечание

Реализация событийных циклов сторонних производителей может не поддерживать настраиваемые средства вотчерами за дочерними объектами. По таким событийным циклам использование set_child_watcher() может быть запрещено или не иметь последствий.

class asyncio.AbstractChildWatcher
add_child_handler(pid, callback, *args)

Зарегистрировать новый дочерний вотчер.

Организация вызова callback(pid, returncode, *args) при завершении процесса с идентификатором PID, равным pid. Указание другого колбэка для того же процесса заменяет предыдущий обработчик.

Вызываемый callback должен быть потокобезопасным.

remove_child_handler(pid)

Удаляет обработчик для процесса с идентификатором PID, равным pid.

Функция возвращает True, если обработчик был успешно удален, False если удалить было нечего.

attach_loop(loop)

Прикрепление вотчера к событийному циклу.

Если вотчера был ранее присоединен к событийному циклу, то он сначала отсоединяется перед присоединением к новому циклу.

Примечание: цикл может быть None.

is_active()

Возвращает True, если вотчер готов к использованию.

Создание подпроцесса с текущим вотчером inactive потомками вызывает RuntimeError.

Добавлено в версии 3.8.

close()

Закрытие вотчера.

Этот метод необходимо вызвать для обеспечения очистки базовых ресурсов.

class asyncio.ThreadedChildWatcher

Эта реализация запускает новый поток ожидания для каждого подпроцесса.

Он работает надежно даже при работе asyncio событийный цикл в неосновном потоке ОС.

Нет заметных накладных расходов при обработке большого количества дочерних элементов (O(1) каждый раз, когда дочерний элемент завершается), но запуск потока для каждого процесса требует дополнительной памяти.

Вотчер используемый по умолчанию.

Добавлено в версии 3.8.

class asyncio.MultiLoopChildWatcher

Эта реализация регистрирует обработчик сигнала SIGCHLD при создании экземпляра. Это может привести к разрыву стороннего код, устанавливающего пользовательский обработчик для SIGCHLD сигнала).

Вотчер позволяет избежать прерывания других код нерестовых процессов путем явного опроса каждого процесса по SIGCHLD сигналу.

Нет ограничений на выполнение подпроцессов из разных потоков после установки вотчера.

Решение является безопасным, но при работе с большим количеством процессов (O(n) каждый раз при получении SIGCHLD) имеет значительные издержки.

Добавлено в версии 3.8.

class asyncio.SafeChildWatcher

Реализация использует активный событийный цикл из основного потока для обработки SIGCHLD сигнала. Если основной поток не выполняется событийный цикл другой поток не может создать подпроцесса (возникает RuntimeError).

Вотчер позволяет избежать прерывания других код нерестовых процессов путем явного опроса каждого процесса по SIGCHLD сигналу.

Это решение является таким же безопасным, как и MultiLoopChildWatcher, и имеет ту же O(N) сложность, но для работы в основном потоке требуется работающая событийный цикл.

class asyncio.FastChildWatcher

Эта реализация восстанавливает все завершенные процессы, вызывая os.waitpid(-1) напрямую, возможно, прерывая другие код нерестовые процессы и ожидая их завершения.

При обработке большого количества нижестоящих элементов (O(1) при каждом завершении нижестоящего элемента) заметных накладных расходов нет.

Для работы этого решения, как и событийный цикл, необходима работающая SafeChildWatcher в основном потоке.

Другая политика

Для реализации новой политики событийного цикла рекомендуется создать подкласс DefaultEventLoopPolicy и переопределить методы, для которых требуется нестандартное поведение, например:

class MyEventLoopPolicy(asyncio.DefaultEventLoopPolicy):

    def get_event_loop(self):
        """Получить событийный цикл.

        Это может быть None или экземпляр EventLoop.
        """
        loop = super().get_event_loop()
        # Сделать что-то с циклом ...
        return loop

asyncio.set_event_loop_policy(MyEventLoopPolicy())