PHP 8.5 support in WordPress 6.9

PHP 8.5 was released on November 20th. Contributors to WordPress have been busy in recent months preparing for this version and weโ€™re happy to report that all issues reported against PHPPHP The web scripting language in which WordPress is primarily architected. WordPress requires PHP 7.4 or higher 8.5 have been addressed in WordPress 6.9 RC2. Compared to previous PHP releases relatively few changes were required, mostly to address new deprecations and warnings. Take a look at the PHP 8.5 support tracking ticket if youโ€™re interested.

Due to the acknowledgement that WordPress is rarely used in isolation (without any theme or plugins), support is labelled as โ€œbetaBeta A pre-release of software that is given out to a large group of users to trial under real conditions. Beta versions have gone through alpha testing in-house and are generally fairly close in look, feel and function to the final product; however, design changes often occur as part of the process. supportโ€ until at least 10% of all WordPress sites are running that version or later, as this indicates good compatibility across the wider ecosystem of plugins and themes.

PHP Compatibility and WordPress Versions page in the WordPress Core Handbook

Following the established guidelines, support for any given version of PHP is labelled as โ€œbeta supportโ€ until at least 10% of all WordPress sites are running that version or later. When WordPress 6.9 ships on December 2nd, support for PHP 8.5 and 8.4 will be labelled as โ€œbeta supportโ€. PHP versions 8.3 back to 7.2 are fully supported.

If you discover a bugbug A bug is an error or unexpected result. Performance improvements, code optimization, and are considered enhancements, not defects. After feature freeze, only bugs are dealt with, with regressions (adverse changes from the previous version) being the highest priority. or compatibility issue while running WordPress with PHP 8.5, please create a ticket on Trac.

Summary

As always, reading through the complete upgrade document is recommended.

Even as WordPress CoreCore Core is the set of software required to run WordPress. The Core Development Team builds WordPress. continues to expand its support for new versions of PHP, support for older versions will remain as-is in WordPress 6.9, staying at PHP 7.2.24 and higher. This will continue to be evaluated and no change will be made until usage numbers show that the impact on users will be minimal.

WordPress continues to encourage all users to run the latest and greatest versions of PHP, including PHP 8.5.

Props @desrosj, @jorbin for reviewing this post.

#6-9, #dev-notes, #dev-notes-6-9, #php-compatibility

Summary, Dev Chat, November 19, 2025

Startย of the meeting inย SlackSlack Slack is a Collaborative Group Chat Platform https://slack.com/. The WordPress community has its own Slack Channel at https://make.wordpress.org/chat/, facilitated by @amykamala ๐Ÿ”— Agenda post.

Announcements ๐Ÿ“ข

GutenbergGutenberg The Gutenberg project is the new Editor Interface for WordPress. The editor improves the process and experience of creating new content, making writing rich content much simpler. It uses โ€˜blocksโ€™ to add richness rather than shortcodes, custom HTML etc. https://wordpress.org/gutenberg/ย 22.1 has been released!

Gutenberg 22.1ย has been released and isย available for download! Thanks to @psykroย for writing this wonderful overview.

WordPress 6.9ย Release Candidaterelease candidate One of the final stages in the version release cycle, this version signals the potential to be a final release to the public. Also see alpha (beta).ย 2 is now available!

WordPress 6.9 Release Candidate 2 is now available for download and testing.
Further information you can find here.

WordPress 6.9ย Dev Notesdev note Each important change in WordPress Core is documented in a developers note, (usually called dev note). Good dev notes generally include a description of the change, the decision that led to this change, and a description of how developers are supposed to work with that change. Dev notes are published on Make/Core blog during the beta phase of WordPress release cycle. Publishing dev notes is particularly important when plugin/theme authors and WordPress developers need to be aware of those changes.In general, all dev notes are compiled into a Field Guide at the beginning of the release candidate phase.

For more detailed information, see the following WordPress 6.9 Dev Notes:

Forthcoming releases ๐Ÿš€

WordPress 6.9 Timeline

WordPress 6.9ย is planned forย December 2, 2025. Release Candidate 3 is planned forย November 25.

Call for Testing

The Test Team invitesย testing and feedbackย on the following upcomingย blockBlock Block is the abstract term used to describe units of markup that, composed together, form the content or layout of a webpage using the WordPress editor. The idea combines concepts of what in the past may have achieved with shortcodes, custom HTML, and embed discovery into a single consistent API and user experience.ย editor features:

Discussions ๐Ÿ’ฌ

CoreCore Core is the set of software required to run WordPress. The Core Development Team builds WordPress. Block Decisions

The discussion focused on how decisions are made about which new blocks should be added to Core. @elrae raised concerns that there is no clear standard, and that blocks like the Math block benefit only a very small group of users. Others argued that Core blocks improve consistency, accessibilityAccessibility Accessibility (commonly shortened to a11y) refers to the design of products, devices, services, or environments for people with disabilities. The concept of accessible design ensures both โ€œdirect accessโ€ (i.e. unassisted) and โ€œindirect accessโ€ meaning compatibility with a personโ€™s assistive technology (for example, computer screen readers). (https://en.wikipedia.org/wiki/Accessibility), and reliability across websites. Everyone agreed that clearer and more transparent guidelines are needed to determine which blocks are truly useful and worth maintaining in the long run.

#6-9, #core, #dev-chat

Whatโ€™s new in Gutenberg 22.1? (18 November, 2025)

โ€œWhatโ€™s new in GutenbergGutenberg The Gutenberg project is the new Editor Interface for WordPress. The editor improves the process and experience of creating new content, making writing rich content much simpler. It uses โ€˜blocksโ€™ to add richness rather than shortcodes, custom HTML etc. https://wordpress.org/gutenberg/โ€ฆโ€ posts (labeled with the #gutenberg-new tag) are posted following every Gutenberg release on a biweekly basis, showcasing new features included in each release. As a reminder, hereโ€™s an overview of different ways to keep up with Gutenberg and the Editor.

Whatโ€™s New In
Gutenberg 22.1?

Gutenberg 22.1 has been released and is available for download!

This release focuses on expanding blockBlock Block is the abstract term used to describe units of markup that, composed together, form the content or layout of a webpage using the WordPress editor. The idea combines concepts of what in the past may have achieved with shortcodes, custom HTML, and embed discovery into a single consistent API and user experience. capabilitiescapability Aย capabilityย is permission to perform one or more types of task. Checking if a user has a capability is performed by the current_user_can function. Each user of a WordPress site might have some permissions but not others, depending on theirย role. For example, users who have the Author role usually have permission to edit their own posts (the โ€œedit_postsโ€ capability), but not permission to edit other usersโ€™ posts (the โ€œedit_others_postsโ€ capability)., enhancing the editor UXUX User experience, and performance improvements. New features include the new coreCore Core is the set of software required to run WordPress. The Core Development Team builds WordPress./tabs block for tabbed content, enabling JavaScriptJavaScript JavaScript or JS is an object-oriented computer programming language commonly used to create interactive effects within web browsers. WordPress makes extensive use of JS for a better user experience. While PHP is executed on the server, JS executes within a userโ€™s browser. https://www.javascript.com and CSSCSS Cascading Style Sheets. editing added to the HTML block, and image prefetching when expanding images in the editor. Other updates include many theme/color tweaks, DataViews and DataForm refinements, collaboration improvements, accessibilityAccessibility Accessibility (commonly shortened to a11y) refers to the design of products, devices, services, or environments for people with disabilities. The concept of accessible design ensures both โ€œdirect accessโ€ (i.e. unassisted) and โ€œindirect accessโ€ meaning compatibility with a personโ€™s assistive technology (for example, computer screen readers). (https://en.wikipedia.org/wiki/Accessibility) and performance optimizations, and numerous bugbug A bug is an error or unexpected result. Performance improvements, code optimization, and are considered enhancements, not defects. After feature freeze, only bugs are dealt with, with regressions (adverse changes from the previous version) being the highest priority. fixes and documentation updates.

New Tabs block

As the name suggests, the new Tabs block allows you to add tabbed content to your posts, pages, and templates.ย 

Enable the Blocks: add experimental blocks setting to test the tabs block.

HTMLHTML HyperText Markup Language. The semantic scripting language primarily used for outputting content in web browsers. block updates

The HTML block now supports adding and editing CSS and JavaScript.

Other Notable Highlights

Image prefetching when expanding images in the editor

Changelog

Features

Block Library

  • New Block: core/tabs. (69789)

Enhancements

  • Routing: Add static and lazy routes support to the boot package. (72937)
  • Theme: Add new caution color ramp. (72782)
  • Theme: Lower the contrast topup value. (73155)
  • Theme: Optimize seed adjustment. (73004)

DataViews

  • Add a context menu when right-clicking on the table headerHeader The header of your site is typically the first thing people will experience. The masthead or header art located across the top of your page is part of the look and feel of your website. It can influence a visitorโ€™s opinion about your content and you/ your organizationโ€™s brand. It may also look different on different screen sizes.. (73104)
  • DataForm: Add new details layout. (72355)
  • DataForm: Simplify form normalization. (72848)
  • DataForm: Card borderless layout. (72514)
  • DataViews list layout: Use regular button for primary action. (72920)
  • DataViewsPicker: Add With Modal storybook story. (72913)
  • Simplify the properties configuration. (73064)
  • Try adding table view to data picker. (72914)
  • Update actions menu structure to group primary and regular actions. (72866)

Block Library

  • Breadcrumbs: Add 404, search and paged support for archives. (72714)
  • Breadcrumbs: Add home page handling and show last item attribute. (72839)
  • Change Accordion block toolbar label to spell โ€œAdd Accordion Itemโ€. (72981)
  • HTML Block: Add JSJS JavaScript, a web scripting language typically executed in the browser. Often used for advanced user interfaces and behaviors./CSS editing. (73108)
  • Paragraph: Migrate to text-align block support. (73111)
  • Update/twitter to X embed icon and text. (73110)

Collaboration

  • Notes: Add form submission shortcut. (72868)
  • Notes: Add keyboard support for tree navigation. (73136)
  • Notes: Disable โ€œAdd noteโ€ button in Distraction free mode. (72954)
  • Notes: Remove the pin/unpin button from the sidebarSidebar A sidebar in WordPress is referred to a widget-ready area used by WordPress themes to display information that is not a part of the main content. It is not always a vertical column on the side. It can be a horizontal rectangle below or above the content area, footer, header, or any where in the theme. header. (72825)

Patterns

  • Hide toolbar slots for contentOnly pattern wrappers. (73182)
  • Starter content: Change alignment and copy. (72829)
  • contentOnly patterns: Mark patterns as contentOnly by adding metadata.patternName to the root block. (72988)

Components

  • Add isBusy prop to ConfirmDialog. (73041)
  • Card Component Padding System Enhancementenhancement Enhancements are simple improvements to WordPress, such as the addition of a hook, a new feature, or an improvement to an existing feature.. (72511)
  • TextareaControl: Add min-height to textarea. (72867)

Colors

  • ColorPicker: Support pasting whole color values. (73166)

Synced Patterns

  • Update synced pattern language from โ€œDetachโ€ to โ€œDisconnect patternโ€. (73105)

Extensibility

  • Term Name: Add levelOptions attribute to control available heading levels. (73005)

Write mode

  • Use color panel for contentOnly pattern editing. (71982)

Block Editor

  • BlockVariationTransforms: Refactor DropdownMenu with Menu. (71938)

Bug Fixes

  • Fix unresolvable typedefs in dependency-extraction-webpack-pluginPlugin A plugin is a piece of software containing a group of functions that can be added to a WordPress website. They can extend functionality or add new features to your WordPress websites. WordPress plugins are written in the PHP programming language and integrate seamlessly with WordPress. These can be free in the WordPress.org Plugin Directory https://wordpress.org/plugins/ or can be cost-based plugin from a third-party.. (72807)
  • Math format: Force LTR direction in RTL languages. (72901)
  • Math format: Remove empty format on serialise. (73143)
  • Template activation: Disallow editing/trashing of non-database templates. (72790)
  • Template activation: Inserting template through /templates should always result in active template. (72770)
  • Template activation: Redirect to โ€˜Create Templatesโ€™ after duplication. (72727)
  • Template activation: Skip gutenberg_get_registered_block_templates query when no slugs are left to find. (72795)
  • Theme: Fix Windows build using cross-env for environment variables. (72944)
  • block-editor: Remove types from package.jsonJSON JSON, or JavaScript Object Notation, is a minimal, readable format for structuring data. It is used primarily to transmit data between a server and web application, as an alternative to XML. exports. (72817)
  • i18ni18n Internationalization, or the act of writing and preparing code to be fully translatable into other languages. Also see localization. Often written with a lowercase i so it is not confused with a lowercase L or the numeral 1. Often an acquired skill.: Use _x() for Template Activation labels. (72928)

Collaboration

  • Block Notes: Adjust note date tooltip position. (72843)
  • Change sidebar title โ€“ Change Notes to All notes. (72885)
  • Disable Notes in Code Editor. (72859)
  • Ensure editor body fits all notes. (72811)
  • Hide add note in distraction free mode. (72835)
  • Notes: Disable or hide โ€œAdd noteโ€ button depending on blockโ€™s state. (72878)
  • Notes: Donโ€™t hide floating sidebar while adding the note. (72968)
  • Notes: Fix โ€˜Add noteโ€™ form position. (72787)
  • Notes: Fix avatarAvatar An avatar is an image or illustration that specifically refers to a character that represents an online user. Itโ€™s usually a square box that appears next to the userโ€™s name. image size in mobile layout. (73008)
  • Notes: Fix first note creation with pinned sidebar. (73164)
  • Notes: Fix selector for orderedBlockIds. (73006)
  • Notes: Fix sidebar opening logic. (72965)
  • Notes: Gracefully handle non-existing note ID references (alt). (73061)
  • Notes: Hide pinned sidebar when there are no notes. (72872)
  • Notes: Refine avatar. (72773)
  • Notes: Spotlight block when clicking add/view notes. (72870)

Block Library

  • Accordion Header, Panel: Add CSS for the default style. (73032)
  • Accordion block: Lock core/accordion iAPI store. (72977)
  • Accordion: Allow font style inheritance from button to inner text blocks. (72957)
  • Allow embeds to grow and shrink inside flex group blocks. (73109)
  • Breadcrumbs: Add fallback for posts with no title. (72869)
  • Cover Block: Show settings inspector controls in the Site Editor. (69178)
  • Fix Navigation Link block variations to show correct labels instead of generic โ€˜Post Linkโ€™. (72517)
  • Fix Navigation Link broken state when bound entity is deleted. (73142)
  • Fix: Hideย  input popover when editing Math block as HTML. (72902)
  • Heading block: Make background padding more specific to block. (72837)
  • Increase CSS specificity of text alignment classes. (62260)
  • Math: Fixing Edit as HTML feature and code editor sync. (72910)

Block Editor

  • Add: Stretch text variations transforms. (73148)
  • Fix padding appender last block focus. (72821)
  • Fix: Donโ€™t load fit text front end scripts on the editor. (72842)
  • Fix: Fit Text flash during the binary search on the initial enabling. (72788)
  • Fix: Fit text may not update when being grouped in a smaller container. (73021)
  • Fix: Make fit text work with the interativity APIAPI An API or Application Programming Interface is a software intermediary that allows programs to interact with each other and share data in limited, clearly defined ways.. (72923)
  • Update: Use a bigger max fit text font size. (73067)
  • Stretch text and stretch heading variation. (73056)

DataViews

  • DataViews Table โ€“ only output aria-label for media when item is clickable. (73034)
  • Fix DataView columns width. (72969)
  • Fix pagination. (73132)
  • Fix: DataViews modal actions in list layout. (72793)
  • Use local time in summary filterFilter Filters are one of the two types of Hooks https://codex.wordpress.org/Plugin_API/Hooks. They provide a way for functions to modify data of other functions. They are the counterpart to Actions. Unlike Actions, filters are meant to work in an isolated manner, and should never have side effects such as affecting global variables and output. and default render for datetime fields. (72756)
  • useFormValidity: Fix nesting levels. (72588)

Global Styles

  • Restore correct additional CSS screen layout. (73192)
  • Show Global Styles in editor only for users with the right caps. (73077)
  • Theme JSON: Fix handling of default presets at block level. (72916)

Components

  • Button: Revert disabled primary button state to its previous one. (73037)
  • CustomSelectControl: Use key to determine the selected item instead of name. (72189)
  • NumberControl: Fix crash when min prop is string and step prop contains decimal. (73107)

Post Editor

  • Editor: Fix template panel check and restore duplicate action. (72964)
  • Fix setupEditor edits not being applied when non-iterable edits are used. (73167)

Site Editor

  • Pages DataViews: Fix content preview field after global styles refactor. (73140)
  • Use padding appender hook in Site editor. (72598)
  • Theme: Disable bgramp tests to fix trunktrunk A directory in Subversion containing the latest development code in preparation for the next major release cycle. If you are running "trunk", then you are on the latest revision. failures. (73122)

Command Palette

  • Commands:ย  Add edit template if user has proper caps. (73087)
  • Decode HTML entities in menu URLURL A specific web address of a website or web page on the Internet, such as a websiteโ€™s URL www.wordpress.org. (72898)

Design Tools

  • Border Panel: Decode values so that border radius presets are properly handled in global styles. (73072)
  • Border radius presets: Support mixed values in the rangecontrol slider. (73033)

Block API

  • Classic Block: Disable lock, renaming, blockVisibility, html support. (72812)
  • Unsupported Block: Disable lock, renaming, blockVisibility support. (72857)

Commands

  • Fix: Adminadmin (and super admin) color scheme is not applied to Command Palette. (73151)

Rich Text

  • RichText: Donโ€™t forget ref passing in Preview mode. (73062)

Synced Patterns

  • Add specific classname to block toolbar icon. (73058)

Media

  • Fix adding blocks through media tab with experimental modal. (73029)

Block Locking

  • Fix contentOnly temporary editing persisting on save (+ refactor some of the code). (72959)

Block Transforms

  • Add default transform for allowedBlocks attribute. (72814)

Block bindings

  • Hide Attributes panel for Date, Nav Link, and Nav Submenu blocks. (72712)

Accessibility

Collaboration

  • Notes: Fix block toolbar display for show icon labels. (73010)
  • Notes: Fix focus return when resolving floating note. (72994)
  • Notes: Focus action button when comment editing is cancelled or comment is updated. (72895)
  • Notes: Improve accessibility tree. (72650)

Block Library

  • Prevent Esc from executing changes in categoryCategory The 'category' taxonomy lets you group posts / content together that share a common bond. Categories are pre-defined and broad ranging. and archive widgets. (72889)

Performance

  • Move PatternOverrideToolbarIndicator functionality into BlockToolbar. (72935)
  • Theme: Add caching for theme color ramp builders. (72796)
  • Theme: Generate default ramps at compile time. (72847)
  • Theme: Inline values for primitive tokens in CSS output. (72890)
  • Theme: Optimize color generating algorithm. (72883)
  • Theme: Use logarithms for contrast difference. (73097)

Block Library

  • Add Image Prefetching for Click to expand Images. (61107)
  • MathML block: Fix lazy script loading. (73099)

Block Editor

  • Reduce inspector subscriptions by not subscribing if panel is not enabled. (73013)

Collaboration

  • Notes: Return early when there are no notes. (72820)

Layout

  • Perf: Only mount SpacingVisualizers when actively visualizing. (72800)

Experiments

  • Boot Package: Add save panel and shortcut. (73170)
  • Editor: Add lazy-editor package and infrastructure. (73028)
  • Remove the posts page code from edit-site and replace it with the new route. (73165)
  • Route Registration: Add support for a routes folder to the build tool. (72950)
  • Routes build tooling: Fix watching, css and min buildling. (72952)
  • Routing Infra: Explore adding a posts route to the boot package. (72976)
  • Routing Infrastructure: Allow single routes to be added to WP-Admin separately. (73137)
  • Routing Single Page Mode: Fix fullscreen editor mode. (73169)
  • Routing: Add a post edit route to the boot demo page. (73065)
  • Routing: Add boot package. (72809)
  • Routing: Add post new and top level redirect route to the posts. (73102)
  • Routing: Allow plugins to register custom site editor like pages. (73120)
  • Template activation: Move to experiment. (73252)

Block Library

  • Disable TinyMCE: Bump needsClassicBlock further down. (72966)
  • Disable TinyMCE: Dequeue mce-view. (72972)
  • Disable TinyMCE: Handle old core/freeform syntax in editor. (72967)

Media

  • Add Upload button to experimental media modal and always allow multiple uploads. (73125)

Components

  • UIUI User interface: Implement Box component as part of new UI package. (72984)

Patterns

  • contentOnly patterns: Allow re-entry into contentOnly mode after โ€˜Edit contentsโ€™. (72044)

Documentation

  • Add PHPPHP The web scripting language in which WordPress is primarily architected. WordPress requires PHP 7.4 or higher function prefixing documentation. (72525)
  • Fix typo in README.md comment. (72879)
  • Tabs: Improve PHP documentation. (72834)
  • Theme: Fix ThemeProvider documentation for accurate color prop. (72943)
  • Update DataViews readme to add more info on the picker component. (72992)

Code Quality

Block Library

  • Breadcrumb: Some code quality improvements. (72873)
  • Remove old polyfills for server block definitions. (72827)

Collaboration

  • Notes: Remove unnecessary useCallback from keyboard navigation handler. (73152)

Block bindings

  • Untangle sources code. (72739)

Components

  • Handle label fallback for dropdownMenu. (70951)

Tools

  • PR enforcer workflow: Use regex to filter labels starting with [Type]. (72672)

Testing

  • Add end-to-end test for DataViews pagination. (73134)
  • Add initial CSS logical properties enforcement (CSS modules). (72758)
  • Automated testing: Add tests to ensure pagination data when fetching intermediate results. (71613)
  • Block Bindings: Add unit testunit test Code written to test a small piece of code or functionality within a larger application. Everything from themes to WordPress core have a series of unit tests. Also see regression. coverage for sources. (72799)
  • Enable no-unused-disable ESLint Comments plugin rule. (72940)
  • Improve the readability of the comment sharing manual cherry pick steps. (72887)
  • Increase memory limit for macOS CI runner. (72980)
  • Remove e2e-test-utils package and deprecated test configuration. (72880)
  • Scripts: Add default linting for ESM & CJS file extension variations. (72801)
  • Switch default ESLint resolver to improve handling for modern exports semantics. (72893)
  • Test across OS and Node.js version for commits to trunk. (72946)
  • Tests: Try fixing โ€œshould refresh the page when stylesheet loading failsโ€ end-to-end test. (72783)
  • end-to-end Tests: Fix some flaky tests. (73159)
  • eslint-plugin: Disable redundant import rules for TypeScript files. (72884)

Build Tooling

  • Upgrade TypeScript to 5.9. (72995)
  • Build v2: Fix build failure on Windows. (72960)
  • Build: Bundle CSS in package transpilation phase. (72805)
  • Build: Inline CSS modules stylesheet content. (72673)
  • Build: Remove typechecking from precommit hooksHooks In WordPress theme and development, hooks are functions that can be applied to an action or a Filter in WordPress. Actions are functions performed when a certain event occurs in WordPress. Filters allow you to modify certain functions. Arguments used to hook both filters and actions look the same.. (72955)
  • Pin full-length commit SHA for 3rd-party actions. (72855)
  • Theme: Fix build issues. (72919)
  • Theme: Update precomputed color ramps script for Node.js v20.10 compatibility. (72971)
  • Try regenerating package lock. (72991)
  • Update package-lock.json. (72996)
  • wp-build: Update package detection to ignore empty folders. (72941)

Components

  • Change types export to declaration file. (72979)

Post Editor

  • Editor: Change the name of the โ€˜Pluginsโ€™ menu group. (72826)

First-time contributors

The following PRs were merged by first-time contributors:

  • @okawayasuno: Math format: Force LTR direction in RTL languages. (72901)
  • @PaulREnglish: Fixย setupEditorย edits not being applied when non-iterable edits are used. (73167)
  • @pranvinit: Cover Block: Show settings inspector controls in the Site Editor. (69178)

Contributors

The following contributors merged PRs in this release:

@aaronrobertshawย @adamsilversteinย @aduthย @andreawetzelย @andrewserongย @annezazuย @arthur791004ย @DAreRodzย @desrosjย @dhruvang21ย @ellatrixย @getdaveย @gigituxย @hbhalodiaย @im3dabasiaย @jeryjย @joedolsonย @jorgefilipecostaย @joshualip-plauditย @jsnajdrย @juanfraย @karthick-muruganย @Mamadukaย @manzoorwanijkย @mcsfย @mikachanย @mtiasย @ntsekourasย @oandregalย @ockhamย @okawayasunoย @PaulREnglishย @pranvinitย @priethorย @ramonjdย @rcrdortizย @roseg43ย @sethrubensteinย @shimotmkย @sidharthpandita1ย @SirLouenย @Soeanย @stokesmanย @sunyatasattvaย @t-hamanoย @Takshil-Kunadiaย @talldanย @tellthemachinesย @tyxlaย @youknowriad

Props @cbravobernal peer review.

#block-editor,ย #core-editor,ย #gutenberg,ย #gutenberg-new

#gutenberg-new

Accessibility Improvements in WordPress 6.9

WordPress 6.9 brings extensive accessibilityAccessibility Accessibility (commonly shortened to a11y) refers to the design of products, devices, services, or environments for people with disabilities. The concept of accessible design ensures both โ€œdirect accessโ€ (i.e. unassisted) and โ€œindirect accessโ€ meaning compatibility with a personโ€™s assistive technology (for example, computer screen readers). (https://en.wikipedia.org/wiki/Accessibility) improvements across WordPress CoreCore Core is the set of software required to run WordPress. The Core Development Team builds WordPress. and GutenbergGutenberg The Gutenberg project is the new Editor Interface for WordPress. The editor improves the process and experience of creating new content, making writing rich content much simpler. It uses โ€˜blocksโ€™ to add richness rather than shortcodes, custom HTML etc. https://wordpress.org/gutenberg/, continuing the goals to meet web content accessibility standards throughout WordPress and make it easier to author accessible content. These updates include changes to administration, customization, login and registration, bundled themes, and the blockBlock Block is the abstract term used to describe units of markup that, composed together, form the content or layout of a webpage using the WordPress editor. The idea combines concepts of what in the past may have achieved with shortcodes, custom HTML, and embed discovery into a single consistent API and user experience. editor.

Core

Improvements to WordPress Core include 33 accessibility enhancements and bugbug A bug is an error or unexpected result. Performance improvements, code optimization, and are considered enhancements, not defects. After feature freeze, only bugs are dealt with, with regressions (adverse changes from the previous version) being the highest priority. fixes. Major changes include numerous new or improved screen reader notifications, a complete update of CSSCSS Cascading Style Sheets. generated content to ensure no excess content is spoken, and code changes to ensure proper semantics and improved focus management.

Administration

  • #47101 โ€“ Improve accessibility when deleting terms via AJAX: color contrast & spoken message.
  • #48655 โ€“ Improve the โ€œAdd-itemโ€ function in menus (esp. for pages)
  • #63118 โ€“ Hide โ€œSkip to Toolbarโ€ shortcut on small screens within adminadmin (and super admin)
  • #63126 โ€“ Theme preview model and Media library model having issues with Shift/Ctrl + Shift next and previous arrows.
  • #63449 โ€“ Low color contrast for <code> elements in description text on Settings > General page
  • #63546 โ€“ Fix unclosed li element in pluginPlugin A plugin is a piece of software containing a group of functions that can be added to a WordPress website. They can extend functionality or add new features to your WordPress websites. WordPress plugins are written in the PHP programming language and integrate seamlessly with WordPress. These can be free in the WordPress.org Plugin Directory https://wordpress.org/plugins/ or can be cost-based plugin from a third-party.-editor.php
  • #63603 โ€“ Replace deprecated / non-standard CSS for `speak` and `aural`
  • #63723 โ€“ On the Add New plugin page, put the Add Plugins screen description above the filterFilter Filters are one of the two types of Hooks https://codex.wordpress.org/Plugin_API/Hooks. They provide a way for functions to modify data of other functions. They are the counterpart to Actions. Unlike Actions, filters are meant to work in an isolated manner, and should never have side effects such as affecting global variables and output. menu

CustomizerCustomizer Tool built into WordPress core that hooks into most modern themes. You can use it to preview and modify many of your siteโ€™s appearance settings.

  • #42078 โ€“ Customize: fix the color hue picker HTMLHTML HyperText Markup Language. The semantic scripting language primarily used for outputting content in web browsers. and accessibility
  • #47579 โ€“ Customizer โ€œSelect logoโ€ and โ€œSelect site iconโ€ look like drop areas, but are buttons.
  • #50696 โ€“ UIUI User interface & Accessibility issues in customizer menus section
  • #63011 โ€“ Customizer: The back button is not keyboard focusable
  • #63832 โ€“ Loss of focus when setting or changing the Site Logo or Site Icon in Customizer

Editing

  • #63460 โ€“ Increase color contrast for embed template
  • #61959 โ€“ Enhance Support for `popovertarget` and `popover` Attributes in Native Browser Popover APIAPI An API or Application Programming Interface is a software intermediary that allows programs to interact with each other and share data in limited, clearly defined ways.

Login and Registration

  • #63281 โ€“ Password field has wrong focus on installations
  • #63286 โ€“ User profile first name, last name, nickname and email fields should have autocomplete attributes for accessibility
  • #48345 โ€“ Add Caps lock message to login screen

Media

  • #63114 โ€“ No screen reader announcements for upload image errors
  • #63238 โ€“ Remove `target=โ€_blankโ€` from Browser Uploader Link
  • #63239 โ€“ Button focus visibility issue in media upload page
  • #63571 โ€“ Excessive Spacing Between Right SidebarSidebar A sidebar in WordPress is referred to a widget-ready area used by WordPress themes to display information that is not a part of the main content. It is not always a vertical column on the side. It can be a horizontal rectangle below or above the content area, footer, header, or any where in the theme. Items in Edit Media Screen on Mobile View
  • #63973 โ€“ Add Media Button missing aria-haspopup and aria-controls

Miscellaneous

  • #40428 โ€“ Introduce best practices to hide CSS generated content from assistive technologies
  • #44267 โ€“ Privacy Request List Table: A way to show the time of request when itโ€™s older than 24 hours.
  • #63030 โ€“ Update CSS for `::-moz-placeholder` color
  • #63620 โ€“ Remove translator comments when hidden text matches visible text
  • #63950 โ€“ Tabbing through database upgrade screen shows โ€œWordPressโ€ text over logo

Bundled Themes

  • #10219 โ€“ โ€œOlder Entriesโ€ and โ€œNewer Entriesโ€ links are wrong when entries displayed in ascending order
  • #44656 โ€“ Multiple themes: Empty site title leaves empty anchor tagtag A directory in Subversion. WordPress uses tags to store a single snapshot of a version (3.6, 3.6.1, etc.), the common convention of tags in version control systems. (Not to be confused with post tags.) in headerHeader The header of your site is typically the first thing people will experience. The masthead or header art located across the top of your page is part of the look and feel of your website. It can influence a visitorโ€™s opinion about your content and you/ your organizationโ€™s brand. It may also look different on different screen sizes.
  • #52116 โ€“ Twenty Twenty: Menu + Search can cause a scroll jump on close
  • #63875 โ€“ Twenty Twenty-Two and Twenty Twenty-Five: <pre> tag overflows container, causing horizontal scroll

Widgets

  • #63531 โ€“ CategoryCategory The 'category' taxonomy lets you group posts / content together that share a common bond. Categories are pre-defined and broad ranging. dropdown does not meet WCAGWCAG WCAG is an acronym for Web Content Accessibility Guidelines. These guidelines are helping make sure the internet is accessible to all people no matter how they would need to access the internet (screen-reader, keyboard only, etc) https://www.w3.org/TR/WCAG21/. 2.2 A on windows and some linux systems

Gutenberg

Changes within Gutenberg include 44 accessibility fixes and enhancements, including the addition of new blocks and the block Notes feature that have undergone accessibility reviews. Numerous fundamental components have had accessibility improvements to ensure that interfaces across the editor are more consistent and understandable.ย 

Blocks

  • #68662 โ€“ Cover: Fix placeholder color options keyboard accessibility
  • #68909 โ€“ Site Title: Fix logic for โ€˜aria-currentโ€™ attribute
  • #69628 โ€“ Site Title: Prevent saving and rendering a value made of only spaces
  • #69689 โ€“ Navigation Link, Navigation Submenu: Remove the title attribute controls
  • #69821 โ€“ Social Icons: Remove custom placeholder state
  • #69837 โ€“ Navigation block: fix submenu Escape key behavior
  • #70139 โ€“ Button Block: Add HTML Element selection in Advanced settings
  • #70192 โ€“ Button: Avoid focus loss when unlinking using keyboard
  • #70210ย  โ€“ Columns block: Donโ€™t use ToolsPanelItem for Columns setting
  • #70730 โ€“ a11yAccessibility Accessibility (commonly shortened to a11y) refers to the design of products, devices, services, or environments for people with disabilities. The concept of accessible design ensures both โ€œdirect accessโ€ (i.e. unassisted) and โ€œindirect accessโ€ meaning compatibility with a personโ€™s assistive technology (for example, computer screen readers). (https://en.wikipedia.org/wiki/Accessibility): Comments Pagination Nav Wrapper
  • #64119 โ€“ Add Accordions Block
  • #73177 โ€“ Fix a11y of descriptions and alerts for โ€œInvalidinvalid A resolution on the bug tracker (and generally common in software development, sometimes also notabug) that indicates the ticket is not a bug, is a support request, or is generally invalid.โ€ Nav Items

Components

  • #67792 โ€“ Improve the EntitiesSavedStates modal dialog design and labeling
  • #69011 โ€“ Remove non translatable additional info from font size picker visual label and improve labeling
  • #69441 โ€“ ARIA: Fix invalid `DropdownMenu` children structure
  • #68633 โ€“ Global Styles: Prevent Unwanted ItemGroup List Rendering in Border Panel
  • #68542 โ€“ Button: Update hover styles to account for pressed state for `tertiary button`
  • #69609 โ€“ ActionModal: Add support for customisable `focusOnMount`
  • #69904 โ€“ Add new HTMLElementControl component
  • #70591 โ€“ `FormTokenField`: Fix focus lost on tab when `__experimentalExpandOnFocus` is set
  • #70096 โ€“ Components: Fix label and placeholder handling in `LinkControlSearchInput`
  • #70660 โ€“ Autocomplete: Prevent text cursor position loss when clicking to insert an item
  • #70146 โ€“ Color Picker: Improve color picker slider focus styles

Data Views

  • #67874 โ€“ Display Checkbox by default in dataviews
  • #69876 โ€“ DataViews: Always show primary action for list layout if hover isnโ€™t supported
  • #71561 โ€“ DataViews: Custom `empty` elements are no longer wrapped in `<p>` tags to improve accessibility
  • #72417 โ€“ DataViews: Use Text-Based Links for Primary Actions
  • #72501 โ€“ Dataviews: Make bulk actions text based.

Editor

  • #68481 โ€“ Fix CSS classes for the post editor iframeiframe iFrame is an acronym for an inline frame. An iFrame is used inside a webpage to load another HTML document and render it. This HTML document may also contain JavaScript and/or CSS which is loaded at the time when iframe tag is parsed by the userโ€™s browser. body.
  • #68975 โ€“ Close patterns modal on insertion and focus on inserted pattern
  • #69305 โ€“ Swap fullscreen mode snackbar notice message.
  • #69334 โ€“ InputControl: Ensure consistent placeholder color
  • #69378 โ€“ Button: Remove fixed width from small and compact buttons with icons
  • #69451 โ€“ Editor: Refactor the โ€˜PostVisibilityโ€™ component
  • #69520 โ€“ Fix shift+tab from post title
  • #69724 โ€“ Post Template Panel: Preserve parent modal when closing template creation dialog
  • #68631 โ€“ Global Styles: Fix incorrect usage of ItemGroup in the Background image panel
  • #69813 โ€“ Background Image Panel: fix focus loss
  • #70128 โ€“ Global Styles: Move `Randomize colors` button to Edit Palette panel
  • #70133 โ€“ Editor: Add label in`TextareaControl` in CollabSidebar
  • #69278 โ€“ Toolbar: Adjust colors for dark mode support
  • #70451ย  โ€“ feat: clarify label & add help text with link for Link Rel

Miscellaneous

  • #69440 โ€“ Make password protected input fields consistent.
  • #70091 โ€“ Templates: Add back button & fix focus loss when navigating through template creation flow

Acknowledgements

Props to @jorbin and @jeffpaul for reviewing this post.

#6-9, #accessibility, #dev-notes, #dev-notes-6-9

Admin menu search query changed

When creating and editing menus in the Menus interface, searching for posts and pages has historically used a full text search as a query. This can make some pages difficult to find, if they use a title that primarily uses common words in the site content.

In WordPress 6.9, the search query arguments have been changed to limit searches to only the post title. This is intended to make it easier to find the post youโ€™re looking for in search results.

The query change adds the argument search_columns with the value array( โ€˜post_titleโ€™ ) to the search. The columns correspond to the database columns in the wp_posts table.

To facilitate sites that may need the previous search logic, a filterFilter Filters are one of the two types of Hooks https://codex.wordpress.org/Plugin_API/Hooks. They provide a way for functions to modify data of other functions. They are the counterpart to Actions. Unlike Actions, filters are meant to work in an isolated manner, and should never have side effects such as affecting global variables and output. has been added to easily modify the search query.

/**
 * Filter the menu quick search arguments.
 *
 * @since 6.9.0
 *
 * @param array $args {
 * ย  ย  Menu quick search arguments.
 *
 * ย  ย  @type booleanย  ย  ย  $no_found_rowsย  ย  ย  ย  ย  Whether to return found rows data. Default true.
 * ย  ย  @type booleanย  ย  ย  $update_post_meta_cache Whether to update post meta cache. Default false.
 * ย  ย  @type booleanย  ย  ย  $update_post_term_cache Whether to update post term cache. Default false.
 * ย  ย  @type intย  ย  ย  ย  ย  $posts_per_page ย  ย  ย  ย  Number of posts to return. Default 10.
 * ย  ย  @type string ย  ย  ย  $post_typeย  ย  ย  ย  ย  ย  ย  Type of post to return.
 * ย  ย  @type string ย  ย  ย  $sย  ย  ย  ย  ย  ย  ย  ย  ย  ย  ย  Search query.
 * ย  ย  @type arrayย  ย  ย  ย  $search_columns ย  ย  ย  ย  Which post table columns to query.
 * }
 */
 $query_args = apply_filters( 'wp_ajax_menu_quick_search_args', $query_args );

To restore the previous behavior, you can unset the additional argument:

/**
 * Restore pre-6.9 menu search arguments.
 *
 * @param array $args Array of arguments as documented.
 *
 * @return array
 */
function restore_menu_quick_search_args( $args ) {
ย  ย  unset( $args['search_columns'] );
ย ย ย ย return $args;
}
add_filter( 'wp_ajax_menu_quick_search_args', 'restore_menu_quick_search_args' );

Related ticketticket Created for both bug reports and feature development on the bug tracker.: Improve the โ€œAdd itemโ€ function in menus.

Acknowledgements

Props to @jorbin for reviewing this post.

#6-9, #dev-notes, #dev-notes-6-9

Legacy Internet Explorer Code Removed

With WordPress 6.9, numerous legacy features that were used to support Internet Explorer have been removed. All versions of Internet Explorer have been unsupported in WordPress since version 5.8, released in July 2021. These changes continue the process of removing code that existed only to provide support for these browsers.

Removed Support for IE Conditional Scripts and Styles

Conditional comment support was added for scripts in WordPress 4.2, and for styles sometime around version 2.6.0, but was made more easily available in WordPress 3.6.

Conditional comments were a mechanism to pass scripts and styles for specific versions of IE. The last browser to support conditional comments in any way was IE9, which has been out of support by WordPress since version 4.8. No supported browser uses scripts or styles provided within conditional comments, treating them the same as any other commented code.

The feature has been removed, and using the โ€˜conditionalโ€™ argument will throw a deprecation notice (โ€œIE conditional comments are ignored by all supported browsers.โ€) if WP_DEBUG is set to true.ย 

Any style or script currently loaded using conditional arguments will be ignored, as will any dependencies of those styles or scripts if they are not already required by another script or style.

IE Conditional scripts and styles were removed in core ticket #63821.

Updates to bundled themes

All bundled themes that used conditional comments have been updated to remove usages of conditional comments and CSSCSS Cascading Style Sheets. syntax only used to support Internet Explorer.

CSS and JSJS JavaScript, a web scripting language typically executed in the browser. Often used for advanced user interfaces and behaviors. files that were only required conditionally remain in place as blank files, containing only comments to indicate when the related support was removed.ย 

Conditional comments were removed from bundled themes in #58836.ย 

IE Compatibility Removals

Compatibility scripts were removed from the Media Elements instantiation process in #63471.

#62128 removed IE-specific hacks and EOT file rules from the Genericons stylesheet for four bundled themes, from Twenty Thirteen to Twenty Sixteen.

Acknowledgements

Props to @jorbin, @westonruter, @jonsurrell and @sabernhardt for reviewing this post.

#6-9, #dev-notes, #dev-notes-6-9

URL-escaping functions can support HTTPS as the default protocol in WordPress 6.9

When a string passed to the esc_url() and esc_url_raw() functions does not include a protocol (https://, http://, etc.), WordPress will prepend http:// to the URLURL A specific web address of a website or web page on the Internet, such as a websiteโ€™s URL www.wordpress.org string before further processing and returning it. This is a reasonable fallback behavior, but there is currently no way to override the default protocol with another (such as https:// for social media profiles).

Starting in WordPress 6.9, the esc_url() and esc_url_raw() functions will now prepend https:// to the URL if it does not already contain a scheme and the first item in the $protocols array is 'https'. The current behavior (prepending http://) will continue when any other value is listed first within the $protocols array.

<?php
/*
 * Recommended approach for defaulting to 'https' while maintaining
 * backward compatibility.
 * 
 * Example: no protocol with $protocols and 'https' first.
 *
 * Output:
 * - WordPress >= 6.9: 'https://profiles.wordpress.org'
 * - WordPress  < 6.9: 'http://profiles.wordpress.org'
 */
echo esc_url( 'profiles.wordpress.org', array( 'https', 'http' ) );

By including 'https' first and then 'http' in the array:

  • WordPress 6.9 would prepend https:// to an incomplete URL.
  • Older WordPress versions would continue to prepend http://, which remains the default scheme when the $protocols argument is not defined. If the array only contains 'https', esc_url() would return an empty string because http is not included in the list of valid protocols.

Additional examples of output include:

<?php
/*
 * Example 1: no protocol included in $url.
 * 
 * Output:
 * - WordPress >= 6.9: 'http://profiles.wordpress.org'
 * - WordPress  < 6.9: 'http://profiles.wordpress.org'
 */
echo esc_url( 'profiles.wordpress.org' );

/*
 * Example 2: 'http' protocol included in $url.
 *
 * Output:
 * - WordPress >= 6.9: 'http://profiles.wordpress.org'
 * - WordPress  < 6.9: 'http://profiles.wordpress.org'
 */
echo esc_url( 'http://profiles.wordpress.org' );

/*
 * Example 3: 'https' protocol included in $url.
 *
 * Output:
 * - WordPress >= 6.9: 'https://profiles.wordpress.org'
 * - WordPress  < 6.9: 'https://profiles.wordpress.org'
 */
echo esc_url( 'https://profiles.wordpress.org' );

/*
 * Example 4: no protocol with $protocols and 'http' first.
 *
 * Output:
 * - WordPress >= 6.9: 'http://profiles.wordpress.org'
 * - WordPress  < 6.9: 'http://profiles.wordpress.org'
 */
echo esc_url( 'profiles.wordpress.org', array( 'http', 'https' ) );
       
/*
 * Example 5: no protocol in $url with $protocols and no 'http'.
 *
 * Output:
 * - WordPress >= 6.9: 'https://profiles.wordpress.org'
 * - WordPress  < 6.9: ''
 *
 * Note: if 'http' is not included in the $protocols array,
 * the fully escaped URL will not pass the final check that
 * a valid, allowed protocol is included.
 */
echo esc_url( 'profiles.wordpress.org', array( 'https' ) );
             
/*
 * Example 6: protocol within $url missing within $protocols.
 *
 * Output for all:
 * - WordPress >= 6.9: ''
 * - WordPress  < 6.9: ''
 *
 * Note: if 'http' is not included in the $protocols array,
 * the fully escaped URL will not pass the final check that
 * a valid, allowed protocol is included.
 */
echo esc_url( 'https://profiles.wordpress.org', array( 'http' ) );
echo esc_url( 'http://profiles.wordpress.org', array( 'https' ) );
echo esc_url( 'mailto:indana@jon.es', array( 'https', 'http' ) );

For more information, refer to #52886.


Props to @desrosj for co-authoring the note, writing the code examples and expanding on details. Props to @jorbin for review.

#6-9, #dev-notes, #dev-notes-6-9

Consistent Cache Keys for Query Groups in WordPress 6.9

Query caches have historically used the last changed timestamp as a salt. While this has proven effective for most sites, it leads to an excessive number of caches which can be problematic on high-traffic and heavily updated sites. WordPress 6.9 introduces changes to how cache keys are created in order to ensure efficient use of object caches and help caches clean up after themselves.

These changes are compatible with existing implementations of persistent caching drop-ins. Vendors are not required to make any changes to their code to support these features in WordPress 6.9. As with other caching functions, the functions are pluggable should vendors wish to optimize for their particular caching implementation. These new functions are:

  • wp_cache_get_salted( string $cache_key, string $group, string|string[] $salt ): mixed
  • wp_cache_set_salted( string $cache_key, mixed $data, string $group, string|string[] $salt, int $expire = 0 ): bool
  • wp_cache_get_multiple_salted( string[] $cache_keys, string $group, string|string[] $salt ): mixed[]
  • wp_cache_set_multiple_salted( mixed[] $data, string $group, string|string[] $salt, int $expire = 0 ): bool[]

What Behavior is Changing

Previous behavior in WordPress 6.8 and earlier:

  • A post object is saved
  • WordPress stores the last changed time of the posts table
  • WP Query is called
  • WordPress caches the database query using a key containing the last changed time
  • Another post is saved, updating the posts tableโ€™s last changed time
  • The previous cache becomes unreachable
  • WP Query is called
  • WordPress does not see a cached query
  • WordPress caches the database query using a new key containing the updated last changed time

New behavior in WordPress 6.9

  • A post object is saved
  • WordPress stores the last changed time of the posts table
  • WP Query is called
  • WordPress caches the database query alongside the last changed time
  • Another post is saved, updating the posts tableโ€™s last changed time
  • WP Query is called
  • WordPress hits the previously generated cache
  • WordPress uses the last changed value to determine if the cache is up-to-date
  • WordPress replaces the previously generated cache with the new results

While both operations perform two cache lookups, the new behavior re-uses the existing cache key and does an in memory comparison of the last changed time. This prevents the cache from containing unreachable cache keys.

The same change in behavior applies to other Query classes such as term queries, comment queries, user queries, etc.

Checking/setting query caches directly

Broadly, the caches affected are in the following cache groups:

  • comment-queries
  • network-queries
  • post-queries
  • site-queries
  • term-queries
  • user-queries
The following specific cache keys are affected and will now be different.ย  If you have been directly checking or setting caches that start with the following keys, you will need to adjust your code.
  • get_comments
  • get_comment_child_ids
  • get_network_ids
  • comment_feed
  • wp_query
  • get_sites
  • wp_get_archives
  • adjacent_post
  • get_page_by_path
  • find_post_by_old_slug
  • get_objects_in_term
  • count_user_postscount_user_posts

Additionally, keys that are generated by WP_User_Query:generate_cache_key and WP_Term_Query::generate_cache_key are affected as well. However, these keys are md5 hashes and thus are less likely to be used directly.

When using the new wp_cache_*_salted functions and passing in an array of salts, the order of items in the array must be consistent. If you are using the changed caches in coreCore Core is the set of software required to run WordPress. The Core Development Team builds WordPress., please review the order in core and use the same order to ensure cache hits.ย 

If you need to support multiple versions of WordPress when updating your code, you can use code that looks similar to:

if (function_exists( 'wp_cache_get_salted` ) ){
ย ย $data = wp_cache_get_salted( $cache_key, 'comment-queries', $last_changed );
} else {
ย ย // your current code here
}

See [60697] for specific examples of how core has been updated and [60941] for an example of how these new functions help cache previously uncached code.ย 

On Upgrade to WordPress 6.9

With the update to cache keys, itโ€™s expected that you may see a short term increase in cache misses upon upgrade. You may wish to preemptively evict the old cache keys in order to prevent stale entries from sticking around, potentially leading to unnecessary evictions based on your cache policies.

For more information, please see #59592.

Props to @desrosj,ย  @peterwilsoncc, and @spacedmonkey for review. Props to @spacedmonkey for comments on the ticketticket Created for both bug reports and feature development on the bug tracker. that could be easily reused here.

#6-9, #cache-api, #dev-notes, #dev-notes-6-9

Miscellaneous Developer-focused Changes in 6.9

In WordPress 6.9, a handful of small, developer-focused changes were made that deserve to be called out. Letโ€™s take a look!

PHPPHP The web scripting language in which WordPress is primarily architected. WordPress requires PHP 7.4 or higher 8.5 New Function Polyfills

The upcoming 8.5 release of PHP includes 2 new functions that can be used to retrieve values from an array:

To encourage more modern PHP practices, polyfills of these functions have been added to WordPress CoreCore Core is the set of software required to run WordPress. The Core Development Team builds WordPress. so that they can be used safely without needing to include function_exists() checks.

For more information, see #63853.

Improved Feed Caching on Multisitemultisite Used to describe a WordPress installation with a network of multiple blogs, grouped by sites. This installation type has shared users tables, and creates separate database tables for each blog (wp_posts becomes wp_0_posts). See also network, blog, site Installs

When RSS feeds are fetched using fetch_feed(), they are currently cached using the (get|set|delete)_transient() functions. On multisite installs, single site transients cannot be shared between sites, but site transients managed through (get|set|delete)_site_transient() can.

In WordPress 6.9, fetch_feed() will now store feeds as site transients instead. This allows a feed to be fetched and stored once for all sites on a multisite install, which improves the overall performance of feeds and reduces the amount of data cached in the database (or persistent object cache, if configured). One example where this is beneficial is the WordPress News blogblog (versus network, site) feed, which is fetched and displayed in a widgetWidget A WordPress Widget is a small block that performs a specific function. You can add these widgets in sidebars also known as widget-ready areas on your web page. WordPress widgets were originally created to provide a simple and easy-to-use way of giving design and structure control of the WordPress theme to the user. on the dashboard for every user.

See #63719 for more details.

External Library Updates

The following external libraries bundled in WordPress are being updated in the 6.9 release:

  • ID3 has been updated to include two changes from the upstream repository that address PHP 8.5 compatibility issues (see #64051). Once a new version containing these two changes has officially been tagged, the library will be updated in full (see #64253).
  • PHPMailer has been updated from 6.9.1 to 6.11.1 (see #63811, #64052, #64055).
  • SimplePie has been updated from 1.8.0 to 1.9.0 (see #63717, #63961).
  • Sodium Compat has been updated from 1.21.1 to 1.23.0 (see #64008, #64079).

New Classic Themes Template for TaxonomyTaxonomy A taxonomy is a way to group things together. In WordPress, some common taxonomies are category, link, tag, or post format. https://codex.wordpress.org/Taxonomies#Default_Taxonomies. Terms

In classic themes, you can now use term IDs when creating taxonomy templates. With taxonomy-$taxonomy-{$term->term_id}.php templates, you donโ€™t need to worry about templates breaking if you rename the Oakland Athletics term to Athletics the way you do if you use slug based template names.ย 

See #35326 for more information.

Better Handling of Transparent PNGs

WordPress 6.8 introduced a regressionregression A software bug that breaks or degrades something that previously worked. Regressions are often treated as critical bugs or blockers. Recent regressions may be given higher priorities. A "3.6 regression" would be a bug in 3.6 that worked as intended in 3.5. that could degrade the quality of PNG images with transparency when processed with Imagick. This was fixed in [60667] by improving the detection of the various types of transparent PNG files and handles them each appropriately.

See #63448 for more information.

New HooksHooks In WordPress theme and development, hooks are functions that can be applied to an action or a Filter in WordPress. Actions are functions performed when a certain event occurs in WordPress. Filters allow you to modify certain functions. Arguments used to hook both filters and actions look the same.

WordPress 6.9 will see 21 new action and filterFilter Filters are one of the two types of Hooks https://codex.wordpress.org/Plugin_API/Hooks. They provide a way for functions to modify data of other functions. They are the counterpart to Actions. Unlike Actions, filters are meant to work in an isolated manner, and should never have side effects such as affecting global variables and output. hooks added. Some will be detailed in a separate developer note, but theyโ€™re all listed below for easy reference.

New Action Hooks

There are 8 new action hooks being introduced in 6.9:ย 

New Filter Hooks

There are 13 new filters being introduced in 6.9:

A Final Farewell to Flash

While Flash was officially retired at the end of 2020, there were a few artifacts remaining within WordPress in the form of SWFObject and SWFUpload. These were removed in [60281] and will no longer ship in new versions of WordPress going forward.

For more information, see #52699 on TracTrac An open source project by Edgewall Software that serves as a bug tracker and project management tool for WordPress..

Props @adamsilverstein for helping to draft the post, and @jorbin for peer-review.

#6-9, #dev-notes, #dev-notes-6-9

Notes feature in WordPress 6.9

WordPress 6.9 introduces Notes, a new feature that allows you to leave contextual feedback at the blockBlock Block is the abstract term used to describe units of markup that, composed together, form the content or layout of a webpage using the WordPress editor. The idea combines concepts of what in the past may have achieved with shortcodes, custom HTML, and embed discovery into a single consistent API and user experience. level. With notes your team can stay aligned, track changes, and turn feedback into action all in one place. Notes can be resolved, and notes and their replies can be edited or deleted.

Who can use notes?

Because notes can only be created or viewed within the post editor, users must have the edit_post capabilitycapability Aย capabilityย is permission to perform one or more types of task. Checking if a user has a capability is performed by the current_user_can function. Each user of a WordPress site might have some permissions but not others, depending on theirย role. For example, users who have the Author role usually have permission to edit their own posts (the โ€œedit_postsโ€ capability), but not permission to edit other usersโ€™ posts (the โ€œedit_others_postsโ€ capability). for that post. By default, this means that:

  • Administrators and Editors can view all notes on all posts.
  • Authors and Contributors can view all notes for posts that they have authored.
  • Subscribers cannot view any notes.

Enabling notes for custom post types

Notes are enabled by default for the post and page built-in post types, but they can be enabled for any custom post typeCustom Post Type WordPress can hold and display many different types of content. A single item of such a content is generally called a post, although post is also a specific post type. Custom Post Types gives your site the ability to have templated posts, to simplify the concept.. When you control the register_post_type() call, this is the preferred way to register support for Notes:

register_post_type( 'book', array(
	'label' => 'Books',
	'public' => true,
	'show_in_rest' => true,
	'supports' => array(
		'title',
		'editor' => array( 'notes' => true ),
		'author',
	),
) );

When the custom post type is registered through a pluginPlugin A plugin is a piece of software containing a group of functions that can be added to a WordPress website. They can extend functionality or add new features to your WordPress websites. WordPress plugins are written in the PHP programming language and integrate seamlessly with WordPress. These can be free in the WordPress.org Plugin Directory https://wordpress.org/plugins/ or can be cost-based plugin from a third-party., support for Notes can be added by registering support using the following code snippet:

function custom_add_post_type_support() {
	$supports        = get_all_post_type_supports( 'my-post-type' );
	$editor_supports = array( 'notes' => true );

	// `add_post_type_support()` overwrites feature sub-properties, 
	// so they must be explicitly merged. 
	// See https://core.trac.wordpress.org/ticket/64156.
	if ( 
		is_array( $supports['editor'] ) && 
		isset( $supports['editor'][0] ) && 
		is_array( $supports['editor'][0] ) 
	) {
		$editor_supports = array_merge( $editor_supports, $supports['editor'][0] );
	}
	add_post_type_support( 'my-post-type', 'editor', $editor_supports );
}
add_action( 'init', 'custom_add_post_type_support' );

Since notes is a sub-feature of the editor, the code needs to manually merge the notes setting with other editor attributes. Work is underway in https://core.trac.wordpress.org/ticket/64156 to make this easier. Once this bugbug A bug is an error or unexpected result. Performance improvements, code optimization, and are considered enhancements, not defects. After feature freeze, only bugs are dealt with, with regressions (adverse changes from the previous version) being the highest priority. is fixed, adding support will be simplified:

add_post_type_support( 'my-post-type', 'editor', array(
ย ย ย ย 'notes' => true,
) );

Accessing notes programmatically

Under the hood, Notes are WP_Comments stored in the comments table, and the standard comments APIs can be used to access them by specifying a comment_type ofย  note.ย 

For example, this will retrieve all notes for a given post ID:

$notes = get_comments( 
	array(
		'post_id' => $post_id,
		'type'    => 'note',
	)
);

Notes can also be retrieved using the REST APIREST API The REST API is an acronym for the RESTful Application Program Interface (API) that uses HTTP requests to GET, PUT, POST and DELETE data. It is how the front end of an application (think โ€œphone appโ€ or โ€œwebsiteโ€) can communicate with the data store (think โ€œdatabaseโ€ or โ€œfile systemโ€) https://developer.wordpress.org/rest-api/:

$request = new WP_REST_Request( 'GET', '/wp/v2/comments' );
$request->set_param( 'post', $post_id );
$request->set_param( 'type', 'note' );
$response = rest_get_server()->dispatch( $request );
if ( ! is_wp_error( $response ) ) {
	$notes = $response->get_data();
	foreach ( $notes as $note ) {
		// Process each note as needed
	}
}

Note status

When a note is added to a block, it:

  • Starts in an โ€œOpenโ€ state with a comment_status of 0 (aka hold).ย 
  • When resolved, changes to a comment_status of 1 (aka approve).
  • When deleted, changes to a status of trash, unless EMPTY_TRASH_DAYS is 0 in which case deleted immediately.

The following snippet will get a list of all unresolved Notes for a given post:

$notes = get_comments( 
	array(
		'post_id' => $post_id,
		'type'    => 'note',
		'status'  => 'hold'
	)
);

Important: Notes must be explicitly requested by specifying either the note or all comment type. Otherwise they are excluded when retrieving comments:

// This only returns comments, 'notes' are automatically excluded.
$comments = get_comments( array ( 'post_id' => $post_id ) );

Notification emails

When another user adds a note to a post, the post_author will receive a notification that a note has been added to the post. Notifications are enabled by default and can be controlled at a site level under Settings->Discussions โ€“ Email me whenever > Anyone posts a note. Developers can also use the existing comment filters to control notifications.ย 

For example, to send notifications for notes on pages but not posts, use this snippet:

function only_notify_page_authors_of_notes( $notify, $comment_id ) {
	if ( 'note' !== get_comment_type( $comment_id ) {
		return $notify;
	}

	if ( 'page' === get_post_type( $comment_post_ID ) {
		return true;
	}

	return false;
}
add_filter( 'notify_post_author', 'only_notify_page_authors_of_notes', 10, 2 );

Miscellaneous

Notes permissions

As previously mentioned, only users who can edit a given post are able to add notes. Because notes are an internal/authorized user feature, the normal restrictions that apply to comment posting do not apply to notes, including the flood protection and duplicate prevention. In addition, the pre_comment_approved filterFilter Filters are one of the two types of Hooks https://codex.wordpress.org/Plugin_API/Hooks. They provide a way for functions to modify data of other functions. They are the counterpart to Actions. Unlike Actions, filters are meant to work in an isolated manner, and should never have side effects such as affecting global variables and output. is not run for notes.

Linking blocks to notes

Top level notes are linked to blocks with a metadata attribute. . When you add a new note to a block, the note ID is stored in block attributes metadata as noteId. Replies are linked to top level notes as children (with their parent set to the top level note)

To get the note ID from a block based on its clientId, you can use this code:

const attributes = getBlockAttributes( clientId );
const noteId     = attributes.metadata?.noteId;

Important: The reverse is not true โ€“ notes do not contain a link back to their associated block. To identify the block(s) associated with a note, search the blocks for the noteId in metadata. You can use this code snippet:

import { store as blockEditorStore } from '@wordpress/block-editor';

const { getBlockAttributes } = useSelect( blockEditorStore );

const { clientIds } = useSelect( ( select ) => {
	const { getClientIdsWithDescendants } = select( blockEditorStore );
	return {
		clientIds: getClientIdsWithDescendants(),
	};
}, [] );

// expectedNoteId is the note we are filtering for.
const blocksWithNote = clientIds.reduce( ( results, clientId ) => {
	const commentId = getBlockAttributes( clientId )?.metadata?.noteId;
	if ( commentId === expectedNoteId ) {
		results[ clientId ] = commentId;
	}
	return results;
}, {} );

Known limitations

  • A note can be associated with more than one block. If a block with a note is split or duplicated, the note becomes associated with both blocks. This is primarily due to an underlying limitation in GutenbergGutenberg The Gutenberg project is the new Editor Interface for WordPress. The editor improves the process and experience of creating new content, making writing rich content much simpler. It uses โ€˜blocksโ€™ to add richness rather than shortcodes, custom HTML etc. https://wordpress.org/gutenberg/ that will be fixed in #29693.
  • A notification is sent for each new non-author note which may not be ideal for all users, especially for cases where a high volume of notes are added to a post will in turn generate a high volume of emails to the post author.
  • Notes do not work outside post content types, for example in templates.
  • All notes are block level, for example this means that they can not reference specific text within a paragraph or text across paragraph blocks.ย  In-line notes will become available as part of #59445.

Whatโ€™s next

There are already new features and enhancements planned for Notes in the next release of WordPress (7.0). These features were suggested during the development cycle, but didnโ€™t make it into the 6.9 release.

  • Fragment notes โ€“ the ability to leave a note on a part of a block or across blocks.
  • โ€œ@โ€ mentions โ€“ mention another user in a post and they will receive a notification.
  • Improved notifications โ€“ control frequency for notifications, for example receive a daily digest of all new note activity.
  • Improved floating layout for wide screens โ€“ shift the floating to sit between the editor frame and the sidebarSidebar A sidebar in WordPress is referred to a widget-ready area used by WordPress themes to display information that is not a part of the main content. It is not always a vertical column on the side. It can be a horizontal rectangle below or above the content area, footer, header, or any where in the theme..
  • Minified mode โ€“ notes display as icons with avatars beside blocks that expand when clicked..
  • Wider availability across the editor including using notes with templates.
  • Real time collaboration with Notes.

You can follow along and contribute to the ongoing effort on the Notes iteration for 7.0 tracking issue.

Have an idea for how to improve Notes? Leave your feedback as a comment below or on the tracking issue linked above.

Props to @jeffpaul, @mamaduka, @wildworks, @annezazu, and @desrosj for review.

#6-9, #core, #dev-notes, #dev-notes-6-9, #notes