Django模型(和其他组件)很难注释,因为它们背后有很多奇妙的技术,好消息是一群酷炫的开发者已经替我们做了艰苦的工作。
django-stubs提供了一组存根文件和mypy插件,为Django提供静态类型和类型推断。
例如,有以下模型:
from django.contrib.auth import get_user_model
from django.db import models
User = get_user_model()
class Post(models.Model):
title = models.CharField(max_length=255)
pubdate = models.DateTimeField()
author = models.ForeignKey(User, on_delete=models.CASCADE)
mypy 会抱怨并说:
demo$ mypy .
demo/models.py:9: error: Need type annotation for 'title'
demo/models.py:10: error: Need type annotation for 'pubdate'
demo/models.py:11: error: Need type annotation for 'author'
Found 3 errors in 1 file (checked 5 source files)
安装该软件包即可解决问题。
pip install django-stubs
并创建一个setup.cfg
文件,其中包含以下内容:
[mypy]
mypy_path = ./demo
plugins =
mypy_django_plugin.main
strict_optional = True
[mypy.plugins.django-stubs]
django_settings_module = demo.settings
(不要忘记根据您的设置模块的名称更新mypy_path
和django_settings_module
指向的目录)
完成此操作后,mypy将能够推断和检查Django模型(以及其他组件)的注释。
demo$ mypy .
Success: no issues found in 5 source files
以下是小视图中使用的示例:
from django.db.models.query import QuerySet
from django.http import HttpRequest, HttpResponse
from django.shortcuts import render
from demo.models import Post
def _get_posts() -> 'QuerySet[Post]':
return Post.objects.all()
def posts(request: HttpRequest, template: str='posts.html') -> HttpResponse:
return render(request, template, {'posts': _get_posts()})
再次提醒,mypy对提供的注释感到满意:
demo$ mypy .
Success: no issues found in 7 source files
同样的,Django Rest Framework 的一个包也可用: djangorestframework-stubs
IntegerField
,但如果使用Union
,那么访问该字段的所有代码都必须考虑到可能性。 - Martijn Pieters