Django5.0发布

Django 5.0 发行说明

2023 年 12 月 4 日

欢迎来到 Django 5.0!

这些发行说明涵盖了新功能,以及从 Django 4.2 或更早版本升级时需要注意的一些向后不兼容的更改。我们已经 开始对某些功能进行弃用流程

如果您要更新现有项目,请参阅如何将 Django 升级到更新版本指南。

Python 兼容性

Django 5.0 支持 Python 3.10、3.11 和 3.12。我们强烈推荐并仅官方支持每个系列的最新版本。

Django 4.2.x 系列是最后一个支持 Python 3.8 和 3.9 的版本。

对旧版本 Django 的第三方库支持

Django 5.0 发布后,我们建议第三方应用程序作者放弃对 Django 4.2 之前的所有版本的支持。那时,您应该能够使用运行包的测试,以便出现弃用警告。修复弃用警告后,您的应用程序应该与 Django 5.0 兼容。python -Wd

Django 5.0 中的新增功能

管理中的方面过滤器

现在,当通过 UI 切换时,会在管理更改列表中显示已应用过滤器的构面计数。可以通过新属性更改此行为 ModelAdmin.show_facets。有关详细信息,请参阅 构面

表单字段渲染的简化模板

Django 5.0 引入了字段组和字段组模板的概念。这简化了 Django 表单字段相关元素的呈现,例如标签、小部件、帮助文本和错误。

例如下面的模板:

python 复制代码
<form>
...
<div>
  {{ form.name.label_tag }}
  {% if form.name.help_text %}
    <div class="helptext" id="{{ form.name.auto_id }}_helptext">
      {{ form.name.help_text|safe }}
    </div>
  {% endif %}
  {{ form.name.errors }}
  {{ form.name }}
  <div class="row">
    <div class="col">
      {{ form.email.label_tag }}
      {% if form.email.help_text %}
        <div class="helptext" id="{{ form.email.auto_id }}_helptext">
          {{ form.email.help_text|safe }}
        </div>
      {% endif %}
      {{ form.email.errors }}
      {{ form.email }}
    </div>
    <div class="col">
      {{ form.password.label_tag }}
      {% if form.password.help_text %}
        <div class="helptext" id="{{ form.password.auto_id }}_helptext">
          {{ form.password.help_text|safe }}
        </div>
      {% endif %}
      {{ form.password.errors }}
      {{ form.password }}
    </div>
  </div>
</div>
...
</form>

现在可以简化为:

python 复制代码
<form>
...
<div>
  {{ form.name.as_field_group }}
  <div class="row">
    <div class="col">{{ form.email.as_field_group }}</div>
    <div class="col">{{ form.password.as_field_group }}</div>
  </div>
</div>
...
</form>

as_field_group()默认情况下使用模板呈现字段 "django/forms/field.html",并且可以根据每个项目、每个字段或每个请求进行自定义。请参阅 可重复使用的字段组模板

数据库生成的模型字段

新功能GeneratedField允许创建数据库生成的列。该字段可在所有支持的数据库后端上使用,以创建始终根据其他字段计算的字段。例如:

python 复制代码
from django.db import models
from django.db.models import F


class Square(models.Model):
    side = models.IntegerField()
    area = models.GeneratedField(
        expression=F("side") * F("side"),
        output_field=models.BigIntegerField(),
        db_persist=True,
    )

用于声明字段选择的更多选项

Field.choices (对于模型字段) 和*(对于表单字段)* 在声明其值时允许更大的灵活性。在 Django 的早期版本中,应该是二元组列表,或者是枚举类型子类,但后者需要访问属性以提供预期形式的值:ChoiceField.choices choices``.choices

python 复制代码
from django.db import models

Medal = models.TextChoices("Medal", "GOLD SILVER BRONZE")

SPORT_CHOICES = [
    ("Martial Arts", [("judo", "Judo"), ("karate", "Karate")]),
    ("Racket", [("badminton", "Badminton"), ("tennis", "Tennis")]),
    ("unknown", "Unknown"),
]


class Winner(models.Model):
    name = models.CharField(...)
    medal = models.CharField(..., choices=Medal.choices)
    sport = models.CharField(..., choices=SPORT_CHOICES)

Django 5.0 添加了对接受映射或可调用而不是可迭代的支持,并且不再需要.choices直接用于扩展枚举类型

python 复制代码
from django.db import models

Medal = models.TextChoices("Medal", "GOLD SILVER BRONZE")

SPORT_CHOICES = {  # Using a mapping instead of a list of 2-tuples.
    "Martial Arts": {"judo": "Judo", "karate": "Karate"},
    "Racket": {"badminton": "Badminton", "tennis": "Tennis"},
    "unknown": "Unknown",
}


def get_scores():
    return [(i, str(i)) for i in range(10)]


class Winner(models.Model):
    name = models.CharField(...)
    medal = models.CharField(..., choices=Medal)  # Using `.choices` not required.
    sport = models.CharField(..., choices=SPORT_CHOICES)
    score = models.IntegerField(choices=get_scores)  # A callable is allowed.

在幕后,每当更新值时,所提供的choices都会被标准化为 2 元组列表作为规范形式。choices有关更多信息,请检查选项上的模型字段参考

小功能

django.contrib.admin
  • AdminSite.get_log_entries()方法允许自定义站点列出的日志条目的查询集。
  • django.contrib.admin.AllValuesFieldListFilterChoicesFieldListFilterRelatedFieldListFilter和 admin过滤RelatedOnlyFieldListFilter器现在可以处理多值查询参数。
  • XRegExp从版本3.2.0升级到5.1.1。
  • AdminSite.get_model_admin()方法返回给定模型类的管理类。
  • 属性ModelAdmin.list_display现在支持boolean 属性。
  • jQuery从版本3.6.4升级到3.7.1。
django.contrib.auth
django.contrib.contenttypes
django.contrib.gis
django.contrib.messages
django.contrib.postgres
异步视图
  • 现在在 ASGI 下http.disconnect处理事件。如果客户端在生成响应之前断开连接,这允许视图执行任何必要的清理。有关更多详细信息,请参阅处理断开连接。
装饰器
错误报告
文件存储
  • File.open()现在将所有位置 ( *args) 和关键字参数 ( **kwargs) 传递给 Python 的内置open().
形式
  • assume_scheme参数 URLField允许指定默认 URL 方案。
  • 为了提高可访问性,进行了以下更改:
    • 表单字段现在包含aria-describedbyHTML 属性,使屏幕阅读器能够将表单字段与其帮助文本相关联。
  • 无效的表单字段现在包含aria-invalid="true"HTML 属性。
国际化
  • 现已提供维吾尔语的支持和翻译。
迁移
楷模
分页
信号
模板
测试
验证器

5.0 中向后不兼容的更改

数据库后端API

本节描述第三方数据库后端可能需要的更改。

  • DatabaseFeatures.supports_expression_defaults``False 如果数据库不支持使用数据库函数作为默认值,则应设置为。
  • DatabaseFeatures.supports_default_keyword_in_insert``False如果数据库不支持查询DEFAULT中的关键字 ,则应设置为 INSERT
  • DatabaseFeatures.supports_default_keyword_in_bulk_insert``False如果数据库不支持DEFAULT批量查询中的关键字 ,则应设置为 INSERT

django.contrib.gis

  • 删除了对 GDAL 2.2 和 2.3 的支持。
  • 删除了对 GEOS 3.6 和 3.7 的支持。

django.contrib.sitemaps

  • 由于 Google Sitemaps ping 端点已弃用,该django.contrib.sitemaps.ping_google()功能和 ping_google管理命令已被删除,并将于 2024 年 1 月删除。
  • 异常django.contrib.sitemaps.SitemapNotFound类被删除。

放弃对 MySQL < 8.0.11 的支持

删除了对 MySQL 8.0.x 系列预发行版的支持。Django 5.0 支持 MySQL 8.0.11 及更高版本。

create_defaults__exact现在可能需要使用QuerySet.update_or_create()

QuerySet.update_or_create()现在支持参数 create_defaults. 因此,任何具有 create_defaults与 一起使用的名为 的字段的模型update_or_create()都应该在查找中使用 指定该字段create_defaults__exact

迁移UUIDFieldMariaDB 10.7+ 上的现有版本

在 MariaDB 10.7+ 上,UUIDField现在创建为UUID列而不是 CHAR(32)列。因此,UUIDField在 Django < 5.0 中创建的任何内容都应该替换为以下UUIDField子类 CHAR(32)

复制代码
class Char32UUIDField(models.UUIDField):
    def db_type(self, connection):
        return "char(32)"

例如:

复制代码
class MyModel(models.Model):
    uuid = models.UUIDField(primary_key=True, default=uuid.uuid4)

应该变成:

复制代码
class Char32UUIDField(models.UUIDField):
    def db_type(self, connection):
        return "char(32)"


class MyModel(models.Model):
    uuid = Char32UUIDField(primary_key=True, default=uuid.uuid4)

运行该makemigrations命令将生成包含无操作操作的迁移AlterField

各种各样的

  • instance未记录方法的参数 被BaseModelFormSet.save_existing()重命名为obj
  • 无证的django.contrib.admin.helpers.checkbox被删除。
  • 整数字段现在在 SQLite 上验证为 64 位整数,以匹配sqlite3.
  • 未记录的Query.annotation_select_mask属性从一组字符串更改为有序的字符串列表。
  • ImageField.update_dimension_fields()``post_init如果width_fieldheight_field未设置,则不再在信号上调用 。
  • Now现在使用数据库功能 LOCALTIMESTAMP而不是CURRENT_TIMESTAMPOracle 上的功能。
  • AdminSite.site_header现在在标签中呈现,<div>而不是在 <h1>. 屏幕阅读器用户依靠标题元素在页面内进行导航。有两个<h1>元素很令人困惑,而且站点标题没有帮助,因为它在所有页面上重复。
  • 为了提高可访问性,管理员的主要内容区域和标题内容区域现在呈现在 a<main><header>标记中,而不是 <div>
  • 在不支持 SQLXOR运算符的数据库上,^异或 ( XOR) 运算符现在返回与奇数个操作数匹配的行,而不是仅与一个操作数匹配。这与 MySQL、MariaDB 和 Python 的行为一致。
  • 最低支持版本asgiref从 3.6.0 增加到 3.7.0。
  • 最低支持版本selenium从 3.8.0 增加到 4.8.0。
  • 和例外AlreadyRegistered情况NotRegistereddjango.contrib.admin.sites移至django.contrib.admin.exceptions
  • SQLite 的最低支持版本从 3.21.0 增加到 3.27.0。
  • cx_Oracle删除了对 <8.3 的支持。
  • 现在,在应用程序注册表完全填充之前执行 SQL 查询会引发RuntimeWarning.
  • BadRequest针对具有application/x-www-form-urlencoded 内容类型的非 UTF-8 编码请求引发。看RFC 1866了解更多详细信息。
  • 最低支持版本colorama增加至0.4.6。
  • 最低支持版本docutils增加至0.19。

5.0 中弃用的功能

各种各样的

  • 和过渡形式DjangoDivFormRenderer渲染Jinja2DivFormRenderer器已被弃用。
  • 不推荐使用传递位置参数nameviolation_error_messageto BaseConstraint,而是使用仅关键字参数。
  • request添加到 的签名中ModelAdmin.lookup_allowed()。不推荐支持ModelAdmin不接受此参数的子类。
  • and 方法get_joining_columns()已被弃用。从 Django 6.0 开始, 将不再回退到 . 子类应该 代替实现。ForeignObject``ForeignObjectRel``django.db.models.sql.datastructures.Join``get_joining_columns()``get_joining_fields()
  • ForeignObject.get_reverse_joining_columns()方法已被弃用。
  • 在 Django 6.0 中,默认方案forms.URLField将从 更改"http""https"。将FORMS_URLFIELD_ASSUME_HTTPS 过渡设置设置为True选择"https"在 Django 5.x 发布周期期间进行假设。
  • FORMS_URLFIELD_ASSUME_HTTPS过渡设置已被弃用。
  • 对不传递 args 或 kwargs 的调用的支持format_html()将被删除。
  • cx_Oracle不推荐使用对oracledb 1.3.2+ Python 驱动程序的支持。
  • DatabaseOperations.field_cast_sql()已被弃用,取而代之的是 DatabaseOperations.lookup_cast(). 从 Django 6.0 开始, BuiltinLookup.process_lhs()将不再调用field_cast_sql(). 第三方数据库后端应该改为实施lookup_cast()
  • django.db.models.enums.ChoicesMeta类被重命名为 ChoicesType.
  • Prefetch.get_current_queryset()方法已被弃用。
  • 相关管理器和描述符的方法get_prefetch_queryset()已被弃用。从 Django 6.0 开始,get_prefetcher()prefetch_related_objects()不再回退到 get_prefetch_queryset(). 子类应该 get_prefetch_querysets()代替实现。

5.0 中删除的功能

这些功能已达到其弃用周期的末尾,并在 Django 5.0 中删除。

有关这些更改的详细信息,包括如何删除这些功能的使用,请参阅4.0 中已弃用的功能。

  • 测试SERIALIZE设置已删除。
  • 未记录的django.utils.baseconv模块已被删除。
  • 未记录的django.utils.datetime_safe模块已被删除。
  • 设置的默认值USE_TZ从 更改FalseTrue
  • 在请求上下文之外构建的站点地图的默认站点地图协议已从 更改'http''https'
  • extra_tests的参数被删除。DiscoverRunner.build_suite()``DiscoverRunner.run_tests()
  • 当没有行时django.contrib.postgres.aggregates.ArrayAggJSONBAgg、 和 聚合StringAgg不再分别返回[][]和。''
  • USE_L10N设置被删除。
  • 过渡USE_DEPRECATED_PYTZ设置被删除。
  • pytz删除了对时区的支持。
  • is_dst参数被删除:
    • QuerySet.datetimes()
    • django.utils.timezone.make_aware()
    • django.db.models.functions.Trunc()
    • django.db.models.functions.TruncSecond()
    • django.db.models.functions.TruncMinute()
    • django.db.models.functions.TruncHour()
    • django.db.models.functions.TruncDay()
    • django.db.models.functions.TruncWeek()
    • django.db.models.functions.TruncMonth()
    • django.db.models.functions.TruncQuarter()
    • django.db.models.functions.TruncYear()
  • django.contrib.gis.admin.GeoModelAdminOSMGeoAdmin被删除。
  • 未记录的BaseForm._html_output()方法已被删除。
  • 渲染and时返回 astr而非 a 的功能已被删除。SafeString``ErrorDict``ErrorList

有关这些更改的详细信息,包括如何删除这些功能的使用,请参阅4.1 中已弃用的功能。

  • SitemapIndexItem.__str__()方法已被删除。
  • 过渡CSRF_COOKIE_MASKED设置被删除。
  • name的参数被django.utils.functional.cached_property()删除。
  • opclasses的参数 被django.contrib.postgres.constraints.ExclusionConstraint删除。
  • errors=None未记录的传递给 SimpleTestCase.assertFormError()和 的能力assertFormsetError()被删除。
  • django.contrib.sessions.serializers.PickleSerializer已移除。
  • 不再允许在不提供参数的情况下使用QuerySet.iterator()预取相关对象的查询集。chunk_size
  • 不再允许将未保存的模型实例传递给相关过滤器。
  • created=True子类的签名中需要 RemoteUserBackend.configure_user()
  • 通过和 GET中的请求 注销的支持已被删除。django.contrib.auth.views.LogoutView``django.contrib.auth.views.logout_then_login()
  • 别名django.utils.timezone.utctodatetime.timezone.utc已删除。
  • 不再允许将响应对象和表单/表单集名称传递给 SimpleTestCase.assertFormError()and 。assertFormSetError()
  • django.contrib.gis.admin.OpenLayersWidget删除。
  • django.contrib.auth.hashers.CryptPasswordHasher删除。
  • "django/forms/default.html"模板 "django/forms/formsets/default.html"被删除。
  • 默认表单和表单集渲染样式更改为基于 div。
  • nulls_first=Falseornulls_last=False传递给Expression.asc() andExpression.desc()方法,并且OrderBy不再允许使用表达式。
相关推荐
小白学大数据1 小时前
Scrapy框架下地图爬虫的进度监控与优化策略
开发语言·爬虫·python·scrapy·数据分析
浊酒南街1 小时前
TensorFlow之微分求导
人工智能·python·tensorflow
立秋67891 小时前
用Python绘制梦幻星空
开发语言·python·pygame
alpszero1 小时前
YOLO11解决方案之对象裁剪探索
人工智能·python·计算机视觉·yolo11
白云千载尽2 小时前
相机、雷达标定工具,以及雷达自动标定的思路
python·自动驾驶·ros
咕噜咕噜啦啦2 小时前
python爬虫实战训练
爬虫·python
盛夏绽放2 小时前
Python字符串常用内置函数详解
服务器·开发语言·python
我想睡觉2612 小时前
Python训练营打卡DAY27
开发语言·python·机器学习
蹦蹦跳跳真可爱5892 小时前
Python----神经网络(基于DNN的风电功率预测)
人工智能·pytorch·python·深度学习·神经网络·dnn
冰轮a2 小时前
Python打卡 DAY 27
python