diff --git a/stubs/pycurl/@tests/stubtest_allowlist.txt b/stubs/pycurl/@tests/stubtest_allowlist.txt new file mode 100644 index 000000000000..5db17c304cd3 --- /dev/null +++ b/stubs/pycurl/@tests/stubtest_allowlist.txt @@ -0,0 +1,3 @@ +# The runtime computes __all__ dynamically (dir(_pycurl) + AsyncCurlMulti), so +# its exact contents depend on the libcurl feature set pycurl was built against. +pycurl.__all__ diff --git a/stubs/pycurl/METADATA.toml b/stubs/pycurl/METADATA.toml index 7031da46feb4..75b538b77452 100644 --- a/stubs/pycurl/METADATA.toml +++ b/stubs/pycurl/METADATA.toml @@ -1,4 +1,4 @@ -version = "7.46.0" +version = "7.47.0" upstream-repository = "https://github.com/pycurl/pycurl" [tool.stubtest] diff --git a/stubs/pycurl/pycurl/__init__.pyi b/stubs/pycurl/pycurl/__init__.pyi new file mode 100644 index 000000000000..43856c3618eb --- /dev/null +++ b/stubs/pycurl/pycurl/__init__.pyi @@ -0,0 +1,2 @@ +from pycurl._pycurl import * +from pycurl.async_multi import AsyncCurlMulti as AsyncCurlMulti diff --git a/stubs/pycurl/pycurl.pyi b/stubs/pycurl/pycurl/_pycurl.pyi similarity index 97% rename from stubs/pycurl/pycurl.pyi rename to stubs/pycurl/pycurl/_pycurl.pyi index baae8d9214f2..fb200d812511 100644 --- a/stubs/pycurl/pycurl.pyi +++ b/stubs/pycurl/pycurl/_pycurl.pyi @@ -1,3 +1,4 @@ +# Stub for the pycurl C extension (imported at runtime as `pycurl._pycurl`). import sys from _typeshed import ReadableBuffer, WriteableBuffer from collections.abc import Callable @@ -13,6 +14,10 @@ def global_cleanup() -> None: ... def version_info( stamp: int = ..., ) -> tuple[int, str, int, str, int, str, int, str, tuple[str, ...], str | None, int, str | None]: ... +def easy_strerror(errornum: int) -> str: ... +def multi_strerror(errornum: int) -> str: ... +def share_strerror(errornum: int) -> str: ... +def url_strerror(errornum: int) -> str: ... class error(Exception): # libcurl protocol errors raise (code, message); arg-parse errors raise (message,). @@ -31,7 +36,7 @@ class HstsEntry(NamedTuple): include_subdomains: bool class HstsIndex(NamedTuple): - index: int # type: ignore[assignment] + idx: int total: int class KhKey(NamedTuple): @@ -48,10 +53,11 @@ class CurlSockAddr(NamedTuple): class Curl: USERPWD: int def close(self) -> None: ... + @property def closed(self) -> bool: ... # For `setopt()` the exact `value` type depends on the passed `option`; `None` used to unassign: # http://pycurl.io/docs/latest/curlobject.html#pycurl.Curl.setopt - def setopt(self, option: int, value: Any | None) -> None: ... + def setopt(self, option: int, value: Any | None, *, use_memoryview: bool = False) -> None: ... def setopt_string(self, option: int, value: str) -> None: ... def perform(self) -> None: ... def perform_rb(self) -> bytes: ... @@ -89,6 +95,7 @@ class Curl: @disjoint_base class CurlMulti: def close(self) -> None: ... + @property def closed(self) -> bool: ... def add_handle(self, obj: Curl) -> None: ... def remove_handle(self, obj: Curl) -> None: ... @@ -102,6 +109,7 @@ class CurlMulti: | tuple[str | bytes, ...] | Callable[[int], Literal[-1, 0] | None] | Callable[[int, int, Self, Any | None], Literal[-1, 0] | None] # See `assign()` below for `Any | None` + | Callable[[int, Curl | None], object] # `M_NOTIFYFUNCTION` (notify) callback; return value ignored | None ), ) -> None: ... @@ -113,6 +121,8 @@ class CurlMulti: # `assign()` accepts literally any object, it's only passed to callbacks and not processed; `None` used to unassign def assign(self, sockfd: int, obj: Any | None, /) -> None: ... def unassign(self, sock_fd: int, /) -> None: ... + def notify_enable(self, *notifications: int) -> None: ... + def notify_disable(self, *notifications: int) -> None: ... def socket_all(self) -> tuple[int, int]: ... def timeout(self) -> int: ... def __contains__(self, key: Curl, /) -> bool: ... @@ -124,10 +134,13 @@ class CurlMulti: @disjoint_base class CurlShare: def close(self) -> None: ... + @property def closed(self) -> bool: ... # Currently this `setopt()` is very limited; `None` to unset is also not accepted: # http://pycurl.io/docs/latest/curlshareobject.html#pycurl.CurlShare.setopt def setopt(self, option: int, value: int) -> None: ... + def share(self, *lock_data: int) -> None: ... + def unshare(self, *lock_data: int) -> None: ... def __enter__(self) -> Self: ... def __exit__( self, exc_type: type[BaseException] | None, exc_value: BaseException | None, traceback: TracebackType | None, / @@ -166,6 +179,7 @@ class CurlMime: def add_multipart(self, name: str | bytes | None = None, subtype: str | bytes | None = None) -> CurlMime: ... def addpart(self) -> CurlMimePart: ... def close(self) -> None: ... + @property def closed(self) -> bool: ... def __enter__(self) -> Self: ... def __exit__( @@ -577,6 +591,9 @@ M_MAX_CONCURRENT_STREAMS: Final = 16 M_MAX_HOST_CONNECTIONS: Final = 7 M_MAX_PIPELINE_LENGTH: Final = 8 M_MAX_TOTAL_CONNECTIONS: Final = 13 +M_NOTIFYFUNCTION: Final[int] +M_NOTIFY_EASY_DONE: Final[int] +M_NOTIFY_INFO_READ: Final[int] M_PIPELINING: Final = 3 M_PIPELINING_SERVER_BL: Final = 10012 M_PIPELINING_SITE_BL: Final = 10011 diff --git a/stubs/pycurl/pycurl/async_multi.pyi b/stubs/pycurl/pycurl/async_multi.pyi new file mode 100644 index 000000000000..0d1868bae07b --- /dev/null +++ b/stubs/pycurl/pycurl/async_multi.pyi @@ -0,0 +1,22 @@ +import asyncio +from collections.abc import Iterable +from types import TracebackType +from typing import Any +from typing_extensions import Self + +from pycurl._pycurl import Curl + +class AsyncCurlMulti: + def __init__(self, close_handles: bool = False) -> None: ... + def setopt(self, option: int, value: Any) -> None: ... # type of value depends on the option + def add_handle(self, curl: Curl) -> asyncio.Future[Curl]: ... + def remove_handle(self, curl: Curl) -> None: ... + async def perform(self, curl: Curl) -> Curl: ... + def futures(self, curls: Iterable[Curl] | None = None) -> tuple[asyncio.Future[Curl], ...]: ... + @property + def closed(self) -> bool: ... + async def aclose(self) -> None: ... + async def __aenter__(self) -> Self: ... + async def __aexit__( + self, exc_type: type[BaseException] | None, exc: BaseException | None, tb: TracebackType | None + ) -> None: ...