-
-
Notifications
You must be signed in to change notification settings - Fork 16.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Untyped decorator makes function untyped #4060
Comments
Does it work with this patch applied? diff --git a/src/flask/scaffold.py b/src/flask/scaffold.py
index f50c9b1b..46d216f6 100644
--- a/src/flask/scaffold.py
+++ b/src/flask/scaffold.py
@@ -642,7 +642,7 @@ class Scaffold:
@setupmethod
def errorhandler(
self, code_or_exception: t.Union[t.Type[Exception], int]
- ) -> t.Callable:
+ ) -> t.Callable[[ErrorHandlerCallable], ErrorHandlerCallable]:
"""Register a function to handle errors by code or exception class.
A decorator that is used to register a function given an |
That was my initial thought, too, but unfortunately, diff --git a/src/flask/scaffold.py b/src/flask/scaffold.py
index 20654b6b..f8f94af1 100644
--- a/src/flask/scaffold.py
+++ b/src/flask/scaffold.py
@@ -33,8 +33,10 @@ if t.TYPE_CHECKING:
# a singleton sentinel value for parameter defaults
_sentinel = object()
+F = t.TypeVar("F", bound=t.Callable[..., t.Any])
-def setupmethod(f: t.Callable) -> t.Callable:
+
+def setupmethod(f: F) -> F:
"""Wraps a method so that it performs a check in debug mode if the
first request was already handled.
"""
@@ -53,7 +55,7 @@ def setupmethod(f: t.Callable) -> t.Callable:
)
return f(self, *args, **kwargs)
- return update_wrapper(wrapper_func, f)
+ return t.cast(F, update_wrapper(wrapper_func, f))
class Scaffold: It seems the mypy error was caused by the decorator not having any type, so changing I have a PR with my complete fix: #4071. |
When I run
mypy --strict
on the following file (namedflask_types.py
),I get the following error:
flask_types.py:7: error: Untyped decorator makes function "page_not_found" untyped
Instead, mypy should return no errors.
Using
--strict
(or the equivalent option insetup.cfg
) in your tests might have caught an error like this, but given how new your type annotations are, I understand why you aren't using the setting yet.The root cause appears to be that the implemented decorators often use
typing.Callable
in type annotations without any type parameters, which causes them to lose type information.The fix for this specific issue is only a couple of lines (I have a prototype implemented locally), but I will try to add appropriate type parameters for
Callable
in as many places as possible. I expect to have a PR out for this in a couple of days.Once I got a fix working for
errorhandler()
, mypy was able to find an error in my type annotations ofpage_not_found()
as well as some internal issues in Flask itself, which I feel demonstrates how better typing would be useful here.Environment:
PS: I really appreciate the new typing annotations in Flask! They seem like they took a lot of effort, and I have already found them useful. Thank you very much!
The text was updated successfully, but these errors were encountered: