GithubHelp home page GithubHelp logo

dplepage / django-types Goto Github PK

View Code? Open in Web Editor NEW

This project forked from sbdchd/django-types

0.0 1.0 0.0 2.42 MB

:doughnut: Type stubs for Django

License: MIT License

Python 99.96% Shell 0.04%

django-types's Introduction

django-types PyPI

Type stubs for Django.

Note: this project was forked from https://github.com/typeddjango/django-stubs with the goal of removing the mypy plugin dependency so that mypy can't crash due to Django config, and that non-mypy type checkers like pyright will work better with Django.

install

pip install django-types

If you're on a Django version < 3.1, you'll need to monkey patch Django's QuerySet and Manager classes so we can index into them with a generic argument. You can either use django-stubs-ext or do this yourself manually:

# in settings.py
from django.db.models.manager import BaseManager
from django.db.models.query import QuerySet

# NOTE: there are probably other items you'll need to monkey patch depending on
# your version.
for cls in (QuerySet, BaseManager):
    cls.__class_getitem__ = classmethod(lambda cls, *args, **kwargs: cls)  # type: ignore [attr-defined]

usage

getting objects to work

By default the base Model class doesn't have objects defined, so you'll have to explicitly type the property.

from django.db import connection, models
from django.db.models.manager import Manager

class User(models.Model):
    title = models.CharField(max_length=255)

    objects = Manager["User"]()

reveal_type(User.objects.all().first())
# note: Revealed type is 'Optional[User]'

ForeignKey ids as properties in ORM models

When defining a Django ORM model with a foreign key, like so:

class User(models.Model):
    team = models.ForeignKey("Team", null=True, on_delete=models.SET_NULL)

two properties are created, team as expected, and team_id. In order for mypy to know about the id property we need to define it manually as follows:

from typing import TYPE_CHECKING

class User(models.Model):
    team = models.ForeignKey("Team", null=True, on_delete=models.SET_NULL)
    if TYPE_CHECKING:
        team_id: int

AutoField

By default Django will create an AutoField for you if one doesn't exist.

For type checkers to know about the id field you'll need to declare the field explicitly.

# before
class Post(models.Model):
    ...

# after
class Post(models.Model):
    id = models.AutoField(primary_key=True)

HttpRequest's user property

The HttpRequest's user property has a type of Union[AbstractBaseUser, AnonymousUser], but for most of your views you'll probably want either an authed user or an AnonymousUser.

So we can define a subclass for each case:

class AuthedHttpRequest(HttpRequest):
    user: User  # type: ignore [assignment]

And then you can use it in your views:

@auth.login_required
def activity(request: AuthedHttpRequest, team_id: str) -> HttpResponse:
    ...

You can also get more strict with your login_required decorator so that the first argument of the fuction it is decorating is AuthedHttpRequest:

from typing import Any, Union, TypeVar, cast
from django.http import HttpRequest, HttpResponse
from typing_extensions import Protocol
from functools import wraps

class RequestHandler1(Protocol):
    def __call__(self, request: AuthedHttpRequest) -> HttpResponse:
        ...


class RequestHandler2(Protocol):
    def __call__(self, request: AuthedHttpRequest, __arg1: Any) -> HttpResponse:
        ...


RequestHandler = Union[RequestHandler1, RequestHandler2]


# Verbose bound arg due to limitations of Python typing.
# see: https://github.com/python/mypy/issues/5876
_F = TypeVar("_F", bound=RequestHandler)


def login_required(view_func: _F) -> _F:
    @wraps(view_func)
    def wrapped_view(
        request: AuthedHttpRequest, *args: object, **kwargs: object
    ) -> HttpResponse:
        if request.user.is_authenticated:
            return view_func(request, *args, **kwargs)  # type: ignore [call-arg]
        raise AuthenticationRequired

    return cast(_F, wrapped_view)

Then the following will type error:

@auth.login_required
def activity(request: HttpRequest, team_id: str) -> HttpResponse:
    ...

related

django-types's People

Contributors

aleksanb avatar antonagestam avatar artofhuman avatar asfaltboy avatar bluetech avatar blueyed avatar brianhelba avatar bullfest avatar chdsbd avatar danifus avatar decentral1se avatar goldziher avatar hannseman avatar henribru avatar intgr avatar k0te avatar kalekseev avatar kszmigiel avatar lwm avatar mkurnikov avatar naddiseo avatar peterjclaw avatar quinox avatar rik avatar roderik333 avatar sbdchd avatar scop avatar sobolevn avatar syastrov avatar vsalvino avatar

Watchers

 avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.