Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions pyrightconfig.stricter.json
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,7 @@
"stubs/protobuf",
"stubs/psutil/psutil/__init__.pyi",
"stubs/psycopg2",
"stubs/punq",
"stubs/pyasn1",
"stubs/Pygments",
"stubs/PyMySQL",
Expand Down
3 changes: 2 additions & 1 deletion stubs/punq/@tests/stubtest_allowlist.txt
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
punq._Empty.__init__
punq._Empty.__init__
punq._Registration.__class_getitem__
4 changes: 1 addition & 3 deletions stubs/punq/METADATA.toml
Original file line number Diff line number Diff line change
@@ -1,4 +1,2 @@
version = "0.7.*"
version = "0.8.*"
upstream-repository = "https://github.com/bobthemighty/punq"

[tool.stubtest]
68 changes: 56 additions & 12 deletions stubs/punq/punq/__init__.pyi
Original file line number Diff line number Diff line change
@@ -1,52 +1,88 @@
from _typeshed import Incomplete
from collections import defaultdict
from collections.abc import Callable
from enum import Enum
from enum import Enum, unique
from typing import Any, Final, Generic, NamedTuple, NewType, TypeVar, overload
from typing_extensions import Self, deprecated

__version__: str
_T = TypeVar("_T", default=Any)

__version__: Final[str]

@deprecated("Deprecated alias for `MissingDependencyError`.")
class MissingDependencyException(Exception): ...

class MissingDependencyError(MissingDependencyException): ...

@deprecated("Deprecated alias for `InvalidRegistrationError`.")
class InvalidRegistrationException(Exception): ...

class InvalidRegistrationError(InvalidRegistrationException): ...

class InvalidFactoryError(InvalidRegistrationError):
def __init__(self, service, factory) -> None: ...

class InvalidSelfRegistrationError(InvalidRegistrationError):
def __init__(self, service) -> None: ...

@deprecated("Deprecated alias for `InvalidForwardReferenceError`.")
class InvalidForwardReferenceException(Exception): ...

class InvalidForwardReferenceError(InvalidForwardReferenceException): ...

# TODO: Make this class Generic
class RegistrationScope:
parent: RegistrationScope | None
entries: defaultdict[Incomplete, list[Incomplete]]
def __init__(self, parent: RegistrationScope | None = None) -> None: ...
def child(self) -> Self: ...
def append(self, key, value) -> None: ...
def get(self, key) -> list[Incomplete]: ...

@unique
class Scope(Enum):
transient = 0
singleton = 1

_T = TypeVar("_T", default=Any)

class _Registration(NamedTuple, Generic[_T]):
service: type[_T] | str
scope: Scope
builder: Callable[..., _T]
needs: dict[str, Any] # the type hints of the builder's parameters
args: dict[str, Any] # passed to builder at instantiation time
cache: bool

_Empty = NewType("_Empty", object) # a class at runtime
empty: Final[_Empty]

class _Registry:
def __init__(self, parent: _Registry | None = None) -> None: ...
def register_service_and_impl(
self,
service: type[_T] | str,
scope: Scope,
impl: type[_T],
resolve_args: dict[str, Any], # forwarded to _Registration.builder
cache: bool = True,
) -> None: ...
def register_service_and_instance(self, service: type[_T] | str, instance: _T) -> None: ...
def register_concrete_service(self, service: type | str, scope: Scope) -> None: ...
def register_concrete_service(
self,
service: type | str,
scope: Scope,
resolve_args: dict[str, Any] | None = None, # forwarded to _Registration.builder
cache: bool = True,
) -> None: ...
def build_context(self, key: type | str, existing: _ResolutionContext | None = None) -> _ResolutionContext: ...
def register(
self,
service: type[_T] | str,
factory: Callable[..., _T] | _Empty = ...,
instance: _T | _Empty = ...,
scope: Scope = Scope.transient,
cache: bool = True,
**kwargs: Any, # forwarded to _Registration.builder
) -> None: ...
def __getitem__(self, service: type[_T] | str) -> list[_Registration[_T]]: ...

class _ResolutionTarget(Generic[_T]):
service: type[_T] | str
Expand All @@ -55,7 +91,7 @@ class _ResolutionTarget(Generic[_T]):
def is_generic_list(self) -> bool: ...
@property
def generic_parameter(self) -> Any: ... # returns the first annotated generic parameter of the service
def next_impl(self) -> _Registration[_T]: ...
def next_impl(self) -> _Registration[_T] | None: ...

class _ResolutionContext:
targets: dict[type | str, _ResolutionTarget[Any]]
Expand All @@ -70,25 +106,33 @@ class _ResolutionContext:

class Container:
registrations: _Registry
def __init__(self) -> None: ...
def __init__(self, registrations: _Registry | None = None, auto_register: bool = False) -> None: ...

# all kwargs are forwarded to _Registration.builder
@overload
def register(self, service: type[_T] | str, *, instance: _T, **kwargs: Any) -> Container: ...
def register(self, service: type[_T] | str, *, instance: _T, cache: bool = True, **kwargs: Any) -> Self: ...
@overload
def register(
self, service: type[_T] | str, factory: Callable[..., _T] | _Empty = ..., *, scope: Scope = Scope.transient, **kwargs: Any
) -> Container: ...
self,
service: type[_T] | str,
factory: Callable[..., _T] | _Empty = ...,
*,
scope: Scope = Scope.transient,
cache: bool = True,
**kwargs: Any,
) -> Self: ...
@overload
def register(
self,
service: type[_T] | str,
factory: Callable[..., _T] | _Empty = ...,
instance: _T | _Empty = ...,
scope: Scope = Scope.transient,
cache: bool = True,
**kwargs: Any,
) -> Container: ...
) -> Self: ...

def resolve_all(self, service: type[_T] | str, **kwargs: Any) -> list[_T]: ...
def resolve(self, service_key: type[_T] | str, **kwargs: Any) -> _T: ...
def instantiate(self, service_key: type[_T] | str, **kwargs: Any) -> _T: ...
def child(self) -> Self: ...