Mercurial > libervia-backend
view libervia/frontends/tools/aio.py @ 4127:5fc26a6ef113
frontends (tools) new `aio` module for tools regarding asyncio:
A first method lets run an async method from blocking code.
rel 424
author | Goffi <goffi@goffi.org> |
---|---|
date | Tue, 03 Oct 2023 16:27:51 +0200 |
parents | |
children | 5de6f3595380 |
line wrap: on
line source
#!/usr/bin/env python3 # Libervia AsyncIO helper methods # Copyright (C) 2009-2023 Jérôme Poisson (goffi@goffi.org) # This program is free software: you can redistribute it and/or modify # it under the terms of the GNU Affero General Public License as published by # the Free Software Foundation, either version 3 of the License, or # (at your option) any later version. # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU Affero General Public License for more details. # You should have received a copy of the GNU Affero General Public License # along with this program. If not, see <http://www.gnu.org/licenses/>. import asyncio from typing import Any, Coroutine from libervia.backend.core import log as logging log = logging.getLogger(__name__) background_tasks = set() def _on_task_done(task: asyncio.Future) -> None: """Callback function to execute when a task is done. @param task: The completed task. Note: The function removes the task from the tracking set and logs any exceptions that might have occurred. """ background_tasks.discard(task) e = task.exception() if e is not None: exc_info = (type(e), e, e.__traceback__) log.error("Task failed:", exc_info=exc_info) def run_async(async_method: Coroutine | asyncio.Future) -> None: """Schedules and tracks an asynchronous method. @param async_method: The method to be scheduled for execution. Note: The function keeps a strong reference to the task to prevent it from being garbage-collected. In case of task failure, logs the error. cf. https://docs.python.org/3/library/asyncio-task.html#asyncio.create_task """ if isinstance(async_method, asyncio.Future): task = asyncio.ensure_future(async_method) else: task = asyncio.create_task(async_method) background_tasks.add(task) task.add_done_callback(_on_task_done)