sbdchd / djangorestframework-types Goto Github PK
View Code? Open in Web Editor NEWThis project forked from typeddjango/djangorestframework-stubs
:sunflower: Type stubs for Django Rest Framework
License: MIT License
This project forked from typeddjango/djangorestframework-stubs
:sunflower: Type stubs for Django Rest Framework
License: MIT License
Hi, could you please release new version on pypi?
I'm running djangorestframework 3.13.1 and djangorestframework-types 0.6.0
GenericAPIView
defines a get_queryset(self)
method.
The type stub does not.
It looks like djangorestframework-stubs package has added this - https://github.com/typeddjango/djangorestframework-stubs/blob/master/rest_framework-stubs/generics.pyi#L20 - is it worth pulling upstream changes into this package?
This code for fails pyright check with Expected 0 positional arguments
from rest_framework.parsers import JSONParser
from rest_framework.test import APIRequestFactory
from rest_framework.request import Request
req = Request(
APIRequestFactory().post(
"/first?queryParamString=ok", {"random": "stuff"}, format="json"
),
parsers=[JSONParser()],
)
class FooListSerializer(serializers.ListSerializer):
...
reveal_type(FooListSerializer(data).data) # list[Any]
class FooListSerializer(serializers.Serializer):
...
reveal_type(FooListSerializer(data, many=True).data) # list[Any]
reveal_type(FooListSerializer(data).data) # dict[str, Any]
need to investigate this more, what happens when passing many=True
to a list serializer?
Also need to handle .validated_data
as well
rel: python/mypy#8330 (comment)
rel: python/mypy#9482
Functions declared in a custom serializer base class are not detected correctly and are flagged by pyright.
A simple example is:
from rest_framework import serializers
class RequestSerializer(serializers.Serializer):
def do_something(self):
print("did something")
class MySerializer(RequestSerializer):
pass
MySerializer().do_something()
Then running pyright on this code I get:
❯ pyright
/Users/rconyers/dev/pyright-inheritance-test/test.py
/Users/rconyers/dev/pyright-inheritance-test/test.py:10:16 - error: Cannot access member "do_something" for type "BaseSerializer"
Member "do_something" is unknown (reportGeneralTypeIssues)
1 error, 0 warnings, 0 informations
However, running the code yields:
❯ python test.py
did something
So it seems like Python is able to successfully resolve the function, but the types are incorrect and are breaking static analysis.
I am using the following dependencies for this minimal reproducible example:
python = "^3.11"
pyright = "^1.1.310"
djangorestframework = "^3.14.0"
djangorestframework-types = "^0.8.0"
The error is not flagged in pyright 1.1.308 but it is flagged in 1.1.309.
The top line of pyright 1.1.309's release notes states:
Behavior Change: Reworked the logic for constructor type analysis to better mirror runtime behaviors of the type.call method. This is a big change with a potential for regressions.
In django-rest-framework
version 3.14.0, some new http status codes (102, 103, 421, 425) were added.
See this commit: encode/django-rest-framework@5bea22f
It would be ideal if status.pyi could be updated to reflect those additions.
.data
isn't the same thing as .json()
and maybe we should remove it so people don't misunderstand
Another option would be to keep it and make it typed object
so it's harder to use, but if you really want it, it's there.
Currently we have Serializer.errors
typed as Any
, but I think we can use the ReturnDict
type instead
can also update BaseSerializer
and Field
while we are at it
serializers are currently typed as Any:
The upstream project made these generic at some point. Some excerpts:
Base Serializer
Serializer
Model Serializer
It would be great if these improvements could be backported.
Specifically
def get_search_fields(self, view: APIView, request: Request) -> Any: ...
# and
def must_call_distinct(self, queryset: QuerySet[Any], search_fields: Any) -> bool: ...
Instead can be:
def get_search_fields(self, view: APIView, request: Request) -> Sequence[str] | None: ...
# and
def must_call_distinct(self, queryset: QuerySet[Any], search_fields: Sequence[str]) -> bool: ...
Is there any steps required to use it with mypy?
I have installed it:
# requirements.txt
Django==4.2.2
djangorestframework==3.14.0
djangorestframework-types==0.8.0
django-types==0.17.0
django-filter==23.2
mypy==1.3.0
But mypy seems to ignore it:
mypy example.py
example.py:1: error: Cannot find implementation or library stub for module named "rest_framework.viewsets" [import]
example.py:1: note: See https://mypy.readthedocs.io/en/stable/running_mypy.html#missing-imports
example.py:2: error: Cannot find implementation or library stub for module named "django_filters.rest_framework" [import]
Found 2 errors in 1 file (checked 1 source file)
rel:
Latest release on the GitHub repository seems to be v0.7.1. On PyPI, we have v0.8.0.
Does that matter?
The schemas.openapi.SchemaGenerator.get_schema request argument is optional in drf. If you override the clause, it either results in pyright complaining that we incorrectly override the method if we set the type of request: Request|None
since the type is now different, or if we say request: Request = None
of course it will show a type error, and if we leave out the default value, now we make it mandatory, while it shouldn't be.
The openapi specs have more information then the TypedDict's in schemas.openapi
allow. This results in type errors if we override some of the fields as described in the docs
For instance this code:
import typing
from rest_framework.request import Request
from rest_framework.schemas.openapi import SchemaGenerator
DRFOpenAPISchema = dict[str, typing.Any]
if typing.TYPE_CHECKING:
from rest_framework.schemas.openapi import DRFOpenAPISchema
class DataSchemaGenerator(SchemaGenerator):
def get_info(self):
info = super().get_info()
info["termsOfService"] = "https://example.com/tos.html"
return info
def get_schema(
self, request: Request | None = None, public: bool = False
) -> DRFOpenAPISchema:
schema = super().get_schema(request, public)
return schema
Results in this error:
Could not assign item in TypedDict "termsOfService" is not a defined key in "DRFOpenAPIInfo"
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.