Closed CharString closed 3 months ago
But maybe this belongs upstream in django-stubs.
Probably it does. Here is an implementation that could work:
from typing import Any, Callable, TypeVar
from django.db.models import Model
_ModelT = TypeVar("_ModelT", bound=Model)
def display(
*,
description: str | None = ...,
) -> Callable[
[Callable[[admin.ModelAdmin[_ModelT], Any], Any]], # Input callable, should be more specific
Callable[[admin.ModelAdmin[_ModelT], _ModelT], Any] # Output callable
]: ...
@admin.register(Appointment)
class MyModelAdmin(admin.ModelAdmin[Appointment]):
@display(description="foo")
def foo(self, obj):
...
reveal_type(foo) # Type of "foo" is "(ModelAdmin[_ModelT@display], _ModelT@display) -> Any"
but doesn't in its current form as it probably needs more work.
I don't really see the use case of having foo
typed without annotating obj
? (you rarely call the display methods by hand?).
This could be useful with "forward typing" callables (e.g. in TypeScript, you can do: cosnt myCallable: SomeCallableType = (arg1, arg2) => {...}
and arg1
/arg2
would be implicitly typed w.r.t. SomeCallableType
), but this is not possible in Python.
The best thing to do would be to explicitly annotate obj
. The display
decorator can typecheck if self
is compatible with obj
(by checking if the solved ModelAdmin
type variable is the same). However, this probably requires HK Type Vars
The use case is existing code bases that don't have annotations, and also the explicit annotation could contradict the required, inferable one, which can result in type errors at runtime.
The use case is existing code bases that don't have annotations
Hum but still, display methods are rarely called explicitly, so having the right type for reveal_type(foo)
(i.e. after the display
decorator is applied) isn't really of great use.
However:
and also the explicit annotation could contradict the required
Is valuable, and as I said:
The display decorator can typecheck if
self
is compatible withobj
(by checking if the solvedModelAdmin
type variable is the same). However, this probably requires HK Type Vars
I had to annotate
obj
but this could be generated in a stub. But maybe this belongs upstream in django-stubs.