Skip to content
Snippets Groups Projects
Commit 7699e279 authored by Edward Betts's avatar Edward Betts
Browse files

New upstream version 1.2.0

parent 7420b16a
No related branches found
No related tags found
No related merge requests found
......@@ -3,9 +3,7 @@
"projectOwner": "bdraco",
"repoType": "github",
"repoHost": "https://github.com",
"files": [
"README.md"
],
"files": ["README.md"],
"imageSize": 80,
"commit": true,
"commitConvention": "angular",
......
......@@ -20,7 +20,7 @@ jobs:
- uses: actions/setup-python@v4
with:
python-version: "3.9"
- uses: pre-commit/action@v3.0.0
- uses: pre-commit/action@v3.0.1
# Make sure commit messages follow the conventional commits convention:
# https://www.conventionalcommits.org
......@@ -42,15 +42,17 @@ jobs:
- "3.10"
- "3.11"
- "3.12"
- "3.13"
os:
- ubuntu-latest
runs-on: ${{ matrix.os }}
steps:
- uses: actions/checkout@v3
- name: Set up Python
uses: actions/setup-python@v4
uses: actions/setup-python@v5
with:
python-version: ${{ matrix.python-version }}
allow-prereleases: true
- uses: snok/install-poetry@v1.3.3
- name: Install Dependencies
run: poetry install
......
......@@ -9,12 +9,12 @@ ci:
repos:
- repo: https://github.com/commitizen-tools/commitizen
rev: v3.5.3
rev: v3.29.0
hooks:
- id: commitizen
stages: [commit-msg]
- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v4.4.0
rev: v4.6.0
hooks:
- id: debug-statements
- id: check-builtin-literals
......@@ -28,42 +28,42 @@ repos:
- id: end-of-file-fixer
- id: trailing-whitespace
- repo: https://github.com/python-poetry/poetry
rev: 1.5.1
rev: 1.8.0
hooks:
- id: poetry-check
- repo: https://github.com/pre-commit/mirrors-prettier
rev: v3.0.0
rev: v4.0.0-alpha.8
hooks:
- id: prettier
args: ["--tab-width", "2"]
- repo: https://github.com/asottile/pyupgrade
rev: v3.9.0
rev: v3.17.0
hooks:
- id: pyupgrade
args: [--py38-plus]
- repo: https://github.com/PyCQA/isort
rev: 5.12.0
rev: 5.13.2
hooks:
- id: isort
- repo: https://github.com/psf/black
rev: 23.7.0
rev: 24.8.0
hooks:
- id: black
- repo: https://github.com/codespell-project/codespell
rev: v2.2.5
rev: v2.3.0
hooks:
- id: codespell
- repo: https://github.com/PyCQA/flake8
rev: 6.0.0
rev: 7.1.1
hooks:
- id: flake8
- repo: https://github.com/pre-commit/mirrors-mypy
rev: v1.4.1
rev: v1.11.1
hooks:
- id: mypy
additional_dependencies: []
- repo: https://github.com/PyCQA/bandit
rev: 1.7.5
rev: 1.7.9
hooks:
- id: bandit
args: [-x, tests]
......@@ -2,6 +2,13 @@
<!--next-version-placeholder-->
## v1.2.0 (2024-08-21)
### Feature
* Improve performance of entering the context manager ([#13](https://github.com/bdraco/async_interrupt/issues/13)) ([`fab2218`](https://github.com/bdraco/async_interrupt/commit/fab2218d31383e42fa12e0cb6d76fd611d8ca997))
* Python 3.13 support ([#14](https://github.com/bdraco/async_interrupt/issues/14)) ([`ec49fee`](https://github.com/bdraco/async_interrupt/commit/ec49fee2bd9233f77a0f5fd597ff06c2db528c92))
## v1.1.2 (2024-06-24)
### Fix
......
[tool.poetry]
name = "async_interrupt"
version = "1.1.2"
version = "1.2.0"
description = "Context manager to raise an exception when a future is done"
authors = ["J. Nick Koston <nick@koston.org>"]
readme = "README.md"
repository = "https://github.com/bdraco/async_interrupt"
classifiers = [
"Development Status :: 2 - Pre-Alpha",
"Development Status :: 5 - Production/Stable",
"Intended Audience :: Developers",
"Natural Language :: English",
"Operating System :: OS Independent",
"Topic :: Software Development :: Libraries",
"License :: OSI Approved :: Apache Software License",
"Programming Language :: Python :: 3.9",
"Programming Language :: Python :: 3.10",
"Programming Language :: Python :: 3.11",
"Programming Language :: Python :: 3.12",
"Programming Language :: Python :: 3.13"
]
packages = [
{ include = "async_interrupt", from = "src" },
......
......@@ -7,13 +7,14 @@ The purpose is to raise as soon as possible to avoid any race conditions.
This is based loosely on async_timeout by Andrew Svetlov and cpython asyncio.timeout
"""
from __future__ import annotations
import asyncio
from types import TracebackType
from typing import TYPE_CHECKING, Any, final
__version__ = "1.1.2"
__version__ = "1.2.0"
__all__ = ("interrupt",)
......@@ -34,7 +35,6 @@ class _Interrupt:
"_exception",
"_future",
"_message",
"_loop",
"_interrupted",
"_task",
"_cancelling",
......@@ -43,13 +43,11 @@ class _Interrupt:
def __init__(
self,
loop: asyncio.AbstractEventLoop,
future: asyncio.Future[Any],
exception: type[Exception],
message: str | None,
) -> None:
"""Initialize the interrupt context manager."""
self._loop = loop
self._future = future
self._interrupted = False
self._exception = exception
......@@ -107,24 +105,32 @@ class _Interrupt:
self._future.remove_done_callback(self._on_interrupt)
def interrupt(
future: asyncio.Future[Any],
exception: type[Exception],
message: str | None,
) -> _Interrupt:
"""Interrupt context manager.
if TYPE_CHECKING:
def interrupt(
future: asyncio.Future[Any],
exception: type[Exception],
message: str | None,
) -> _Interrupt:
"""Interrupt context manager.
Useful in cases when you want to apply interrupt logic around block
of code that uses await expression where an exception needs to be
raised as soon as possible to avoid race conditions.
Useful in cases when you want to apply interrupt logic around block
of code that uses await expression where an exception needs to be
raised as soon as possible to avoid race conditions.
>>> async with interrupt(future, APIUnavailableError, 'API is became unavailable'):
... await api.call()
>>> async with interrupt(
future,
APIUnavailableError,
'API is became unavailable'
):
... await api.call()
future - the future that will cause the block to be interrupted
exception - the exception to raise when the future is done
message - the message to pass when constructing the exception
"""
loop = asyncio.get_running_loop()
return _Interrupt(loop, future, exception, message)
future - the future that will cause the block to be interrupted
exception - the exception to raise when the future is done
message - the message to pass when constructing the exception
"""
return _Interrupt(future, exception, message)
else:
interrupt = _Interrupt
......@@ -74,7 +74,7 @@ async def test_reuse_not_allowed():
loop = asyncio.get_running_loop()
future = loop.create_future()
loop.call_soon(future.set_result, None)
manual_interrupt = _Interrupt(loop, future, ValueError, "message")
manual_interrupt = _Interrupt(future, ValueError, "message")
async with manual_interrupt:
await asyncio.sleep(0)
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment