# Wagtail 7.2 release notes

_November 5, 2025_

```{contents}
---
local:
depth: 1
---
```

## What's new

### Python 3.14 support

This release adds formal support for Python 3.14.

### Reordering support for model and snippet listing views

The listing view of {class}`~.ModelViewSet` and {class}`~.SnippetViewSet` now supports reordering of items using drag-and-drop. This feature can be enabled by setting the name of an integer field used for ordering as the {attr}`~.ModelViewSet.sort_order_field` attribute on the viewset or on the model. This can be a custom field, or set via inheriting [Orderable](wagtail.models.Orderable).

Make sure to set default values for the sort order field on existing items before enabling this feature to avoid unexpected behavior. Here is an example: `BreadType.objects.all().update(sort_order=F('pk') - 1)`.

This feature was developed by Joey Jurjens and Sage Abdullah.

### Media listings improvements

Admin and document listings now support filtering by usage count. Image choosers now have both grid and list layouts, with a new toggle for users to switch between the two. The new toggle has also been added to standalone image listings for consistency.

Thank you to Joel William for implementing this as part of the [Google Summer of Code program](https://wagtail.org/blog/four-contributors-for-gsoc-2025/), with support from Coen van der Kamp, Sage Abdullah, Thibaud Colas, Ben Enright.

### Readability score metric

Built-in [content checks](https://guide.wagtail.org/en-latest/reference/content-checks/) now include a readability score, based on length of words and sentences in the page content. The content metrics also now provide an explainer panel detailing how they are calculated. This feature was developed by Thibaud Colas.

### Quick access to first validation error

Error messages for form validation errors now contain a "Go to the first error" shortcut button. This speeds up navigating to address error messages, particularly for forms split between multiple tabs, where the errors can be hard to locate. This feature was developed by Srishti Jaiswal, Sage Abdullah and LB (Ben) Johnston.

### Elasticsearch 9 and OpenSearch backends

Wagtail's search mechanism is now handled by the external [Django Modelsearch](https://django-modelsearch.readthedocs.io/en/latest/) library. This change will take effect automatically on upgrading to Wagtail 7.2, with no configuration changes required to most existing projects (but see the upgrade consideration notes below).

As part of this update, dedicated backends for OpenSearch and Elasticsearch 9 are now available; previously OpenSearch was only supported through a legacy version of the Elasticsearch 7 client library. For instructions on configuring these backends, see [](wagtailsearch_backends). Django Modelsearch is developed by Karl Hobley, with additional contributions and Wagtail compatibility developed by Matt Westcott.

### Keyboard shortcuts improvements

We introduce two new shortcuts, `?` to open the keyboard shortcuts dialog, and `/` to focus the search input in the sidebar. The keyboard shortcuts dialog has been reorganized into better categories. When keyboard shortcuts are disabled in user preferences, the "add comment" shortcut is also disabled, and messaging has been added to the keyboard shortcuts dialog to indicate the status of keyboard shortcuts and how to enable or disable them via user preferences. This feature was developed by Pravin Kamble.

Thank you to Dhruvi Patel for implementing this as part of the [Google Summer of Code program](https://wagtail.org/blog/four-contributors-for-gsoc-2025/), with support from LB (Ben) Johnston, Scott Cranfill, Thibaud Colas.

### Other features

 * Allow deep contentpath for comments on fields other than StreamField (Lasse Schmieding, Sébastien Corbin, Joel William, Sage Abdullah)
 * Add `max_value` of 100 (%) for the `closeness` field in Image URL Generator form (LB (Ben) Johnston)
 * Allow defining a custom `WorkflowLock` subclass via [`Task.lock_class`](custom_task_lock_class) in a custom task (Dan Braghis)
 * Support calculating content metrics without opening the preview panel (Sage Abdullah)
 * Update project template settings to use pathlib Path object (Eric Matthes)

### Bug fixes

 * Use the correct method of resolving the file storage dynamically for `FileField` usage in images & documents (Amir Mahmoodi)
 * Use model name when ordering by page type in page listings (Sage Abdullah)
 * Prevent error from default `update_fields` parameter on `Page.asave()` (Tosinibikunle)
 * Ignore hidden error messages in minimap & `CountController` default `findValue` (Sage Abdullah)
 * Change default ordering for `UserViewSet` to `User.USERNAME_FIELD` to support default ordering with custom User models that may not have a `name` field (Lynwee)
 * Ensure starter tests in the project template pass (Lasse Schmieding)
 * Ensure fixed RichText toolbar shows under footer actions (Maciek Baron)
 * Prevent error when iterating over specific tasks with missing models (Lasse Schmieding)
 * Ensure `TableBlock` header dropdown default option can be translated (arpitmak)
 * Fix missing cache key prefix when removing cached redirect files (Heric Libong)

### Documentation

 * Fix cross-reference links to the TypeDoc-generated docs (Sage Abdullah)
 * Refine readthedocs' search indexing for releases and client-side code (Sage Abdullah)
 * Fix incorrect link to third party site in advanced topics (Yousef Al-Hadhrami (Yemeni))
 * Fix incorrect import references and update steps for clarity in getting started tutorial (Hunzlah Malik, Pravin Kamble)
 * Fix code example for `construct_wagtail_userbar` (Baptiste Mispelon)
 * Add a note about CSP for background image position and responsive embed styles (Thibaud Colas, Chiemezuo Akujobi, Sage Abdullah)
 * Add guidance for AI-led contributions to contributor docs (Andrew Selzer)
 * Add guidance for AI agents via `AGENTS.md` (Andrew Selzer)
 * Add Windows command examples for contributing setup (Shivam Kumar)
 * Add recent third party tutorials from 2025 (LB (Ben) Johnston)

### Maintenance

 * Removed support for Python 3.8 (Matt Westcott)
 * Test against Python 3.14 prerelease (Sage Abdullah)
 * Updated NPM packages and linting configuration (LB (Ben) Johnston)
 * Added linting script to keep package.json and pre-commit package versions in sync (LB (Ben) Johnston)
 * Migrate privacy switch modal field hiding to the Stimulus [`RulesController`](controller:RulesController) (LB (Ben) Johnston)
 * Add semgrep rules for inline styles and scripts (Chiemezuo Akujobi, Sage Abdullah)
 * Fix intermittent test failures caused by nondeterministic order in TestFilteredModelChoiceField (Sage Abdullah)
 * Add support for `attrs` in `formattedfield` tag & clean up other usages of the `attrs` template include (LB (Ben) Johnston)
 * Allow exempting external templates from number formatting checks (Sage Abdullah)
 * Migrate file title generation to SyncController for CSP compliance (Aayushman Singh, Chiemezuo Akujobi, LB (Ben) Johnston, Sage Abdullah)
 * Remove outdated pytest configuration (Shivam Kumar)
 * Avoid mutable default argument in `ImageNode` within image template tags (minusf)
 * Use consistent sentence format for user-facing errors (LB (Ben) Johnson)
 * Update django-tasks dependency to allow 0.9, for preliminary Django 6.0 support (Sage Abdullah)
 * Fix linting issues B009 and B010 (`getattr` & `setattr` uses constant) plus B033 (avoid duplicate values in set literals) (minusf)


## Upgrade considerations - changes affecting all projects

### Elasticsearch and OpenSearch users should run `update_index` after upgrading

Users of the Elasticsearch and OpenSearch backends are advised to run the command `./manage.py update_index` after upgrading to Wagtail 7.2. If this is already set up to run on a regular schedule as recommended, no further action is required.

This is due to a change in the indexed document structure - specifically, the `content_type` field has been renamed to `_django_content_type`. Indexed documents will be upgraded to the new format on the next run of the `update_index` command. As of this release the old and new document format are handled equivalently, and searches will continue to work as before; however, support for the old format will be dropped in Wagtail 8.0. Consequently, upgrading to Wagtail 8.0 without first having run `update_index` on Wagtail 7.2 or later may result in incomplete search results.

### `ATOMIC_REBUILD` now active by default on Elasticsearch and OpenSearch

The `ATOMIC_REBUILD` option, which rebuilds Elasticsearch and OpenSearch indexes as a fresh copy allowing searching to continue on the existing copy while rebuilding is in progress, is now enabled by default. If this is not appropriate for your configuration (for example, the user account used to connect to the server does not have permission to create indexes, or your service provider imposes a strict limit on the number of indexes), you can revert to the previous behavior by adding `"ATOMIC_REBUILD": False` to the backend's configuration options in `WAGTAILSEARCH_BACKENDS`.

### `INDEX` configuration option on Elasticsearch and OpenSearch replaced with `INDEX_PREFIX`

The `INDEX` configuration option for Elasticsearch and OpenSearch backends has been deprecated. This option specifies a prefix to be used on all index names, allowing multiple Wagtail instances to share the same Elasticsearch server. This has now been replaced with the `INDEX_PREFIX` option. For example, the option `"INDEX": "mysite"` should now be replaced with `"INDEX_PREFIX": "mysite_"` (note the trailing `_` character).

The `INDEX` option is still recognized in this release, but support for this will be dropped in Wagtail 8.0. For backends other than Elasticsearch and OpenSearch, the `INDEX` option is no longer used and can be removed.

## Upgrade considerations - deprecation of old functionality

### Removed support for Python 3.9

Python 3.9 is no longer supported as of this release; please upgrade to Python 3.10 or above before upgrading Wagtail.

## Upgrade considerations - changes to undocumented internals

### File title generation in document and image uploads now uses SyncController

The JavaScript code previously used to generate the title from the file name when uploading images or documents has been replaced with a Stimulus [`SyncController`](controller:SyncController) implementation. This change improves compliance with Content Security Policy (CSP) by avoiding the need for inline scripts.

The events described in [images title generation on upload](images_title_generation_on_upload) and [documents title generation on upload](docs_title_generation_on_upload) still continue to work as before. However, they may be deprecated in a future release in favor of the events dispatched by the `SyncController` with the `w-sync` prefix.

The use of `creationFormFileFieldSelector`, `creationFormTitleFieldSelector`, `creationFormEventName` options in `ChooserModalOnloadHandlerFactory` have been deprecated and will be removed in a future release.

### `refresh_index` method on search backends renamed to `refresh_indexes`

The undocumented `refresh_index` method on search backend instances has been renamed to `refresh_indexes`, to reflect the fact that it acts on all indexes managed by the backend.
