From 88130b95e8bbd9dac44c03962ce0ac8a4b17a9d9 Mon Sep 17 00:00:00 2001 From: Aaron Jorbin <622599+aaronjorbin@users.noreply.github.com> Date: Tue, 2 Dec 2025 15:13:52 -0600 Subject: [PATCH 001/126] bump workflows for 6.9 --- .github/phpunit-matrix.js | 0 .github/workflows/test-old-branches.yml | 2 +- .github/workflows/upgrade-develop-testing.yml | 4 ++-- .github/workflows/upgrade-testing.yml | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) create mode 100644 .github/phpunit-matrix.js diff --git a/.github/phpunit-matrix.js b/.github/phpunit-matrix.js new file mode 100644 index 0000000000000..e69de29bb2d1d diff --git a/.github/workflows/test-old-branches.yml b/.github/workflows/test-old-branches.yml index 952f10370e277..892cc3847d9e9 100644 --- a/.github/workflows/test-old-branches.yml +++ b/.github/workflows/test-old-branches.yml @@ -25,7 +25,7 @@ on: permissions: {} env: - CURRENTLY_SUPPORTED_BRANCH: '6.8' + CURRENTLY_SUPPORTED_BRANCH: '6.9' jobs: dispatch-workflows-for-old-branches: diff --git a/.github/workflows/upgrade-develop-testing.yml b/.github/workflows/upgrade-develop-testing.yml index 8d00334c38903..fddea0d149c45 100644 --- a/.github/workflows/upgrade-develop-testing.yml +++ b/.github/workflows/upgrade-develop-testing.yml @@ -67,7 +67,7 @@ jobs: db-type: [ 'mysql' ] db-version: [ '5.7', '8.4' ] # WordPress 4.9 is the oldest version that supports PHP 7.2. - wp: [ '4.9', '6.7', '6.8', '6.9-RC1' ] + wp: [ '4.9', '6.7', '6.8', '6.9' ] multisite: [ false, true ] exclude: @@ -102,7 +102,7 @@ jobs: db-type: [ 'mysql' ] db-version: [ '8.4' ] # WordPress 4.9 is the oldest version that supports PHP 7.2. - wp: [ '6.7', '6.8' ] + wp: [ '6.8', '6.9' ] multisite: [ false, true ] exclude: diff --git a/.github/workflows/upgrade-testing.yml b/.github/workflows/upgrade-testing.yml index f6ba23c87a328..d6fab95181c18 100644 --- a/.github/workflows/upgrade-testing.yml +++ b/.github/workflows/upgrade-testing.yml @@ -71,7 +71,7 @@ jobs: php: [ '7.2', '7.3', '7.4', '8.0', '8.1', '8.2', '8.3', '8.4', '8.5' ] db-type: [ 'mysql' ] db-version: [ '5.7', '8.0', '8.4', '9.5' ] - wp: [ '6.7', '6.8' ] + wp: [ '6.8', '6.9' ] multisite: [ false, true ] exclude: From 154bd43031e6d7d257081d29c74ade67b69e4c2b Mon Sep 17 00:00:00 2001 From: Jon Surrell Date: Wed, 3 Dec 2025 17:25:34 +0000 Subject: [PATCH 002/126] HTML API: Ensure correct encoding of modified class names. Some class names with HTML character references could be mishandled, for example: - Failure to remove an existing class like `&` with `::remove_class( '&' )` - Double-encoding of an existing class like `&` after a modification, becoming `&` The second case manifested after double-encoding prevention was removed from `::set_attribute()` in [60919]. Developed in https://github.com/WordPress/wordpress-develop/pull/10591. Props jonsurrell, dmsnell. Fixes #64340. git-svn-id: https://develop.svn.wordpress.org/trunk@61346 602fd350-edb4-49c9-b593-d223f7449a82 --- .../html-api/class-wp-html-tag-processor.php | 10 ++-- .../tests/html-api/wpHtmlTagProcessor.php | 48 ++++++++++++++++++- 2 files changed, 52 insertions(+), 6 deletions(-) diff --git a/src/wp-includes/html-api/class-wp-html-tag-processor.php b/src/wp-includes/html-api/class-wp-html-tag-processor.php index 3cdbd91480ca0..31c4bc8a10654 100644 --- a/src/wp-includes/html-api/class-wp-html-tag-processor.php +++ b/src/wp-includes/html-api/class-wp-html-tag-processor.php @@ -2342,10 +2342,12 @@ private function class_name_updates_to_attributes_updates(): void { } if ( false === $existing_class && isset( $this->attributes['class'] ) ) { - $existing_class = substr( - $this->html, - $this->attributes['class']->value_starts_at, - $this->attributes['class']->value_length + $existing_class = WP_HTML_Decoder::decode_attribute( + substr( + $this->html, + $this->attributes['class']->value_starts_at, + $this->attributes['class']->value_length + ) ); } diff --git a/tests/phpunit/tests/html-api/wpHtmlTagProcessor.php b/tests/phpunit/tests/html-api/wpHtmlTagProcessor.php index b6ec3affb2788..22ace3890f469 100644 --- a/tests/phpunit/tests/html-api/wpHtmlTagProcessor.php +++ b/tests/phpunit/tests/html-api/wpHtmlTagProcessor.php @@ -2887,11 +2887,11 @@ public static function data_updating_attributes_in_malformed_html() { ), 'HTML tag opening inside attribute value' => array( 'input' => '
This <is> a <strong is="true">thing.
test', - 'expected' => '
This <is> a <strong is="true">thing.
test', + 'expected' => '
This <is> a <strong is="true">thing.
test', ), 'HTML tag brackets in attribute values and data markup' => array( 'input' => '
This <is> a <strong is="true">thing.
test', - 'expected' => '
This <is> a <strong is="true">thing.
test', + 'expected' => '
This <is> a <strong is="true">thing.
test', ), 'Single and double quotes in attribute value' => array( 'input' => '

test', @@ -3028,6 +3028,50 @@ public static function data_updating_attributes_in_malformed_html() { ); } + /** + * @ticket 64340 + */ + public function test_class_changes_produce_correct_html() { + $processor = new WP_HTML_Tag_Processor( '

' ); + $processor->next_tag(); + + $processor->add_class( '"' ); + $processor->get_updated_html(); + + $processor->add_class( 'OK' ); + $processor->get_updated_html(); + + $this->assertTrue( $processor->has_class( '&' ), 'Missing expected "&" class.' ); + $this->assertTrue( $processor->has_class( '"' ), 'Missing expected \'"\' class.' ); + $this->assertTrue( $processor->has_class( 'OK' ), 'Missing expected "OK" class.' ); + + $expected = '
'; + $this->assertEqualHTML( + $expected, + $processor->get_updated_html(), + '', + 'HTML was not correctly updated after adding classes.' + ); + + $processor->remove_class( '&' ); + $processor->get_updated_html(); + + $processor->remove_class( '"' ); + $processor->get_updated_html(); + + $this->assertFalse( $processor->has_class( '&' ) ); + $this->assertFalse( $processor->has_class( '"' ) ); + $this->assertTrue( $processor->has_class( 'OK' ) ); + + $expected = '
'; + $this->assertEqualHTML( + $expected, + $processor->get_updated_html(), + '', + 'HTML was not correctly updated after removing classes.' + ); + } + /** * @covers WP_HTML_Tag_Processor::next_tag */ From c2d591fe9dffce3c8b70aea4e19c45f1a8a84575 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Wed, 3 Dec 2025 18:07:53 +0000 Subject: [PATCH 003/126] General: Leverage `DOMParser` to implement `wp.sanitize.stripTags()`. Developed in https://github.com/WordPress/wordpress-develop/pull/10536 Follow-up to [60907]. Props hbhalodia, dmsnell, westonruter. See #48054. Fixes #64274. git-svn-id: https://develop.svn.wordpress.org/trunk@61347 602fd350-edb4-49c9-b593-d223f7449a82 --- src/js/_enqueues/wp/sanitize.js | 29 ++++++++++++++++------------- 1 file changed, 16 insertions(+), 13 deletions(-) diff --git a/src/js/_enqueues/wp/sanitize.js b/src/js/_enqueues/wp/sanitize.js index 4252d0a014f7a..4fec26ab30683 100644 --- a/src/js/_enqueues/wp/sanitize.js +++ b/src/js/_enqueues/wp/sanitize.js @@ -23,22 +23,25 @@ * @return {string} Stripped text. */ stripTags: function( text ) { - let _text = text || ''; + const domParser = new DOMParser(); + const htmlDocument = domParser.parseFromString( + text, + 'text/html' + ); - // Do the search-replace until there is nothing to be replaced. - do { - // Keep pre-replace text for comparison. - text = _text; - - // Do the replacement. - _text = text - .replace( /|$)/g, '' ) - .replace( /<(script|style)[^>]*>[\s\S]*?(<\/\1>|$)/ig, '' ) - .replace( /<\/?[a-z][\s\S]*?(>|$)/ig, '' ); - } while ( _text !== text ); + /* + * The following self-assignment appears to be a no-op, but it isn't. + * It enforces the escaping. Reading the `innerText` property decodes + * character references, returning a raw string. When written, however, + * the text is re-escaped to ensure that the rendered text replicates + * what it's given. + * + * See . + */ + htmlDocument.body.innerText = htmlDocument.body.innerText; // Return the text with stripped tags. - return _text; + return htmlDocument.body.innerHTML; }, /** From 55134bdb13d9c526801251536b7f348043900678 Mon Sep 17 00:00:00 2001 From: westonruter Date: Wed, 3 Dec 2025 19:45:02 +0000 Subject: [PATCH 004/126] Block Editor: Move Block Patterns API functions to `block-patterns.php`. Follow-up to [48156]. Props anukasha, dhiraj0901, swissspidy, palak678, madhavishah01. See #50445. Fixes #64234. git-svn-id: https://develop.svn.wordpress.org/trunk@61348 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/block-patterns.php | 53 +++++++++++++++++++ ...s-wp-block-pattern-categories-registry.php | 27 ---------- .../class-wp-block-patterns-registry.php | 26 --------- 3 files changed, 53 insertions(+), 53 deletions(-) diff --git a/src/wp-includes/block-patterns.php b/src/wp-includes/block-patterns.php index 4a2886cdfd38f..133c6d54ea33a 100644 --- a/src/wp-includes/block-patterns.php +++ b/src/wp-includes/block-patterns.php @@ -8,6 +8,59 @@ add_theme_support( 'core-block-patterns' ); +/** + * Registers a new block pattern. + * + * @since 5.5.0 + * + * @param string $pattern_name Block pattern name including namespace. + * @param array $pattern_properties List of properties for the block pattern. + * See WP_Block_Patterns_Registry::register() for accepted arguments. + * @return bool True if the pattern was registered with success and false otherwise. + */ +function register_block_pattern( $pattern_name, $pattern_properties ) { + return WP_Block_Patterns_Registry::get_instance()->register( $pattern_name, $pattern_properties ); +} + +/** + * Unregisters a block pattern. + * + * @since 5.5.0 + * + * @param string $pattern_name Block pattern name including namespace. + * @return bool True if the pattern was unregistered with success and false otherwise. + */ +function unregister_block_pattern( $pattern_name ) { + return WP_Block_Patterns_Registry::get_instance()->unregister( $pattern_name ); +} + +/** + * Registers a new pattern category. + * + * @since 5.5.0 + * + * @param string $category_name Pattern category name including namespace. + * @param array $category_properties List of properties for the block pattern. + * See WP_Block_Pattern_Categories_Registry::register() for + * accepted arguments. + * @return bool True if the pattern category was registered with success and false otherwise. + */ +function register_block_pattern_category( $category_name, $category_properties ) { + return WP_Block_Pattern_Categories_Registry::get_instance()->register( $category_name, $category_properties ); +} + +/** + * Unregisters a pattern category. + * + * @since 5.5.0 + * + * @param string $category_name Pattern category name including namespace. + * @return bool True if the pattern category was unregistered with success and false otherwise. + */ +function unregister_block_pattern_category( $category_name ) { + return WP_Block_Pattern_Categories_Registry::get_instance()->unregister( $category_name ); +} + /** * Registers the core block patterns and categories. * diff --git a/src/wp-includes/class-wp-block-pattern-categories-registry.php b/src/wp-includes/class-wp-block-pattern-categories-registry.php index 05ddce8af0547..be7cd6d467538 100644 --- a/src/wp-includes/class-wp-block-pattern-categories-registry.php +++ b/src/wp-includes/class-wp-block-pattern-categories-registry.php @@ -162,30 +162,3 @@ public static function get_instance() { return self::$instance; } } - -/** - * Registers a new pattern category. - * - * @since 5.5.0 - * - * @param string $category_name Pattern category name including namespace. - * @param array $category_properties List of properties for the block pattern. - * See WP_Block_Pattern_Categories_Registry::register() for - * accepted arguments. - * @return bool True if the pattern category was registered with success and false otherwise. - */ -function register_block_pattern_category( $category_name, $category_properties ) { - return WP_Block_Pattern_Categories_Registry::get_instance()->register( $category_name, $category_properties ); -} - -/** - * Unregisters a pattern category. - * - * @since 5.5.0 - * - * @param string $category_name Pattern category name including namespace. - * @return bool True if the pattern category was unregistered with success and false otherwise. - */ -function unregister_block_pattern_category( $category_name ) { - return WP_Block_Pattern_Categories_Registry::get_instance()->unregister( $category_name ); -} diff --git a/src/wp-includes/class-wp-block-patterns-registry.php b/src/wp-includes/class-wp-block-patterns-registry.php index 4667979fc72b5..fe85160bac831 100644 --- a/src/wp-includes/class-wp-block-patterns-registry.php +++ b/src/wp-includes/class-wp-block-patterns-registry.php @@ -277,29 +277,3 @@ public static function get_instance() { return self::$instance; } } - -/** - * Registers a new block pattern. - * - * @since 5.5.0 - * - * @param string $pattern_name Block pattern name including namespace. - * @param array $pattern_properties List of properties for the block pattern. - * See WP_Block_Patterns_Registry::register() for accepted arguments. - * @return bool True if the pattern was registered with success and false otherwise. - */ -function register_block_pattern( $pattern_name, $pattern_properties ) { - return WP_Block_Patterns_Registry::get_instance()->register( $pattern_name, $pattern_properties ); -} - -/** - * Unregisters a block pattern. - * - * @since 5.5.0 - * - * @param string $pattern_name Block pattern name including namespace. - * @return bool True if the pattern was unregistered with success and false otherwise. - */ -function unregister_block_pattern( $pattern_name ) { - return WP_Block_Patterns_Registry::get_instance()->unregister( $pattern_name ); -} From 040e6b60a9e1ae720204da19201152980e2ea28b Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Wed, 3 Dec 2025 20:52:53 +0000 Subject: [PATCH 005/126] Database: Further correct MariaDB version check in `wpdb::has_cap()`. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit On older PHP versions, MariaDB version is reported with the `5.5.5-` prefix, e.g. `5.5.5-10.6.24-MariaDB`. This includes PHP 8.0.15 or earlier, as well as PHP 8.1.0—8.1.2, which was not accounted for previously. This commit updates the condition for removing the `5.5.5-` prefix to include PHP 8.1.0—8.1.2. Follow-up to [54384]. Props maximumsoftware, hbhalodia, SergeyBiryukov. Fixes #64332. git-svn-id: https://develop.svn.wordpress.org/trunk@61349 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/class-wpdb.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/wp-includes/class-wpdb.php b/src/wp-includes/class-wpdb.php index 68f1acfdf751f..23c865b87d817 100644 --- a/src/wp-includes/class-wpdb.php +++ b/src/wp-includes/class-wpdb.php @@ -4081,7 +4081,8 @@ public function has_cap( $db_cap ) { * the polyfills from wp-includes/compat.php are not loaded. */ if ( '5.5.5' === $db_version && false !== strpos( $db_server_info, 'MariaDB' ) - && PHP_VERSION_ID < 80016 // PHP 8.0.15 or older. + && ( PHP_VERSION_ID <= 80015 // PHP 8.0.15 or older. + || 80100 <= PHP_VERSION_ID && PHP_VERSION_ID <= 80102 ) // PHP 8.1.0 to PHP 8.1.2. ) { // Strip the '5.5.5-' prefix and set the version to the correct value. $db_server_info = preg_replace( '/^5\.5\.5-(.*)/', '$1', $db_server_info ); From fab4765bf2a54e14ebe7362389b8af714c0d4f83 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Thu, 4 Dec 2025 23:06:50 +0000 Subject: [PATCH 006/126] Upgrade/Install: Add missing file to the `$_old_files` array. Follow-up to [60490], [61338]. Props WFMattR, sajib1223, davidbaumwald, mukesh27, SergeyBiryukov. Fixes #64336. git-svn-id: https://develop.svn.wordpress.org/trunk@61351 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/update-core.php | 1 + 1 file changed, 1 insertion(+) diff --git a/src/wp-admin/includes/update-core.php b/src/wp-admin/includes/update-core.php index e1b5398fb46c2..e417966c130fc 100644 --- a/src/wp-admin/includes/update-core.php +++ b/src/wp-admin/includes/update-core.php @@ -847,6 +847,7 @@ 'wp-includes/blocks/post-author/editor-rtl.css', 'wp-includes/blocks/post-author/editor-rtl.min.css', 'wp-includes/SimplePie/src/Decode', + 'wp-includes/SimplePie/src/Core.php', ); /** From 9ac51695f3c3c08d81b95248ce7c6d2bccd614a6 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Fri, 5 Dec 2025 01:38:48 +0000 Subject: [PATCH 007/126] Mail: Add missing `embeds` key for the `wp_mail_succeeded` action's `$mail_data` param. Follow-up to [60698]. Props iflairwebtechnologies, SirLouen, johnbillion. See #28059. Fixes #64348. git-svn-id: https://develop.svn.wordpress.org/trunk@61352 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/pluggable.php | 2 +- tests/phpunit/tests/pluggable/wpMail.php | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/src/wp-includes/pluggable.php b/src/wp-includes/pluggable.php index 8f167ca2b16a8..1d5ee194c9f10 100644 --- a/src/wp-includes/pluggable.php +++ b/src/wp-includes/pluggable.php @@ -618,7 +618,7 @@ function wp_mail( $to, $subject, $message, $headers = '', $attachments = array() */ do_action_ref_array( 'phpmailer_init', array( &$phpmailer ) ); - $mail_data = compact( 'to', 'subject', 'message', 'headers', 'attachments' ); + $mail_data = compact( 'to', 'subject', 'message', 'headers', 'attachments', 'embeds' ); // Send! try { diff --git a/tests/phpunit/tests/pluggable/wpMail.php b/tests/phpunit/tests/pluggable/wpMail.php index b7ed263b10ded..785c73eccda6e 100644 --- a/tests/phpunit/tests/pluggable/wpMail.php +++ b/tests/phpunit/tests/pluggable/wpMail.php @@ -446,6 +446,7 @@ public function test_phpmailer_exception_thrown() { 'message' => 'Test Message', 'headers' => array(), 'attachments' => array(), + 'embeds' => array(), 'phpmailer_exception_code' => 2, ); From c0f72c22720ebb369f84b5d363b953d3dbbc950c Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Fri, 5 Dec 2025 05:48:07 +0000 Subject: [PATCH 008/126] Plugins: Restore line break between the filter links row and the plugin cards in the Featured view. Follow-up to [60528]. Props mukesh27, sajib1223, TobiasBg, narenin, sabernhardt, westonruter. See #63723. Fixes #64337. git-svn-id: https://develop.svn.wordpress.org/trunk@61353 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/plugin-install.php | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/src/wp-admin/includes/plugin-install.php b/src/wp-admin/includes/plugin-install.php index 7e5a04c0a0aa5..9925c26bb33c1 100644 --- a/src/wp-admin/includes/plugin-install.php +++ b/src/wp-admin/includes/plugin-install.php @@ -399,6 +399,7 @@ function display_plugins_table() { ); break; case 'install_plugins_featured': + echo '
'; break; case 'install_plugins_recommended': echo '

' . __( 'These suggestions are based on the plugins you and other users have installed.' ) . '

'; @@ -409,9 +410,6 @@ function display_plugins_table() { } break; } - if ( isset( $_GET['tab'] ) && 'featured' === $_GET['tab'] ) { - echo '
'; - } ?>
display(); ?> From 7cfd4043a92e132605f9f3a81c4a47e08dd50619 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Fri, 5 Dec 2025 18:30:24 +0000 Subject: [PATCH 009/126] Docs: Update `@since x.y.z` with actual version number. Follow-up to [60364]. Props solankisoftware, oztaser. See #43421. Fixes #64366. git-svn-id: https://develop.svn.wordpress.org/trunk@61354 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/capabilities.php | 2 +- src/wp-includes/class-wp-roles.php | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/wp-includes/capabilities.php b/src/wp-includes/capabilities.php index 85f68985de511..80f203eb7c88f 100644 --- a/src/wp-includes/capabilities.php +++ b/src/wp-includes/capabilities.php @@ -1124,7 +1124,7 @@ function get_role( $role ) { * ) ); * * @since 2.0.0 - * @since x.y.z Support was added for a numerically indexed array of strings for the capabilities array. + * @since 6.9.0 Support was added for a numerically indexed array of strings for the capabilities array. * * @param string $role Role name. * @param string $display_name Display name for role. diff --git a/src/wp-includes/class-wp-roles.php b/src/wp-includes/class-wp-roles.php index 0b94e0f9594cf..f620fb5a05ac7 100644 --- a/src/wp-includes/class-wp-roles.php +++ b/src/wp-includes/class-wp-roles.php @@ -165,7 +165,7 @@ public function reinit() { * ) ); * * @since 2.0.0 - * @since x.y.z Support was added for a numerically indexed array of strings for the capabilities array. + * @since 6.9.0 Support was added for a numerically indexed array of strings for the capabilities array. * * @param string $role Role name. * @param string $display_name Role display name. From 5a6356eacd998136263429d96a72aecc28bb1ad3 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Sat, 6 Dec 2025 01:52:00 +0000 Subject: [PATCH 010/126] Site Health: Add common HTTP response headers for page cache detection. Developed in https://github.com/WordPress/wordpress-develop/pull/10598 Follow-up to [54043]. Props akshat2802, szepeviktor, dmsnell, vincentbreton, dannythedog, westonruter. See #56041. Fixes #63748. git-svn-id: https://develop.svn.wordpress.org/trunk@61355 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/class-wp-site-health.php | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/src/wp-admin/includes/class-wp-site-health.php b/src/wp-admin/includes/class-wp-site-health.php index 8388d7ad37a58..a5a8c7f4dade2 100644 --- a/src/wp-admin/includes/class-wp-site-health.php +++ b/src/wp-admin/includes/class-wp-site-health.php @@ -3412,6 +3412,16 @@ public function get_page_cache_headers() { }, 'x-srcache-store-status' => $cache_hit_callback, 'x-srcache-fetch-status' => $cache_hit_callback, + + // Generic caching proxies (Nginx, Varnish, etc.) + 'x-cache' => $cache_hit_callback, + 'x-cache-status' => $cache_hit_callback, + 'x-litespeed-cache' => $cache_hit_callback, + 'x-proxy-cache' => $cache_hit_callback, + 'via' => '', + + // Cloudflare + 'cf-cache-status' => $cache_hit_callback, ); /** From 6548b0792f4e3e197604ca61e75f0d4481469946 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Sat, 6 Dec 2025 12:26:37 +0000 Subject: [PATCH 011/126] Docs: Add missing parameter descriptions in `wp-admin/install.php`. Follow-up to [32654]. Props rejaulalomkhan. See #64224. git-svn-id: https://develop.svn.wordpress.org/trunk@61356 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/install.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/wp-admin/install.php b/src/wp-admin/install.php index 64cb4104c41ae..1bd34a4973d51 100644 --- a/src/wp-admin/install.php +++ b/src/wp-admin/install.php @@ -52,7 +52,7 @@ * * @since 2.5.0 * - * @param string $body_classes + * @param string $body_classes Class attribute values for the body tag. */ function display_header( $body_classes = '' ) { header( 'Content-Type: text/html; charset=utf-8' ); @@ -85,7 +85,7 @@ function display_header( $body_classes = '' ) { * * @global wpdb $wpdb WordPress database abstraction object. * - * @param string|null $error + * @param string|null $error Error message to display, if any. */ function display_setup_form( $error = null ) { global $wpdb; From 0af5be7a634b5b2de29560894c5273885d52ab22 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Sun, 7 Dec 2025 01:09:51 +0000 Subject: [PATCH 012/126] Script Loader: Re-target release for missing dependency notices from 7.0.0 to 6.9.1. Follow-up to [61323], [60999]. See #64229. git-svn-id: https://develop.svn.wordpress.org/trunk@61357 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/class-wp-dependencies.php | 6 +++--- src/wp-includes/class-wp-script-modules.php | 4 ++-- src/wp-includes/class-wp-scripts.php | 2 +- src/wp-includes/class-wp-styles.php | 2 +- 4 files changed, 7 insertions(+), 7 deletions(-) diff --git a/src/wp-includes/class-wp-dependencies.php b/src/wp-includes/class-wp-dependencies.php index 60c117d2f67b4..92c277e86fe6b 100644 --- a/src/wp-includes/class-wp-dependencies.php +++ b/src/wp-includes/class-wp-dependencies.php @@ -111,7 +111,7 @@ class WP_Dependencies { * warning is emitted with {@see _doing_it_wrong()}. The handle is then added to this list, so that duplicate * warnings don't occur. * - * @since 7.0.0 + * @since 6.9.1 * @var string[] */ private $dependencies_with_missing_dependencies = array(); @@ -223,7 +223,7 @@ public function all_deps( $handles, $recursion = false, $group = false ) { _doing_it_wrong( get_class( $this ) . '::add', $this->get_dependency_warning_message( $handle, $missing_dependencies ), - '7.0.0' + '6.9.1' ); $this->dependencies_with_missing_dependencies[] = $handle; } @@ -563,7 +563,7 @@ public function get_etag( $load ) { /** * Gets a dependency warning message for a handle. * - * @since 7.0.0 + * @since 6.9.1 * * @param string $handle Handle with missing dependencies. * @param string[] $missing_dependency_handles Missing dependency handles. diff --git a/src/wp-includes/class-wp-script-modules.php b/src/wp-includes/class-wp-script-modules.php index e05e1900a2b49..d5769675156f5 100644 --- a/src/wp-includes/class-wp-script-modules.php +++ b/src/wp-includes/class-wp-script-modules.php @@ -76,7 +76,7 @@ class WP_Script_Modules { * An ID is added to this list when it is discovered to have missing dependencies. At this time, a warning is * emitted with {@see _doing_it_wrong()}. The ID is then added to this list, so that duplicate warnings don't occur. * - * @since 7.0.0 + * @since 6.9.1 * @var string[] */ private $modules_with_missing_dependencies = array(); @@ -744,7 +744,7 @@ private function sort_item_dependencies( string $id, array $import_types, array $id, implode( ', ', $missing_dependencies ) ), - '7.0.0' + '6.9.1' ); $this->modules_with_missing_dependencies[] = $id; } diff --git a/src/wp-includes/class-wp-scripts.php b/src/wp-includes/class-wp-scripts.php index a30b09249fd52..3e7908095e2cb 100644 --- a/src/wp-includes/class-wp-scripts.php +++ b/src/wp-includes/class-wp-scripts.php @@ -1168,7 +1168,7 @@ public function reset() { /** * Gets a script-specific dependency warning message. * - * @since 7.0.0 + * @since 6.9.1 * * @param string $handle Script handle with missing dependencies. * @param string[] $missing_dependency_handles Missing dependency handles. diff --git a/src/wp-includes/class-wp-styles.php b/src/wp-includes/class-wp-styles.php index 67fb3a0fd40e1..455f1c986e8dc 100644 --- a/src/wp-includes/class-wp-styles.php +++ b/src/wp-includes/class-wp-styles.php @@ -497,7 +497,7 @@ public function reset() { /** * Gets a style-specific dependency warning message. * - * @since 7.0.0 + * @since 6.9.1 * * @param string $handle Style handle with missing dependencies. * @param string[] $missing_dependency_handles Missing dependency handles. From d0a4bf290763ddd4ac2c7ad7b6b05fca681893f5 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Sun, 7 Dec 2025 04:14:08 +0000 Subject: [PATCH 013/126] Docs: Improve accuracy for types in phpdoc for `WP_Dependencies`, `_WP_Dependency`, `WP_Scripts`, and `WP_Styles`. This increases these classes to PHPStan level 8. Developed in https://github.com/WordPress/wordpress-develop/pull/10607 See #64238. git-svn-id: https://develop.svn.wordpress.org/trunk@61358 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/class-wp-dependencies.php | 7 ++++--- src/wp-includes/class-wp-dependency.php | 4 ++-- src/wp-includes/class-wp-scripts.php | 13 +++++++------ src/wp-includes/class-wp-styles.php | 4 ++-- 4 files changed, 15 insertions(+), 13 deletions(-) diff --git a/src/wp-includes/class-wp-dependencies.php b/src/wp-includes/class-wp-dependencies.php index 92c277e86fe6b..c3dc40bc88141 100644 --- a/src/wp-includes/class-wp-dependencies.php +++ b/src/wp-includes/class-wp-dependencies.php @@ -56,11 +56,12 @@ class WP_Dependencies { /** * An array of additional arguments passed when a handle is registered. * - * Arguments are appended to the item query string. + * The keys are dependency handles and the values are query strings which are appended to the item URL's query + * string, after the `ver` if provided. * * @since 2.6.0 * - * @var array + * @var array */ public $args = array(); @@ -100,7 +101,7 @@ class WP_Dependencies { * * @since 5.9.0 * - * @var array + * @var array */ private $queued_before_register = array(); diff --git a/src/wp-includes/class-wp-dependency.php b/src/wp-includes/class-wp-dependency.php index 6666b166af7ad..4900bf737ddeb 100644 --- a/src/wp-includes/class-wp-dependency.php +++ b/src/wp-includes/class-wp-dependency.php @@ -66,7 +66,7 @@ class _WP_Dependency { * Extra data to supply to the handle. * * @since 2.6.0 - * @var array + * @var array */ public $extra = array(); @@ -82,7 +82,7 @@ class _WP_Dependency { * Translation path set for this dependency. * * @since 5.0.0 - * @var string + * @var string|null */ public $translations_path; diff --git a/src/wp-includes/class-wp-scripts.php b/src/wp-includes/class-wp-scripts.php index 3e7908095e2cb..13266274048ea 100644 --- a/src/wp-includes/class-wp-scripts.php +++ b/src/wp-includes/class-wp-scripts.php @@ -46,7 +46,7 @@ class WP_Scripts extends WP_Dependencies { * Holds handles of scripts which are enqueued in footer. * * @since 2.8.0 - * @var array + * @var string[] */ public $in_footer = array(); @@ -118,7 +118,7 @@ class WP_Scripts extends WP_Dependencies { * List of default directories. * * @since 2.8.0 - * @var array + * @var string[]|null */ public $default_dirs; @@ -374,7 +374,8 @@ public function do_item( $handle, $group = false ) { $filtered_src = apply_filters( 'script_loader_src', $src, $handle ); if ( - $this->in_default_dir( $filtered_src ) + is_string( $filtered_src ) + && $this->in_default_dir( $filtered_src ) && ( $before_script || $after_script || $translations_stop_concat || $this->is_delayed_strategy( $strategy ) ) ) { $this->do_concat = false; @@ -589,9 +590,9 @@ public function get_inline_script_tag( $handle, $position = 'after' ) { * * @since 2.1.0 * - * @param string $handle Name of the script to attach data to. - * @param string $object_name Name of the variable that will contain the data. - * @param array $l10n Array of data to localize. + * @param string $handle Name of the script to attach data to. + * @param string $object_name Name of the variable that will contain the data. + * @param array $l10n Array of data to localize. * @return bool True on success, false on failure. */ public function localize( $handle, $object_name, $l10n ) { diff --git a/src/wp-includes/class-wp-styles.php b/src/wp-includes/class-wp-styles.php index 455f1c986e8dc..2af3581d9aae1 100644 --- a/src/wp-includes/class-wp-styles.php +++ b/src/wp-includes/class-wp-styles.php @@ -96,7 +96,7 @@ class WP_Styles extends WP_Dependencies { * List of default directories. * * @since 2.8.0 - * @var array + * @var string[]|null */ public $default_dirs; @@ -183,7 +183,7 @@ public function do_item( $handle, $group = false ) { } if ( $this->do_concat ) { - if ( $this->in_default_dir( $src ) && ! isset( $obj->extra['alt'] ) ) { + if ( is_string( $src ) && $this->in_default_dir( $src ) && ! isset( $obj->extra['alt'] ) ) { $this->concat .= "$handle,"; $this->concat_version .= "$handle$ver"; From 4804f98c3ca557fc55731d0217a9f9394213406c Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Sun, 7 Dec 2025 06:47:15 +0000 Subject: [PATCH 014/126] Site Health: Include value of `EMPTY_TRASH_DAYS` constant in debug data. Follow-up to [44986], [45078], [58855]. Props deepakprajapati, desrosj, dhruvang21, SergeyBiryukov. Fixes #64189. git-svn-id: https://develop.svn.wordpress.org/trunk@61359 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/class-wp-debug-data.php | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/src/wp-admin/includes/class-wp-debug-data.php b/src/wp-admin/includes/class-wp-debug-data.php index cd04297684bcd..9823396dd4d70 100644 --- a/src/wp-admin/includes/class-wp-debug-data.php +++ b/src/wp-admin/includes/class-wp-debug-data.php @@ -1592,6 +1592,11 @@ private static function get_wp_constants(): array { 'value' => $db_collate, 'debug' => $db_collate_debug, ), + 'EMPTY_TRASH_DAYS' => array( + 'label' => 'EMPTY_TRASH_DAYS', + 'value' => EMPTY_TRASH_DAYS ? EMPTY_TRASH_DAYS : __( 'Empty value' ), + 'debug' => EMPTY_TRASH_DAYS, + ), ); return array( From 4e69f1529604d51e200ceb78f8412a72d2560c61 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Mon, 8 Dec 2025 21:53:05 +0000 Subject: [PATCH 015/126] Posts, Post Types: Only set default title for custom post types if they have title support. Previously, the default post title was always set to `Auto Draft`, regardless of whether the CPT supports a title. This commit ensures that the default title is present when a CPT has title support, and is an empty string otherwise. Follow-up to [12987], [49288], [49614]. Props SirLouen, rajanit2000, garrett-eclipse, wildworks, nrqsnchz, donmhico, marybaum, audrasjb, bridgetwillard, TimothyBlynJacobs, joyously, hellofromTonya, helen, Cybr, mosescursor, fakhriaz, gulamdastgir04, peterwilsoncc, mindctrl, westonruter, SergeyBiryukov. Fixes #45516. git-svn-id: https://develop.svn.wordpress.org/trunk@61360 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/post.php | 2 +- tests/phpunit/tests/admin/includesPost.php | 32 ++++++++++++++++++++++ 2 files changed, 33 insertions(+), 1 deletion(-) diff --git a/src/wp-admin/includes/post.php b/src/wp-admin/includes/post.php index 97345331de221..ab8fb62a7b4f0 100644 --- a/src/wp-admin/includes/post.php +++ b/src/wp-admin/includes/post.php @@ -764,7 +764,7 @@ function get_default_post_to_edit( $post_type = 'post', $create_in_db = false ) if ( $create_in_db ) { $post_id = wp_insert_post( array( - 'post_title' => __( 'Auto Draft' ), + 'post_title' => post_type_supports( $post_type, 'title' ) ? __( 'Auto Draft' ) : '', 'post_type' => $post_type, 'post_status' => 'auto-draft', ), diff --git a/tests/phpunit/tests/admin/includesPost.php b/tests/phpunit/tests/admin/includesPost.php index f049ac7d686b7..d9d39d8da727d 100644 --- a/tests/phpunit/tests/admin/includesPost.php +++ b/tests/phpunit/tests/admin/includesPost.php @@ -548,6 +548,38 @@ public function test_get_default_post_to_edit_with_wp_insert_post_error() { get_default_post_to_edit( 'post', true ); } + /** + * Tests that default post title is present when a CPT has title support, and is empty otherwise. + * + * @ticket 45516 + * + * @covers ::get_default_post_to_edit + */ + public function test_get_default_post_to_edit_with_and_without_title_support() { + register_post_type( + 'yes_title', + array( + 'supports' => array( 'title', 'editor' ), + ) + ); + register_post_type( + 'no_title', + array( + 'supports' => array( 'editor' ), + ) + ); + + /* + * The ID is obtained because get_default_post_to_edit() will force the post_title + * to be overridden on the returned WP_Post object. + */ + $default_yes_title_post_id = get_default_post_to_edit( 'yes_title', true )->ID; + $default_no_title_post_id = get_default_post_to_edit( 'no_title', true )->ID; + + $this->assertSame( __( 'Auto Draft' ), get_post( $default_yes_title_post_id )->post_title, 'Expected post_title to be the default title.' ); + $this->assertSame( '', get_post( $default_no_title_post_id )->post_title, 'Expected post_title to be an empty string.' ); + } + /** * @ticket 38293 */ From e7009d64e2c8a36c2afe550f099b80d6bf4c029f Mon Sep 17 00:00:00 2001 From: Aki Hamano Date: Tue, 9 Dec 2025 06:32:55 +0000 Subject: [PATCH 016/126] I18N: add border.radiusSizes key to theme-i18n.json Makes border radius size name property translatable by updating `theme.json` i18n schema. Props hbhalodia, mukesh27, swissspidy, twvania, umeshsinghin, wildworks. Fixes #64333. git-svn-id: https://develop.svn.wordpress.org/trunk@61361 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/theme-i18n.json | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/src/wp-includes/theme-i18n.json b/src/wp-includes/theme-i18n.json index 1b7a8d0d31190..8ceaee85afbbe 100644 --- a/src/wp-includes/theme-i18n.json +++ b/src/wp-includes/theme-i18n.json @@ -52,6 +52,13 @@ } ] }, + "border": { + "radiusSizes": [ + { + "name": "Border radius size name" + } + ] + }, "blocks": { "*": { "typography": { @@ -96,6 +103,13 @@ "name": "Space size name" } ] + }, + "border": { + "radiusSizes": [ + { + "name": "Border radius size name" + } + ] } } } From 4b2de7ade71feb3bfcb298913eb88bbdd4c14deb Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Tue, 9 Dec 2025 06:52:03 +0000 Subject: [PATCH 017/126] Docs: Improve specificity of types in `WP_Script_Modules` and `script-modules.php` functions. Developed in https://github.com/WordPress/wordpress-develop/pull/10614 Follow-up to [61358]. See #64238. git-svn-id: https://develop.svn.wordpress.org/trunk@61362 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/class-wp-script-modules.php | 108 ++++++++++---------- src/wp-includes/script-modules.php | 100 +++++++++--------- 2 files changed, 104 insertions(+), 104 deletions(-) diff --git a/src/wp-includes/class-wp-script-modules.php b/src/wp-includes/class-wp-script-modules.php index d5769675156f5..ff3973999581b 100644 --- a/src/wp-includes/class-wp-script-modules.php +++ b/src/wp-includes/class-wp-script-modules.php @@ -88,31 +88,31 @@ class WP_Script_Modules { * @since 6.5.0 * @since 6.9.0 Added the $args parameter. * - * @param string $id The identifier of the script module. Should be unique. It will be used in the - * final import map. - * @param string $src Optional. Full URL of the script module, or path of the script module relative - * to the WordPress root directory. If it is provided and the script module has - * not been registered yet, it will be registered. - * @param array $deps { - * Optional. List of dependencies. - * - * @type string|array ...$0 { - * An array of script module identifiers of the dependencies of this script - * module. The dependencies can be strings or arrays. If they are arrays, - * they need an `id` key with the script module identifier, and can contain - * an `import` key with either `static` or `dynamic`. By default, - * dependencies that don't contain an `import` key are considered static. - * - * @type string $id The script module identifier. - * @type string $import Optional. Import type. May be either `static` or - * `dynamic`. Defaults to `static`. - * } - * } - * @param string|false|null $version Optional. String specifying the script module version number. Defaults to false. - * It is added to the URL as a query string for cache busting purposes. If $version - * is set to false, the version number is the currently installed WordPress version. - * If $version is set to null, no version is added. - * @param array $args { + * @param string $id The identifier of the script module. Should be unique. It will be used in the + * final import map. + * @param string $src Optional. Full URL of the script module, or path of the script module relative + * to the WordPress root directory. If it is provided and the script module has + * not been registered yet, it will be registered. + * @param array $deps { + * Optional. List of dependencies. + * + * @type string|array ...$0 { + * An array of script module identifiers of the dependencies of this script + * module. The dependencies can be strings or arrays. If they are arrays, + * they need an `id` key with the script module identifier, and can contain + * an `import` key with either `static` or `dynamic`. By default, + * dependencies that don't contain an `import` key are considered static. + * + * @type string $id The script module identifier. + * @type string $import Optional. Import type. May be either `static` or + * `dynamic`. Defaults to `static`. + * } + * } + * @param string|false|null $version Optional. String specifying the script module version number. Defaults to false. + * It is added to the URL as a query string for cache busting purposes. If $version + * is set to false, the version number is the currently installed WordPress version. + * If $version is set to null, no version is added. + * @param array $args { * Optional. An array of additional args. Default empty array. * * @type bool $in_footer Whether to print the script module in the footer. Only relevant to block themes. Default 'false'. Optional. @@ -260,31 +260,31 @@ public function set_in_footer( string $id, bool $in_footer ): bool { * @since 6.5.0 * @since 6.9.0 Added the $args parameter. * - * @param string $id The identifier of the script module. Should be unique. It will be used in the - * final import map. - * @param string $src Optional. Full URL of the script module, or path of the script module relative - * to the WordPress root directory. If it is provided and the script module has - * not been registered yet, it will be registered. - * @param array $deps { - * Optional. List of dependencies. - * - * @type string|array ...$0 { - * An array of script module identifiers of the dependencies of this script - * module. The dependencies can be strings or arrays. If they are arrays, - * they need an `id` key with the script module identifier, and can contain - * an `import` key with either `static` or `dynamic`. By default, - * dependencies that don't contain an `import` key are considered static. - * - * @type string $id The script module identifier. - * @type string $import Optional. Import type. May be either `static` or - * `dynamic`. Defaults to `static`. - * } - * } - * @param string|false|null $version Optional. String specifying the script module version number. Defaults to false. - * It is added to the URL as a query string for cache busting purposes. If $version - * is set to false, the version number is the currently installed WordPress version. - * If $version is set to null, no version is added. - * @param array $args { + * @param string $id The identifier of the script module. Should be unique. It will be used in the + * final import map. + * @param string $src Optional. Full URL of the script module, or path of the script module relative + * to the WordPress root directory. If it is provided and the script module has + * not been registered yet, it will be registered. + * @param array $deps { + * Optional. List of dependencies. + * + * @type string|array ...$0 { + * An array of script module identifiers of the dependencies of this script + * module. The dependencies can be strings or arrays. If they are arrays, + * they need an `id` key with the script module identifier, and can contain + * an `import` key with either `static` or `dynamic`. By default, + * dependencies that don't contain an `import` key are considered static. + * + * @type string $id The script module identifier. + * @type string $import Optional. Import type. May be either `static` or + * `dynamic`. Defaults to `static`. + * } + * } + * @param string|false|null $version Optional. String specifying the script module version number. Defaults to false. + * It is added to the URL as a query string for cache busting purposes. If $version + * is set to false, the version number is the currently installed WordPress version. + * If $version is set to null, no version is added. + * @param array $args { * Optional. An array of additional args. Default empty array. * * @type bool $in_footer Whether to print the script module in the footer. Only relevant to block themes. Default 'false'. Optional. @@ -534,8 +534,8 @@ public function print_import_map() { * * @since 6.5.0 * - * @return array Array with an `imports` key mapping to an array of script module identifiers and their respective - * URLs, including the version query. + * @return array> Array with an `imports` key mapping to an array of script module + * identifiers and their respective URLs, including the version query. */ private function get_import_map(): array { $imports = array(); @@ -556,7 +556,7 @@ private function get_import_map(): array { * * @since 6.5.0 * - * @return array Script modules marked for enqueue, keyed by script module identifier. + * @return array> Script modules marked for enqueue, keyed by script module identifier. */ private function get_marked_for_enqueue(): array { return wp_array_slice_assoc( @@ -577,7 +577,7 @@ private function get_marked_for_enqueue(): array { * @param string[] $ids The identifiers of the script modules for which to gather dependencies. * @param string[] $import_types Optional. Import types of dependencies to retrieve: 'static', 'dynamic', or both. * Default is both. - * @return array List of dependencies, keyed by script module identifier. + * @return array> List of dependencies, keyed by script module identifier. */ private function get_dependencies( array $ids, array $import_types = array( 'static', 'dynamic' ) ): array { $all_dependencies = array(); diff --git a/src/wp-includes/script-modules.php b/src/wp-includes/script-modules.php index fc2197889f761..c1e90c1c852eb 100644 --- a/src/wp-includes/script-modules.php +++ b/src/wp-includes/script-modules.php @@ -37,31 +37,31 @@ function wp_script_modules(): WP_Script_Modules { * @since 6.5.0 * @since 6.9.0 Added the $args parameter. * - * @param string $id The identifier of the script module. Should be unique. It will be used in the - * final import map. - * @param string $src Optional. Full URL of the script module, or path of the script module relative - * to the WordPress root directory. If it is provided and the script module has - * not been registered yet, it will be registered. - * @param array $deps { - * Optional. List of dependencies. - * - * @type string|array ...$0 { - * An array of script module identifiers of the dependencies of this script - * module. The dependencies can be strings or arrays. If they are arrays, - * they need an `id` key with the script module identifier, and can contain - * an `import` key with either `static` or `dynamic`. By default, - * dependencies that don't contain an `import` key are considered static. - * - * @type string $id The script module identifier. - * @type string $import Optional. Import type. May be either `static` or - * `dynamic`. Defaults to `static`. - * } - * } - * @param string|false|null $version Optional. String specifying the script module version number. Defaults to false. - * It is added to the URL as a query string for cache busting purposes. If $version - * is set to false, the version number is the currently installed WordPress version. - * If $version is set to null, no version is added. - * @param array $args { + * @param string $id The identifier of the script module. Should be unique. It will be used in the + * final import map. + * @param string $src Optional. Full URL of the script module, or path of the script module relative + * to the WordPress root directory. If it is provided and the script module has + * not been registered yet, it will be registered. + * @param array $deps { + * Optional. List of dependencies. + * + * @type string|array ...$0 { + * An array of script module identifiers of the dependencies of this script + * module. The dependencies can be strings or arrays. If they are arrays, + * they need an `id` key with the script module identifier, and can contain + * an `import` key with either `static` or `dynamic`. By default, + * dependencies that don't contain an `import` key are considered static. + * + * @type string $id The script module identifier. + * @type string $import Optional. Import type. May be either `static` or + * `dynamic`. Defaults to `static`. + * } + * } + * @param string|false|null $version Optional. String specifying the script module version number. Defaults to false. + * It is added to the URL as a query string for cache busting purposes. If $version + * is set to false, the version number is the currently installed WordPress version. + * If $version is set to null, no version is added. + * @param array $args { * Optional. An array of additional args. Default empty array. * * @type bool $in_footer Whether to print the script module in the footer. Only relevant to block themes. Default 'false'. Optional. @@ -81,31 +81,31 @@ function wp_register_script_module( string $id, string $src, array $deps = array * @since 6.5.0 * @since 6.9.0 Added the $args parameter. * - * @param string $id The identifier of the script module. Should be unique. It will be used in the - * final import map. - * @param string $src Optional. Full URL of the script module, or path of the script module relative - * to the WordPress root directory. If it is provided and the script module has - * not been registered yet, it will be registered. - * @param array $deps { - * Optional. List of dependencies. - * - * @type string|array ...$0 { - * An array of script module identifiers of the dependencies of this script - * module. The dependencies can be strings or arrays. If they are arrays, - * they need an `id` key with the script module identifier, and can contain - * an `import` key with either `static` or `dynamic`. By default, - * dependencies that don't contain an `import` key are considered static. - * - * @type string $id The script module identifier. - * @type string $import Optional. Import type. May be either `static` or - * `dynamic`. Defaults to `static`. - * } - * } - * @param string|false|null $version Optional. String specifying the script module version number. Defaults to false. - * It is added to the URL as a query string for cache busting purposes. If $version - * is set to false, the version number is the currently installed WordPress version. - * If $version is set to null, no version is added. - * @param array $args { + * @param string $id The identifier of the script module. Should be unique. It will be used in the + * final import map. + * @param string $src Optional. Full URL of the script module, or path of the script module relative + * to the WordPress root directory. If it is provided and the script module has + * not been registered yet, it will be registered. + * @param array $deps { + * Optional. List of dependencies. + * + * @type string|array ...$0 { + * An array of script module identifiers of the dependencies of this script + * module. The dependencies can be strings or arrays. If they are arrays, + * they need an `id` key with the script module identifier, and can contain + * an `import` key with either `static` or `dynamic`. By default, + * dependencies that don't contain an `import` key are considered static. + * + * @type string $id The script module identifier. + * @type string $import Optional. Import type. May be either `static` or + * `dynamic`. Defaults to `static`. + * } + * } + * @param string|false|null $version Optional. String specifying the script module version number. Defaults to false. + * It is added to the URL as a query string for cache busting purposes. If $version + * is set to false, the version number is the currently installed WordPress version. + * If $version is set to null, no version is added. + * @param array $args { * Optional. An array of additional args. Default empty array. * * @type bool $in_footer Whether to print the script module in the footer. Only relevant to block themes. Default 'false'. Optional. From 3e553907a67168fdf1ca481dec82c003c3d112ff Mon Sep 17 00:00:00 2001 From: Jorge Costa Date: Tue, 9 Dec 2025 18:32:27 +0000 Subject: [PATCH 018/126] Add: Unit test to validate core abilities schemas only include valid properties. On https://github.com/WordPress/wordpress-develop/pull/10508 we fixed an issue where some core abilties used invalid schema-04 properties. This commit adds a unit test to make all the properties used are valid, so the same issue does not happen in the future. Props jorgefilipecosta, westonruter. Fixes: #64384 git-svn-id: https://develop.svn.wordpress.org/trunk@61363 602fd350-edb4-49c9-b593-d223f7449a82 --- .../abilities-api/wpRegisterCoreAbilities.php | 89 +++++++++++++++++++ 1 file changed, 89 insertions(+) diff --git a/tests/phpunit/tests/abilities-api/wpRegisterCoreAbilities.php b/tests/phpunit/tests/abilities-api/wpRegisterCoreAbilities.php index c89d6daf32cd6..48cae6efd1dee 100644 --- a/tests/phpunit/tests/abilities-api/wpRegisterCoreAbilities.php +++ b/tests/phpunit/tests/abilities-api/wpRegisterCoreAbilities.php @@ -174,4 +174,93 @@ public function test_core_get_environment_info_executes(): void { $this->assertArrayHasKey( 'wp_version', $ability_data ); $this->assertSame( $environment, $ability_data['environment'] ); } + + /** + * Tests that all core ability schemas only use valid JSON Schema keywords. + * + * This prevents regressions where invalid keywords like 'examples' are used + * in schema properties (not valid in JSON Schema draft-04 used by WordPress). + * + * @ticket 64384 + */ + public function test_core_abilities_schemas_use_only_valid_keywords(): void { + $allowed_keywords = rest_get_allowed_schema_keywords(); + // Add 'required' which is valid at the property level for draft-04. + $allowed_keywords[] = 'required'; + + $abilities = wp_get_abilities(); + + $this->assertNotEmpty( $abilities, 'Core abilities should be registered.' ); + + foreach ( $abilities as $ability ) { + $this->assert_schema_uses_valid_keywords( + $ability->get_input_schema(), + $allowed_keywords, + $ability->get_name() . ' input_schema' + ); + $this->assert_schema_uses_valid_keywords( + $ability->get_output_schema(), + $allowed_keywords, + $ability->get_name() . ' output_schema' + ); + } + } + + /** + * Recursively validates that a schema only uses allowed keywords. + * + * @param array|null $schema The schema to validate. + * @param string[] $allowed_keywords List of allowed schema keywords. + * @param string $context Context for error messages. + */ + private function assert_schema_uses_valid_keywords( ?array $schema, array $allowed_keywords, string $context ): void { + if ( null === $schema ) { + return; + } + + foreach ( $schema as $key => $value ) { + // Skip integer keys (array indices). + if ( is_int( $key ) ) { + continue; + } + + // These keywords contain nested schemas that we recurse into. + $nesting_keywords = array( 'properties', 'items', 'additionalProperties', 'patternProperties', 'anyOf', 'oneOf' ); + + if ( ! in_array( $key, $nesting_keywords, true ) && ! in_array( $key, $allowed_keywords, true ) ) { + $this->fail( "Invalid schema keyword '{$key}' found in {$context}. Valid keywords are: " . implode( ', ', $allowed_keywords ) ); + } + + // Recursively check nested schemas. + if ( 'properties' === $key && is_array( $value ) ) { + foreach ( $value as $prop_name => $prop_schema ) { + $this->assert_schema_uses_valid_keywords( + $prop_schema, + $allowed_keywords, + "{$context}.properties.{$prop_name}" + ); + } + } elseif ( 'items' === $key && is_array( $value ) ) { + $this->assert_schema_uses_valid_keywords( + $value, + $allowed_keywords, + "{$context}.items" + ); + } elseif ( ( 'anyOf' === $key || 'oneOf' === $key ) && is_array( $value ) ) { + foreach ( $value as $index => $sub_schema ) { + $this->assert_schema_uses_valid_keywords( + $sub_schema, + $allowed_keywords, + "{$context}.{$key}[{$index}]" + ); + } + } elseif ( 'additionalProperties' === $key && is_array( $value ) ) { + $this->assert_schema_uses_valid_keywords( + $value, + $allowed_keywords, + "{$context}.additionalProperties" + ); + } + } + } } From 7bad2f3ee1facf65993c5b91419229e563405629 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Tue, 9 Dec 2025 22:02:19 +0000 Subject: [PATCH 019/126] Tests: Use `assertSame()` in some newly introduced tests. This ensures that not only the return values match the expected results, but also that their type is the same. Going forward, stricter type checking by using `assertSame()` should generally be preferred to `assertEquals()` where appropriate, to make the tests more reliable. Follow-up to [61032]. See #64324. git-svn-id: https://develop.svn.wordpress.org/trunk@61364 602fd350-edb4-49c9-b593-d223f7449a82 --- tests/phpunit/tests/abilities-api/wpAbilitiesRegistry.php | 4 ++-- tests/phpunit/tests/abilities-api/wpRegisterAbility.php | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/phpunit/tests/abilities-api/wpAbilitiesRegistry.php b/tests/phpunit/tests/abilities-api/wpAbilitiesRegistry.php index badd81c3b626a..319063196d0c5 100644 --- a/tests/phpunit/tests/abilities-api/wpAbilitiesRegistry.php +++ b/tests/phpunit/tests/abilities-api/wpAbilitiesRegistry.php @@ -468,7 +468,7 @@ public function test_get_registered_for_known_ability() { $this->registry->register( 'test/three', self::$test_ability_args ); $result = $this->registry->get_registered( 'test/two' ); - $this->assertEquals( 'test/two', $result->get_name() ); + $this->assertSame( 'test/two', $result->get_name() ); } /** @@ -499,7 +499,7 @@ public function test_unregister_for_known_ability() { $this->registry->register( 'test/three', self::$test_ability_args ); $result = $this->registry->unregister( 'test/three' ); - $this->assertEquals( 'test/three', $result->get_name() ); + $this->assertSame( 'test/three', $result->get_name() ); $this->assertFalse( $this->registry->is_registered( 'test/three' ) ); } diff --git a/tests/phpunit/tests/abilities-api/wpRegisterAbility.php b/tests/phpunit/tests/abilities-api/wpRegisterAbility.php index 91a8aaf237a84..d07de062e12b2 100644 --- a/tests/phpunit/tests/abilities-api/wpRegisterAbility.php +++ b/tests/phpunit/tests/abilities-api/wpRegisterAbility.php @@ -253,7 +253,7 @@ public function test_register_ability_no_permissions(): void { $actual, 'Execution should fail due to no permissions' ); - $this->assertEquals( 'ability_invalid_permissions', $actual->get_error_code() ); + $this->assertSame( 'ability_invalid_permissions', $actual->get_error_code() ); } /** From 0dbba7d06afc231805d5d608531a3837bfbfa67e Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Tue, 9 Dec 2025 22:41:51 +0000 Subject: [PATCH 020/126] Networks and Sites: Ensure the Site Address field renders in correct order when RTL locale is active. Developed in https://github.com/WordPress/wordpress-develop/pull/10612 Props geminorum, johnjamesjacoby, westonruter. See #49949. Fixes #64381. git-svn-id: https://develop.svn.wordpress.org/trunk@61365 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/network/site-new.php | 23 ++++++++++++----------- 1 file changed, 12 insertions(+), 11 deletions(-) diff --git a/src/wp-admin/network/site-new.php b/src/wp-admin/network/site-new.php index d1b0576113c4c..359af42557ef3 100644 --- a/src/wp-admin/network/site-new.php +++ b/src/wp-admin/network/site-new.php @@ -217,17 +217,18 @@ - - .domain ); ?> - domain . get_network()->path - ?> - - ' . __( 'Only lowercase letters (a-z), numbers, and hyphens are allowed.' ) . '

'; - ?> + + + domain ) ); ?> + + domain . get_network()->path ); ?> + + +

+ +

From ffe878be32de398fa218573c2f125bdd0e23b1e9 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Wed, 10 Dec 2025 23:25:48 +0000 Subject: [PATCH 021/126] Tests: Use `assertSame()` in some newly introduced tests. This ensures that not only the return values match the expected results, but also that their type is the same. Going forward, stricter type checking by using `assertSame()` should generally be preferred to `assertEquals()` where appropriate, to make the tests more reliable. Follow-up to [59132]. See #64324. git-svn-id: https://develop.svn.wordpress.org/trunk@61367 602fd350-edb4-49c9-b593-d223f7449a82 --- ...isterBlockTypeFromMetadataWithRegistry.php | 24 +++++++++---------- 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/tests/phpunit/tests/blocks/registerBlockTypeFromMetadataWithRegistry.php b/tests/phpunit/tests/blocks/registerBlockTypeFromMetadataWithRegistry.php index b778a3fb5c838..4cadfa91a33bd 100644 --- a/tests/phpunit/tests/blocks/registerBlockTypeFromMetadataWithRegistry.php +++ b/tests/phpunit/tests/blocks/registerBlockTypeFromMetadataWithRegistry.php @@ -44,12 +44,12 @@ public function test_register_block_type_from_metadata_with_registry() { // Assert that the block was registered successfully $this->assertInstanceOf( 'WP_Block_Type', $registered_block ); - $this->assertEquals( 'test-suite/test-block', $registered_block->name ); - $this->assertEquals( 'Custom Test Block', $registered_block->title ); - $this->assertEquals( 'widgets', $registered_block->category ); - $this->assertEquals( 'smiley', $registered_block->icon ); - $this->assertEquals( 'A test block registered via WP_Block_Metadata_Registry', $registered_block->description ); - $this->assertEquals( array( 'html' => false ), $registered_block->supports ); + $this->assertSame( 'test-suite/test-block', $registered_block->name ); + $this->assertSame( 'Custom Test Block', $registered_block->title ); + $this->assertSame( 'widgets', $registered_block->category ); + $this->assertSame( 'smiley', $registered_block->icon ); + $this->assertSame( 'A test block registered via WP_Block_Metadata_Registry', $registered_block->description ); + $this->assertSame( array( 'html' => false ), $registered_block->supports ); } public function test_register_block_type_from_metadata_with_registry_and_override() { @@ -83,12 +83,12 @@ public function test_register_block_type_from_metadata_with_registry_and_overrid // Assert that the block was registered successfully with overrides $this->assertInstanceOf( 'WP_Block_Type', $registered_block ); - $this->assertEquals( 'test-suite/test-block', $registered_block->name ); - $this->assertEquals( 'Overridden Title', $registered_block->title ); - $this->assertEquals( 'widgets', $registered_block->category ); - $this->assertEquals( 'smiley', $registered_block->icon ); - $this->assertEquals( 'A test block registered via WP_Block_Metadata_Registry', $registered_block->description ); - $this->assertEquals( array( 'html' => true ), $registered_block->supports ); + $this->assertSame( 'test-suite/test-block', $registered_block->name ); + $this->assertSame( 'Overridden Title', $registered_block->title ); + $this->assertSame( 'widgets', $registered_block->category ); + $this->assertSame( 'smiley', $registered_block->icon ); + $this->assertSame( 'A test block registered via WP_Block_Metadata_Registry', $registered_block->description ); + $this->assertSame( array( 'html' => true ), $registered_block->supports ); } private function unregister_test_blocks() { From 7b0a402a4ab89023c5146e8dd063e42985e37b0a Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Thu, 11 Dec 2025 00:45:50 +0000 Subject: [PATCH 022/126] I18N: Add missing translation functions for REST API app login. Developed in https://github.com/WordPress/wordpress-develop/pull/10578 Follow-up to [49110], [49109]. Props geminorum. See #42790. Fixes #64331. git-svn-id: https://develop.svn.wordpress.org/trunk@61368 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-login.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/wp-login.php b/src/wp-login.php index 60d9c21f3ddf1..429032a43a402 100644 --- a/src/wp-login.php +++ b/src/wp-login.php @@ -1462,10 +1462,10 @@ function wp_login_viewport_meta() { if ( ! empty( $query['app_name'] ) ) { /* translators: 1: Website name, 2: Application name. */ - $message = sprintf( 'Please log in to %1$s to authorize %2$s to connect to your account.', get_bloginfo( 'name', 'display' ), '' . esc_html( $query['app_name'] ) . '' ); + $message = sprintf( __( 'Please log in to %1$s to authorize %2$s to connect to your account.' ), get_bloginfo( 'name', 'display' ), '' . esc_html( $query['app_name'] ) . '' ); } else { /* translators: %s: Website name. */ - $message = sprintf( 'Please log in to %s to proceed with authorization.', get_bloginfo( 'name', 'display' ) ); + $message = sprintf( __( 'Please log in to %s to proceed with authorization.' ), get_bloginfo( 'name', 'display' ) ); } $errors->add( 'authorize_application', $message, 'message' ); From 28094f9ed7e53e34534a3b312e4ab9e43955b0de Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Thu, 11 Dec 2025 01:53:26 +0000 Subject: [PATCH 023/126] Export: Update `export_wp()` to handle `get_comment()` returning `null` due to filter. The `get_comment` filter now explicitly documents returning `null` in addition to a `WP_Comment` object. This allows the filter to be used to exclude comments from an export. The `get_comment()` function already supported returning `null`. Developed in https://github.com/WordPress/wordpress-develop/pull/8383 Props abcd95, WPExplorer, desrosj, mukesh27, westonruter, SirLouen, lbones, mdibrahimk48, audrasjb, jorbin, wildworks, hellofromTonya, saurabh.dhariwal, mabfahad. Fixes #61244. git-svn-id: https://develop.svn.wordpress.org/trunk@61369 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/export.php | 7 +++++- src/wp-includes/comment.php | 5 +++- tests/phpunit/tests/admin/exportWp.php | 33 ++++++++++++++++++++++++++ tests/phpunit/tests/comment.php | 16 +++++++++++++ 4 files changed, 59 insertions(+), 2 deletions(-) diff --git a/src/wp-admin/includes/export.php b/src/wp-admin/includes/export.php index 9d5903a98c5c3..4fe697e7e6d4d 100644 --- a/src/wp-admin/includes/export.php +++ b/src/wp-admin/includes/export.php @@ -685,7 +685,12 @@ function wxr_filter_postmeta( $return_me, $meta_key ) { endforeach; $_comments = $wpdb->get_results( $wpdb->prepare( "SELECT * FROM $wpdb->comments WHERE comment_post_ID = %d AND comment_approved <> 'spam'", $post->ID ) ); - $comments = array_map( 'get_comment', $_comments ); + $comments = array_filter( + array_map( 'get_comment', $_comments ), + static function ( $comment ) { + return $comment instanceof WP_Comment; + } + ); foreach ( $comments as $c ) : ?> diff --git a/src/wp-includes/comment.php b/src/wp-includes/comment.php index 7ce49765237a7..bb4abf2cd7f7f 100644 --- a/src/wp-includes/comment.php +++ b/src/wp-includes/comment.php @@ -240,9 +240,12 @@ function get_comment( $comment = null, $output = OBJECT ) { * * @since 2.3.0 * - * @param WP_Comment $_comment Comment data. + * @param WP_Comment|null $_comment Comment data. */ $_comment = apply_filters( 'get_comment', $_comment ); + if ( ! ( $_comment instanceof WP_Comment ) ) { + return null; + } if ( OBJECT === $output ) { return $_comment; diff --git a/tests/phpunit/tests/admin/exportWp.php b/tests/phpunit/tests/admin/exportWp.php index ebb60018c0e7a..059dcab1a8351 100644 --- a/tests/phpunit/tests/admin/exportWp.php +++ b/tests/phpunit/tests/admin/exportWp.php @@ -290,4 +290,37 @@ private function populate_args_post_authors( array &$args, $expected_ids ) { $post_ids_key = $expected_ids[0]; $args['author'] = self::$post_ids[ $post_ids_key ]['post_author']; } + + /** + * @ticket 61244 + */ + public function test_export_wp_should_not_include_empty_comments_when_filtered() { + $post_id = self::factory()->post->create( array( 'post_title' => 'Test Post' ) ); + self::factory()->comment->create_post_comments( $post_id, 3 ); + + // Add filter to make get_comment return null. + add_action( + 'export_wp', + static function () { + add_filter( 'get_comment', '__return_null' ); + } + ); + + $xml_obj = $this->get_the_export( array() ); + $comment_tags = $xml_obj->xpath( '//wp:comment' ); + $this->assertCount( 0, $comment_tags, 'No tags should be present when comments are filtered out.' ); + } + + /** + * @ticket 61244 + */ + public function test_export_wp_includes_comments_when_not_filtered() { + $post_id = self::factory()->post->create( array( 'post_title' => 'Test Post' ) ); + $comment_count = 3; + self::factory()->comment->create_post_comments( $post_id, $comment_count ); + + $xml_obj = $this->get_the_export( array() ); + $comment_tags = $xml_obj->xpath( '//wp:comment' ); + $this->assertCount( $comment_count, $comment_tags, 'Export should include all comments when not filtered.' ); + } } diff --git a/tests/phpunit/tests/comment.php b/tests/phpunit/tests/comment.php index 592ad317003ee..11e78140f1020 100644 --- a/tests/phpunit/tests/comment.php +++ b/tests/phpunit/tests/comment.php @@ -1896,4 +1896,20 @@ public function test_wp_trash_comment_only_top_level_notes_trigger_child_deletio // Verify the sibling note is NOT trashed (no cascade since child is not top-level). $this->assertSame( '1', get_comment( $sibling_note )->comment_approved ); } + + /** + * @ticket 61244 + * + * @covers ::get_comment + */ + public function test_get_comment_filter() { + $comment_id = self::factory()->comment->create( array( 'comment_post_ID' => self::$post_id ) ); + + $comment = get_comment( $comment_id ); + $this->assertInstanceOf( WP_Comment::class, $comment ); + $this->assertSame( $comment_id, (int) $comment->comment_ID, 'Expected the same comment.' ); + + add_filter( 'get_comment', '__return_null' ); + $this->assertNull( get_comment( $comment_id ), 'Expected get_comment() to return null when get_comment filter returns null.' ); + } } From e4afce0fc81a2e50d4d769b3906814bd767d0586 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Thu, 11 Dec 2025 23:47:08 +0000 Subject: [PATCH 024/126] Tests: Use `assertSame()` in some newly introduced tests. This ensures that not only the return values match the expected results, but also that their type is the same. Going forward, stricter type checking by using `assertSame()` should generally be preferred to `assertEquals()` where appropriate, to make the tests more reliable. Follow-up to [60775], [61131]. See #64324. git-svn-id: https://develop.svn.wordpress.org/trunk@61370 602fd350-edb4-49c9-b593-d223f7449a82 --- tests/phpunit/tests/menu/wpAjaxMenuQuickSearch.php | 2 +- tests/phpunit/tests/pluggable/wpMail.php | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/phpunit/tests/menu/wpAjaxMenuQuickSearch.php b/tests/phpunit/tests/menu/wpAjaxMenuQuickSearch.php index f687fc4b069c9..8cdcb2e04aefa 100644 --- a/tests/phpunit/tests/menu/wpAjaxMenuQuickSearch.php +++ b/tests/phpunit/tests/menu/wpAjaxMenuQuickSearch.php @@ -192,6 +192,6 @@ public function test_search_returns_post_types_with_numeric_slugs() { $this->assertCount( 1, $results ); $results_json = array_map( 'json_decode', $results ); - $this->assertEquals( 'wptests_123', $results_json[0]->post_type ); + $this->assertSame( 'wptests_123', $results_json[0]->post_type ); } } diff --git a/tests/phpunit/tests/pluggable/wpMail.php b/tests/phpunit/tests/pluggable/wpMail.php index 785c73eccda6e..c17137269a3f7 100644 --- a/tests/phpunit/tests/pluggable/wpMail.php +++ b/tests/phpunit/tests/pluggable/wpMail.php @@ -666,12 +666,12 @@ public function test_wp_mail_encoding_does_not_bleed() { wp_mail( WP_TESTS_EMAIL, 'Looong line testing', $content ); $mailer = tests_retrieve_phpmailer_instance(); - $this->assertEquals( 'quoted-printable', $mailer->Encoding ); + $this->assertSame( 'quoted-printable', $mailer->Encoding ); wp_mail( WP_TESTS_EMAIL, 'A follow up short email', 'Short email' ); $mailer = tests_retrieve_phpmailer_instance(); - $this->assertEquals( '7bit', $mailer->Encoding ); + $this->assertSame( '7bit', $mailer->Encoding ); } /** From f476ebe8187ce0a8d56396c1e9e9fb1db8e6dbfc Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Fri, 12 Dec 2025 01:13:43 +0000 Subject: [PATCH 025/126] I18N: Use `wp_get_list_item_separator()` as list separator for the states of sites, posts, and media. Developed in https://github.com/WordPress/wordpress-develop/pull/10577 Follow-up to [52929]. Props geminorum. See #39733. Fixes #64330. git-svn-id: https://develop.svn.wordpress.org/trunk@61371 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/class-wp-ms-sites-list-table.php | 5 +++-- src/wp-admin/includes/template.php | 10 ++++++---- 2 files changed, 9 insertions(+), 6 deletions(-) diff --git a/src/wp-admin/includes/class-wp-ms-sites-list-table.php b/src/wp-admin/includes/class-wp-ms-sites-list-table.php index 6097f5e13ecd4..f2df9b43fed1a 100644 --- a/src/wp-admin/includes/class-wp-ms-sites-list-table.php +++ b/src/wp-admin/includes/class-wp-ms-sites-list-table.php @@ -674,6 +674,7 @@ protected function site_states( $site ) { if ( ! empty( $site_states ) ) { $state_count = count( $site_states ); + $separator = wp_get_list_item_separator(); $i = 0; @@ -682,9 +683,9 @@ protected function site_states( $site ) { foreach ( $site_states as $state ) { ++$i; - $separator = ( $i < $state_count ) ? ', ' : ''; + $suffix = ( $i < $state_count ) ? $separator : ''; - echo "{$state}{$separator}"; + echo "{$state}{$suffix}"; } } } diff --git a/src/wp-admin/includes/template.php b/src/wp-admin/includes/template.php index 1c86a2a9d0334..b607e71d75c2c 100644 --- a/src/wp-admin/includes/template.php +++ b/src/wp-admin/includes/template.php @@ -2251,6 +2251,7 @@ function _post_states( $post, $display = true ) { if ( ! empty( $post_states ) ) { $state_count = count( $post_states ); + $separator = wp_get_list_item_separator(); $i = 0; @@ -2259,9 +2260,9 @@ function _post_states( $post, $display = true ) { foreach ( $post_states as $state ) { ++$i; - $separator = ( $i < $state_count ) ? ', ' : ''; + $suffix = ( $i < $state_count ) ? $separator : ''; - $post_states_html .= "{$state}{$separator}"; + $post_states_html .= "{$state}{$suffix}"; } } @@ -2379,6 +2380,7 @@ function _media_states( $post, $display = true ) { if ( ! empty( $media_states ) ) { $state_count = count( $media_states ); + $separator = wp_get_list_item_separator(); $i = 0; @@ -2387,9 +2389,9 @@ function _media_states( $post, $display = true ) { foreach ( $media_states as $state ) { ++$i; - $separator = ( $i < $state_count ) ? ', ' : ''; + $suffix = ( $i < $state_count ) ? $separator : ''; - $media_states_string .= "{$state}{$separator}"; + $media_states_string .= "{$state}{$suffix}"; } } From 7686e78f6c68607af926c7f3695ed2b250bbbb46 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Fri, 12 Dec 2025 05:06:16 +0000 Subject: [PATCH 026/126] Revisions: Prevent fatal error in PHP 8+ when saving a post revision with revisioned non-scalar post meta. Developed in https://github.com/WordPress/wordpress-develop/pull/10560 Follow-up to [56714]. Props LAPSrj, manhphucofficial, westonruter. See #20299. Fixes #64314. git-svn-id: https://develop.svn.wordpress.org/trunk@61372 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/revision.php | 2 +- tests/phpunit/tests/post/revisions.php | 59 ++++++++++++++++++++++++++ 2 files changed, 60 insertions(+), 1 deletion(-) diff --git a/src/wp-includes/revision.php b/src/wp-includes/revision.php index a2267fcbf8f60..f292ad9150c31 100644 --- a/src/wp-includes/revision.php +++ b/src/wp-includes/revision.php @@ -187,7 +187,7 @@ function wp_save_post_revision( $post_id ) { $post_has_changed = false; foreach ( array_keys( _wp_post_revision_fields( $post ) ) as $field ) { - if ( normalize_whitespace( $post->$field ) !== normalize_whitespace( $latest_revision->$field ) ) { + if ( normalize_whitespace( maybe_serialize( $post->$field ) ) !== normalize_whitespace( maybe_serialize( $latest_revision->$field ) ) ) { $post_has_changed = true; break; } diff --git a/tests/phpunit/tests/post/revisions.php b/tests/phpunit/tests/post/revisions.php index 699c10d29ba91..5b6e70b4605bf 100644 --- a/tests/phpunit/tests/post/revisions.php +++ b/tests/phpunit/tests/post/revisions.php @@ -930,4 +930,63 @@ static function ( $revisions ) { 'The title of the second revision was incorrect.' ); } + + /** + * @ticket 64314 + * @covers ::wp_save_post_revision + */ + public function test_wp_save_post_revision_with_array_post_meta() { + // This filter is true by default, but this is explicitly to test looking for differences among non-scalar fields. + add_filter( 'wp_save_post_revision_check_for_changes', '__return_true' ); + + $post_id = self::factory()->post->create(); + $meta_key = 'favorite_things'; + + // Ensure the post meta is saved with each revision. + add_filter( + 'wp_post_revision_meta_keys', + static function ( $meta_keys ) use ( $meta_key ) { + $meta_keys[] = $meta_key; + return $meta_keys; + } + ); + + // Ensure the post meta are used when determining whether a revision should be saved. + add_filter( + '_wp_post_revision_fields', + static function ( $fields ) use ( $meta_key ) { + $fields[ $meta_key ] = 'Favorite Things'; + return $fields; + } + ); + + // Set initial value. + $initial_favorites = array( + 'raindrops on roses', + 'whiskers on kittens', + 'bright copper kettles', + ); + update_post_meta( $post_id, $meta_key, $initial_favorites ); + + // Save the first revision. + $revision_id_1 = wp_save_post_revision( $post_id ); + $this->assertIsInt( $revision_id_1, 'Expected first revision to be created.' ); + $this->assertCount( 1, wp_get_post_revisions( $post_id ), 'First revision should be created.' ); + $this->assertSame( $initial_favorites, get_post_meta( $revision_id_1, $meta_key, true ), 'Expected first revision post meta to have the initial value.' ); + + // Save the second revision. + $updated_favorites = array_merge( + $initial_favorites, + array( + 'warm woolen mittens', + 'crisp apple strudels', + 'brown paper packages tied up with strings', + ) + ); + update_post_meta( $post_id, $meta_key, $updated_favorites ); + $revision_id_2 = wp_save_post_revision( $post_id ); + $this->assertIsInt( $revision_id_2, 'Expected second revision to be created.' ); + $this->assertCount( 2, wp_get_post_revisions( $post_id ), 'Second revision should be created after array field change.' ); + $this->assertSame( $updated_favorites, get_post_meta( $revision_id_2, $meta_key, true ), 'Expected second revision post meta to have the updated value.' ); + } } From 3f829845c3562c5bb023e198d8879a86dc5f6d49 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Fri, 12 Dec 2025 21:36:52 +0000 Subject: [PATCH 027/126] Tests: Use `assertSame()` in some newly introduced tests. This ensures that not only the return values match the expected results, but also that their type is the same. Going forward, stricter type checking by using `assertSame()` should generally be preferred to `assertEquals()` where appropriate, to make the tests more reliable. Follow-up to [61032], [61045]. See #64324. git-svn-id: https://develop.svn.wordpress.org/trunk@61373 602fd350-edb4-49c9-b593-d223f7449a82 --- .../wpRestAbilitiesV1CategoriesController.php | 22 +++++++-------- .../wpRestAbilitiesV1ListController.php | 28 +++++++++---------- .../wpRestAbilitiesV1RunController.php | 20 ++++++------- 3 files changed, 35 insertions(+), 35 deletions(-) diff --git a/tests/phpunit/tests/rest-api/wpRestAbilitiesV1CategoriesController.php b/tests/phpunit/tests/rest-api/wpRestAbilitiesV1CategoriesController.php index 2fa665ed320a9..8a93c7a64047d 100644 --- a/tests/phpunit/tests/rest-api/wpRestAbilitiesV1CategoriesController.php +++ b/tests/phpunit/tests/rest-api/wpRestAbilitiesV1CategoriesController.php @@ -171,9 +171,9 @@ public function test_get_item(): void { $this->assertEquals( 200, $response->get_status() ); $data = $response->get_data(); - $this->assertEquals( 'test-data-retrieval', $data['slug'] ); - $this->assertEquals( 'Data Retrieval', $data['label'] ); - $this->assertEquals( 'Abilities that retrieve and return data from the WordPress site.', $data['description'] ); + $this->assertSame( 'test-data-retrieval', $data['slug'] ); + $this->assertSame( 'Data Retrieval', $data['label'] ); + $this->assertSame( 'Abilities that retrieve and return data from the WordPress site.', $data['description'] ); $this->assertArrayHasKey( 'meta', $data ); } @@ -189,10 +189,10 @@ public function test_get_item_with_meta(): void { $this->assertEquals( 200, $response->get_status() ); $data = $response->get_data(); - $this->assertEquals( 'test-communication', $data['slug'] ); + $this->assertSame( 'test-communication', $data['slug'] ); $this->assertArrayHasKey( 'meta', $data ); $this->assertIsArray( $data['meta'] ); - $this->assertEquals( 'high', $data['meta']['priority'] ); + $this->assertSame( 'high', $data['meta']['priority'] ); } /** @@ -212,8 +212,8 @@ public function test_get_item_with_selected_fields(): void { $data = $response->get_data(); $this->assertCount( 2, $data, 'Response should only contain the requested fields.' ); - $this->assertEquals( 'test-data-retrieval', $data['slug'] ); - $this->assertEquals( 'Data Retrieval', $data['label'] ); + $this->assertSame( 'test-data-retrieval', $data['slug'] ); + $this->assertSame( 'Data Retrieval', $data['label'] ); } /** @@ -230,7 +230,7 @@ public function test_get_item_not_found(): void { $this->assertEquals( 404, $response->get_status() ); $data = $response->get_data(); - $this->assertEquals( 'rest_ability_category_not_found', $data['code'] ); + $this->assertSame( 'rest_ability_category_not_found', $data['code'] ); } /** @@ -424,8 +424,8 @@ public function test_get_schema(): void { $this->assertArrayHasKey( 'schema', $data ); $schema = $data['schema']; - $this->assertEquals( 'ability-category', $schema['title'] ); - $this->assertEquals( 'object', $schema['type'] ); + $this->assertSame( 'ability-category', $schema['title'] ); + $this->assertSame( 'object', $schema['type'] ); $this->assertArrayHasKey( 'properties', $schema ); $properties = $schema['properties']; @@ -438,7 +438,7 @@ public function test_get_schema(): void { $this->assertArrayHasKey( 'meta', $properties ); $slug_property = $properties['slug']; - $this->assertEquals( 'string', $slug_property['type'] ); + $this->assertSame( 'string', $slug_property['type'] ); $this->assertTrue( $slug_property['readonly'] ); } diff --git a/tests/phpunit/tests/rest-api/wpRestAbilitiesV1ListController.php b/tests/phpunit/tests/rest-api/wpRestAbilitiesV1ListController.php index 19e3522f01a9f..e64965242dc98 100644 --- a/tests/phpunit/tests/rest-api/wpRestAbilitiesV1ListController.php +++ b/tests/phpunit/tests/rest-api/wpRestAbilitiesV1ListController.php @@ -307,10 +307,10 @@ public function test_get_item(): void { $data = $response->get_data(); $this->assertCount( 7, $data, 'Response should contain all fields.' ); - $this->assertEquals( 'test/calculator', $data['name'] ); - $this->assertEquals( 'Calculator', $data['label'] ); - $this->assertEquals( 'Performs basic calculations', $data['description'] ); - $this->assertEquals( 'math', $data['category'] ); + $this->assertSame( 'test/calculator', $data['name'] ); + $this->assertSame( 'Calculator', $data['label'] ); + $this->assertSame( 'Performs basic calculations', $data['description'] ); + $this->assertSame( 'math', $data['category'] ); $this->assertArrayHasKey( 'input_schema', $data ); $this->assertArrayHasKey( 'output_schema', $data ); $this->assertArrayHasKey( 'meta', $data ); @@ -334,8 +334,8 @@ public function test_get_item_with_selected_fields(): void { $data = $response->get_data(); $this->assertCount( 2, $data, 'Response should only contain the requested fields.' ); - $this->assertEquals( 'test/calculator', $data['name'] ); - $this->assertEquals( 'Calculator', $data['label'] ); + $this->assertSame( 'test/calculator', $data['name'] ); + $this->assertSame( 'Calculator', $data['label'] ); } /** @@ -355,9 +355,9 @@ public function test_get_item_with_embed_context(): void { $data = $response->get_data(); $this->assertCount( 3, $data, 'Response should only contain the fields for embed context.' ); - $this->assertEquals( 'test/calculator', $data['name'] ); - $this->assertEquals( 'Calculator', $data['label'] ); - $this->assertEquals( 'math', $data['category'] ); + $this->assertSame( 'test/calculator', $data['name'] ); + $this->assertSame( 'Calculator', $data['label'] ); + $this->assertSame( 'math', $data['category'] ); } /** @@ -374,7 +374,7 @@ public function test_get_item_not_found(): void { $this->assertEquals( 404, $response->get_status() ); $data = $response->get_data(); - $this->assertEquals( 'rest_ability_not_found', $data['code'] ); + $this->assertSame( 'rest_ability_not_found', $data['code'] ); } /** @@ -389,7 +389,7 @@ public function test_get_item_not_show_in_rest(): void { $this->assertEquals( 404, $response->get_status() ); $data = $response->get_data(); - $this->assertEquals( 'rest_ability_not_found', $data['code'] ); + $this->assertSame( 'rest_ability_not_found', $data['code'] ); } /** @@ -581,8 +581,8 @@ public function test_get_schema(): void { $this->assertArrayHasKey( 'schema', $data ); $schema = $data['schema']; - $this->assertEquals( 'ability', $schema['title'] ); - $this->assertEquals( 'object', $schema['type'] ); + $this->assertSame( 'ability', $schema['title'] ); + $this->assertSame( 'object', $schema['type'] ); $this->assertArrayHasKey( 'properties', $schema ); $properties = $schema['properties']; @@ -745,7 +745,7 @@ public function test_filter_by_category(): void { // Should only have math category abilities foreach ( $data as $ability ) { - $this->assertEquals( 'math', $ability['category'], 'All abilities should be in math category' ); + $this->assertSame( 'math', $ability['category'], 'All abilities should be in math category' ); } // Should at least contain the calculator diff --git a/tests/phpunit/tests/rest-api/wpRestAbilitiesV1RunController.php b/tests/phpunit/tests/rest-api/wpRestAbilitiesV1RunController.php index f4340f85fad81..bccc30c2f2e94 100644 --- a/tests/phpunit/tests/rest-api/wpRestAbilitiesV1RunController.php +++ b/tests/phpunit/tests/rest-api/wpRestAbilitiesV1RunController.php @@ -472,7 +472,7 @@ public function test_execute_destructive_ability_delete(): void { $response = $this->server->dispatch( $request ); $this->assertEquals( 200, $response->get_status() ); - $this->assertEquals( 'User successfully deleted!', $response->get_data() ); + $this->assertSame( 'User successfully deleted!', $response->get_data() ); } /** @@ -630,7 +630,7 @@ public function test_contextual_permission_check(): void { $response = $this->server->dispatch( $request ); $this->assertEquals( 200, $response->get_status() ); - $this->assertEquals( 'Success: test data', $response->get_data() ); + $this->assertSame( 'Success: test data', $response->get_data() ); } /** @@ -646,8 +646,8 @@ public function test_do_not_show_in_rest(): void { $this->assertEquals( 404, $response->get_status() ); $data = $response->get_data(); - $this->assertEquals( 'rest_ability_not_found', $data['code'] ); - $this->assertEquals( 'Ability not found.', $data['message'] ); + $this->assertSame( 'rest_ability_not_found', $data['code'] ); + $this->assertSame( 'Ability not found.', $data['message'] ); } /** @@ -679,8 +679,8 @@ public function test_wp_error_return_handling(): void { $this->assertEquals( 500, $response->get_status() ); $data = $response->get_data(); - $this->assertEquals( 'test_error', $data['code'] ); - $this->assertEquals( 'This is a test error', $data['message'] ); + $this->assertSame( 'test_error', $data['code'] ); + $this->assertSame( 'This is a test error', $data['message'] ); } /** @@ -698,7 +698,7 @@ public function test_execute_non_existent_ability(): void { $this->assertEquals( 404, $response->get_status() ); $data = $response->get_data(); - $this->assertEquals( 'rest_ability_not_found', $data['code'] ); + $this->assertSame( 'rest_ability_not_found', $data['code'] ); } /** @@ -714,8 +714,8 @@ public function test_run_endpoint_schema(): void { $this->assertArrayHasKey( 'schema', $data ); $schema = $data['schema']; - $this->assertEquals( 'ability-execution', $schema['title'] ); - $this->assertEquals( 'object', $schema['type'] ); + $this->assertSame( 'ability-execution', $schema['title'] ); + $this->assertSame( 'object', $schema['type'] ); $this->assertArrayHasKey( 'properties', $schema ); $this->assertArrayHasKey( 'result', $schema['properties'] ); } @@ -761,7 +761,7 @@ public function test_get_request_with_nested_input_array(): void { $this->assertEquals( 200, $response->get_status() ); $data = $response->get_data(); - $this->assertEquals( 'nested', $data['level1']['level2']['value'] ); + $this->assertSame( 'nested', $data['level1']['level2']['value'] ); $this->assertEquals( array( 1, 2, 3 ), $data['array'] ); } From fbcb7ec7dc422574a2ffa8a8310ca69c02d1ed59 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Sat, 13 Dec 2025 20:10:50 +0000 Subject: [PATCH 028/126] Filesystem API: Pass correct `$file` value to `pre_unzip_file` and `unzip_file` filters. This commit ensures that the original `$file` argument passed to the function is not unintentionally overwritten by the use of the same variable name in two `foreach` loops. Follow-up to [56689]. Props sanchothefat, westonruter, mukesh27, SergeyBiryukov. Fixes #64398. git-svn-id: https://develop.svn.wordpress.org/trunk@61374 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/file.php | 22 +++++++++---------- .../tests/filesystem/unzipFilePclzip.php | 10 +++++---- 2 files changed, 17 insertions(+), 15 deletions(-) diff --git a/src/wp-admin/includes/file.php b/src/wp-admin/includes/file.php index 0658662126a59..948cb8e88e86d 100644 --- a/src/wp-admin/includes/file.php +++ b/src/wp-admin/includes/file.php @@ -1896,14 +1896,14 @@ function _unzip_file_pclzip( $file, $to, $needed_dirs = array() ) { $uncompressed_size = 0; // Determine any children directories needed (From within the archive). - foreach ( $archive_files as $file ) { - if ( str_starts_with( $file['filename'], '__MACOSX/' ) ) { // Skip the OS X-created __MACOSX directory. + foreach ( $archive_files as $archive_file ) { + if ( str_starts_with( $archive_file['filename'], '__MACOSX/' ) ) { // Skip the OS X-created __MACOSX directory. continue; } - $uncompressed_size += $file['size']; + $uncompressed_size += $archive_file['size']; - $needed_dirs[] = $to . untrailingslashit( $file['folder'] ? $file['filename'] : dirname( $file['filename'] ) ); + $needed_dirs[] = $to . untrailingslashit( $archive_file['folder'] ? $archive_file['filename'] : dirname( $archive_file['filename'] ) ); } // Enough space to unzip the file and copy its contents, with a 10% buffer. @@ -1967,22 +1967,22 @@ function _unzip_file_pclzip( $file, $to, $needed_dirs = array() ) { } // Extract the files from the zip. - foreach ( $archive_files as $file ) { - if ( $file['folder'] ) { + foreach ( $archive_files as $archive_file ) { + if ( $archive_file['folder'] ) { continue; } - - if ( str_starts_with( $file['filename'], '__MACOSX/' ) ) { // Don't extract the OS X-created __MACOSX directory files. + + if ( str_starts_with( $archive_file['filename'], '__MACOSX/' ) ) { // Don't extract the OS X-created __MACOSX directory files. continue; } // Don't extract invalid files: - if ( 0 !== validate_file( $file['filename'] ) ) { + if ( 0 !== validate_file( $archive_file['filename'] ) ) { continue; } - if ( ! $wp_filesystem->put_contents( $to . $file['filename'], $file['content'], FS_CHMOD_FILE ) ) { - return new WP_Error( 'copy_failed_pclzip', __( 'Could not copy file.' ), $file['filename'] ); + if ( ! $wp_filesystem->put_contents( $to . $archive_file['filename'], $archive_file['content'], FS_CHMOD_FILE ) ) { + return new WP_Error( 'copy_failed_pclzip', __( 'Could not copy file.' ), $archive_file['filename'] ); } } diff --git a/tests/phpunit/tests/filesystem/unzipFilePclzip.php b/tests/phpunit/tests/filesystem/unzipFilePclzip.php index a53ce50a0df75..10e4b1082a794 100644 --- a/tests/phpunit/tests/filesystem/unzipFilePclzip.php +++ b/tests/phpunit/tests/filesystem/unzipFilePclzip.php @@ -37,7 +37,7 @@ public static function set_up_before_class() { */ public function test_should_apply_pre_unzip_file_filters() { $filter = new MockAction(); - add_filter( 'pre_unzip_file', array( $filter, 'filter' ) ); + add_filter( 'pre_unzip_file', array( $filter, 'filter' ), 10, 2 ); // Prepare test environment. $unzip_destination = self::$test_data_dir . 'archive/'; @@ -53,7 +53,8 @@ public function test_should_apply_pre_unzip_file_filters() { $this->rmdir( $unzip_destination ); $this->delete_folders( $unzip_destination ); - $this->assertSame( 1, $filter->get_call_count() ); + $this->assertSame( 1, $filter->get_call_count(), 'The filter should be called once.' ); + $this->assertSame( self::$test_data_dir . 'archive.zip', $filter->get_args()[0][1], 'The $file parameter should be correct.' ); } /** @@ -63,7 +64,7 @@ public function test_should_apply_pre_unzip_file_filters() { */ public function test_should_apply_unzip_file_filters() { $filter = new MockAction(); - add_filter( 'unzip_file', array( $filter, 'filter' ) ); + add_filter( 'unzip_file', array( $filter, 'filter' ), 10, 2 ); // Prepare test environment. $unzip_destination = self::$test_data_dir . 'archive/'; @@ -79,6 +80,7 @@ public function test_should_apply_unzip_file_filters() { $this->rmdir( $unzip_destination ); $this->delete_folders( $unzip_destination ); - $this->assertSame( 1, $filter->get_call_count() ); + $this->assertSame( 1, $filter->get_call_count(), 'The filter should be called once.' ); + $this->assertSame( self::$test_data_dir . 'archive.zip', $filter->get_args()[0][1], 'The $file parameter should be correct.' ); } } From ed47b17625451cb2d02277caa69903391c7fd884 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Sun, 14 Dec 2025 06:57:50 +0000 Subject: [PATCH 029/126] Coding Standards: Remove whitespace at end of line. Fixes PHPCS warning: `Squiz.WhiteSpace.SuperfluousWhitespace.EndLine`. Follow-up to [61374]. See #64398. git-svn-id: https://develop.svn.wordpress.org/trunk@61375 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/file.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/wp-admin/includes/file.php b/src/wp-admin/includes/file.php index 948cb8e88e86d..3627a16d3ecda 100644 --- a/src/wp-admin/includes/file.php +++ b/src/wp-admin/includes/file.php @@ -1971,7 +1971,7 @@ function _unzip_file_pclzip( $file, $to, $needed_dirs = array() ) { if ( $archive_file['folder'] ) { continue; } - + if ( str_starts_with( $archive_file['filename'], '__MACOSX/' ) ) { // Don't extract the OS X-created __MACOSX directory files. continue; } From fcb6f55671db0f1cf3455f91eb12abb02b5843ac Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Sun, 14 Dec 2025 07:11:49 +0000 Subject: [PATCH 030/126] Taxonomy: Avoid type error in `wp_delete_object_term_relationships()` when invalid taxonomy supplied. Developed in https://github.com/WordPress/wordpress-develop/pull/10621 Props owolter, westonruter. Fixes #64406. git-svn-id: https://develop.svn.wordpress.org/trunk@61376 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/taxonomy.php | 4 ++++ .../term/wpDeleteObjectTermRelationships.php | 20 +++++++++++++++++++ 2 files changed, 24 insertions(+) diff --git a/src/wp-includes/taxonomy.php b/src/wp-includes/taxonomy.php index 69f3fe7484c24..c314d474e6734 100644 --- a/src/wp-includes/taxonomy.php +++ b/src/wp-includes/taxonomy.php @@ -1999,6 +1999,10 @@ function wp_delete_object_term_relationships( $object_id, $taxonomies ) { foreach ( (array) $taxonomies as $taxonomy ) { $term_ids = wp_get_object_terms( $object_id, $taxonomy, array( 'fields' => 'ids' ) ); + if ( ! is_array( $term_ids ) ) { + // Skip return value in the case of an error or the 'wp_get_object_terms' filter returning an invalid value. + continue; + } $term_ids = array_map( 'intval', $term_ids ); wp_remove_object_terms( $object_id, $term_ids, $taxonomy ); } diff --git a/tests/phpunit/tests/term/wpDeleteObjectTermRelationships.php b/tests/phpunit/tests/term/wpDeleteObjectTermRelationships.php index e4ee55f46d104..bd97b4de3b0e7 100644 --- a/tests/phpunit/tests/term/wpDeleteObjectTermRelationships.php +++ b/tests/phpunit/tests/term/wpDeleteObjectTermRelationships.php @@ -53,4 +53,24 @@ public function test_array_of_taxonomies() { $this->assertSameSets( array( $t2 ), $terms ); } + + /** + * @ticket 64406 + */ + public function test_delete_when_error() { + $taxonomy_name = 'wptests_tax'; + register_taxonomy( $taxonomy_name, 'post' ); + $term_id = self::factory()->term->create( array( 'taxonomy' => $taxonomy_name ) ); + $object_id = 567; + wp_set_object_terms( $object_id, array( $term_id ), $taxonomy_name ); + + // Confirm the setup. + $terms = wp_get_object_terms( $object_id, array( $taxonomy_name ), array( 'fields' => 'ids' ) ); + $this->assertSame( array( $term_id ), $terms, 'Expected same object terms.' ); + + // Try wp_delete_object_term_relationships() when the taxonomy is invalid (no change expected). + wp_delete_object_term_relationships( $object_id, 'wptests_taxation' ); + $terms = wp_get_object_terms( $object_id, array( $taxonomy_name ), array( 'fields' => 'ids' ) ); + $this->assertSame( array( $term_id ), $terms, 'Expected the object terms to be unchanged.' ); + } } From b4b73eb27903efe699a71dcc27c5ecfe93d215c9 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Sun, 14 Dec 2025 08:10:25 +0000 Subject: [PATCH 031/126] REST API: Use valid host in unit tests for URL Details endpoint. This ensures that the `url` parameter is not marked as invalid due to `wp_http_validate_url()` failing because of a `gethostbyname()` failure. Follow-up to [51973]. Props westonruter, swissspidy. See #54358. Fixes #64412. git-svn-id: https://develop.svn.wordpress.org/trunk@61377 602fd350-edb4-49c9-b593-d223f7449a82 --- .../tests/rest-api/wpRestUrlDetailsController.php | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/tests/phpunit/tests/rest-api/wpRestUrlDetailsController.php b/tests/phpunit/tests/rest-api/wpRestUrlDetailsController.php index 57ecccd7bf42d..7187d1696c05a 100644 --- a/tests/phpunit/tests/rest-api/wpRestUrlDetailsController.php +++ b/tests/phpunit/tests/rest-api/wpRestUrlDetailsController.php @@ -43,11 +43,15 @@ class Tests_REST_WpRestUrlDetailsController extends WP_Test_REST_Controller_Test /** * URL placeholder. * + * Even though the request is being intercepted with a mocked response, it is not fully bypassing the network. The + * REST API endpoint is validating the `url` parameter with `wp_http_validate_url()` which includes a call to + * `gethostbyname()`. So the domain used in the placeholder URL must be valid to ensure it passes a validity check. + * * @since 5.9.0 * * @var string */ - const URL_PLACEHOLDER = 'https://placeholder-site.com'; + const URL_PLACEHOLDER = 'https://example.com'; /** * Array of request args. @@ -129,9 +133,9 @@ public function test_get_items() { $this->assertSame( array( 'title' => 'Example Website — - with encoded content.', - 'icon' => 'https://placeholder-site.com/favicon.ico?querystringaddedfortesting', + 'icon' => 'https://example.com/favicon.ico?querystringaddedfortesting', 'description' => 'Example description text here. Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore.', - 'image' => 'https://placeholder-site.com/images/home/screen-themes.png?3', + 'image' => 'https://example.com/images/home/screen-themes.png?3', ), $data ); @@ -444,7 +448,7 @@ static function ( $response, $url ) { $this->assertSame( 418, $data['status'], 'Response "status" is not 418' ); - $expected = 'Response for URL https://placeholder-site.com altered via rest_prepare_url_details filter'; + $expected = 'Response for URL https://example.com altered via rest_prepare_url_details filter'; $this->assertSame( $expected, $data['response'], 'Response "response" is not "' . $expected . '"' ); } From 70fef6d3daca81a560b7be6ff7a803ac298d9947 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Sun, 14 Dec 2025 22:28:52 +0000 Subject: [PATCH 032/126] Heartbeat: Handle race condition in `wp-auth-check` where `heartbeat-tick` may fire before `DOMContentLoaded`. Developed in https://github.com/WordPress/wordpress-develop/pull/10624 Follow-up to [23805], [50547]. Props westonruter, ArtZ91, siliconforks. See #23295. Fixes #64403. git-svn-id: https://develop.svn.wordpress.org/trunk@61379 602fd350-edb4-49c9-b593-d223f7449a82 --- src/js/_enqueues/lib/auth-check.js | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/src/js/_enqueues/lib/auth-check.js b/src/js/_enqueues/lib/auth-check.js index 44ff15a153410..ff64573639a25 100644 --- a/src/js/_enqueues/lib/auth-check.js +++ b/src/js/_enqueues/lib/auth-check.js @@ -159,12 +159,23 @@ setShowTimeout(); }); }).on( 'heartbeat-tick.wp-auth-check', function( e, data ) { - if ( 'wp-auth-check' in data ) { + if ( ! ( 'wp-auth-check' in data ) ) { + return; + } + + var showOrHide = function () { if ( ! data['wp-auth-check'] && wrap.hasClass( 'hidden' ) && ! tempHidden ) { show(); } else if ( data['wp-auth-check'] && ! wrap.hasClass( 'hidden' ) ) { hide(); } + }; + + // This is necessary due to a race condition where the heartbeat-tick event may fire before DOMContentLoaded. + if ( wrap ) { + showOrHide(); + } else { + $( showOrHide ); } }); From 33b0f7250a01c7e8a0626d6a483fec97dc92db97 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Sun, 14 Dec 2025 23:55:01 +0000 Subject: [PATCH 033/126] Docs: Update `wp_get_media_creation_timestamp()` DocBlock for consistency. Follow-up to [19687], [41746]. See #64224. git-svn-id: https://develop.svn.wordpress.org/trunk@61380 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/media.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/wp-admin/includes/media.php b/src/wp-admin/includes/media.php index 8436bde73b7fa..210539681ad56 100644 --- a/src/wp-admin/includes/media.php +++ b/src/wp-admin/includes/media.php @@ -3769,8 +3769,8 @@ function wp_read_audio_metadata( $file ) { * @link https://github.com/JamesHeinrich/getID3/blob/master/structure.txt * * @param array $metadata The metadata returned by getID3::analyze(). - * @return int|false A UNIX timestamp for the media's creation date if available - * or a boolean FALSE if a timestamp could not be determined. + * @return int|false A Unix timestamp for the media's creation date if available + * or a boolean false if the timestamp could not be determined. */ function wp_get_media_creation_timestamp( $metadata ) { $creation_date = false; From 214ac551f54813c8280bbfb9854615a09c18f73d Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Mon, 15 Dec 2025 23:47:57 +0000 Subject: [PATCH 034/126] Twenty Nineteen: Align font family of Calendar block in editor with the front end. This commit addresses a visual inconsistency in the Twenty Nineteen theme where the Calendar block (`.wp-calendar-table`) displayed a different font family in the block editor compared to the front end. Props rishabhwp, viralsampat, khushipatel15, sabernhardt, arshitrajyaguru97, SirLouen, SergeyBiryukov. Fixes #63331. git-svn-id: https://develop.svn.wordpress.org/trunk@61384 602fd350-edb4-49c9-b593-d223f7449a82 --- .../themes/twentynineteen/style-editor.css | 67 ++++++++++--------- .../themes/twentynineteen/style-editor.scss | 6 ++ 2 files changed, 42 insertions(+), 31 deletions(-) diff --git a/src/wp-content/themes/twentynineteen/style-editor.css b/src/wp-content/themes/twentynineteen/style-editor.css index cbc56e102099c..7602cbe5f8a66 100644 --- a/src/wp-content/themes/twentynineteen/style-editor.css +++ b/src/wp-content/themes/twentynineteen/style-editor.css @@ -36,7 +36,7 @@ h6:lang(ar), figcaption:lang(ar), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(ar), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(ar), .wp-block-file:lang(ar), ul.wp-block-archives li > a:lang(ar), .wp-block-categories li > a:lang(ar), -.wp-block-latest-posts li > a:lang(ar), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ar), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ar), .wp-caption dd:lang(ar), .wp-block-freeform blockquote cite:lang(ar) { +.wp-block-latest-posts li > a:lang(ar), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ar), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ar), .wp-caption dd:lang(ar), .wp-block-freeform blockquote cite:lang(ar), .wp-calendar-table:lang(ar) { font-family: Tahoma, Arial, sans-serif; } @@ -54,7 +54,7 @@ h6:lang(ary), figcaption:lang(ary), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(ary), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(ary), .wp-block-file:lang(ary), ul.wp-block-archives li > a:lang(ary), .wp-block-categories li > a:lang(ary), -.wp-block-latest-posts li > a:lang(ary), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ary), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ary), .wp-caption dd:lang(ary), .wp-block-freeform blockquote cite:lang(ary) { +.wp-block-latest-posts li > a:lang(ary), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ary), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ary), .wp-caption dd:lang(ary), .wp-block-freeform blockquote cite:lang(ary), .wp-calendar-table:lang(ary) { font-family: Tahoma, Arial, sans-serif; } @@ -72,7 +72,7 @@ h6:lang(azb), figcaption:lang(azb), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(azb), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(azb), .wp-block-file:lang(azb), ul.wp-block-archives li > a:lang(azb), .wp-block-categories li > a:lang(azb), -.wp-block-latest-posts li > a:lang(azb), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(azb), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(azb), .wp-caption dd:lang(azb), .wp-block-freeform blockquote cite:lang(azb) { +.wp-block-latest-posts li > a:lang(azb), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(azb), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(azb), .wp-caption dd:lang(azb), .wp-block-freeform blockquote cite:lang(azb), .wp-calendar-table:lang(azb) { font-family: Tahoma, Arial, sans-serif; } @@ -90,7 +90,7 @@ h6:lang(ckb), figcaption:lang(ckb), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(ckb), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(ckb), .wp-block-file:lang(ckb), ul.wp-block-archives li > a:lang(ckb), .wp-block-categories li > a:lang(ckb), -.wp-block-latest-posts li > a:lang(ckb), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ckb), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ckb), .wp-caption dd:lang(ckb), .wp-block-freeform blockquote cite:lang(ckb) { +.wp-block-latest-posts li > a:lang(ckb), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ckb), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ckb), .wp-caption dd:lang(ckb), .wp-block-freeform blockquote cite:lang(ckb), .wp-calendar-table:lang(ckb) { font-family: Tahoma, Arial, sans-serif; } @@ -108,7 +108,7 @@ h6:lang(fa-IR), figcaption:lang(fa-IR), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(fa-IR), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(fa-IR), .wp-block-file:lang(fa-IR), ul.wp-block-archives li > a:lang(fa-IR), .wp-block-categories li > a:lang(fa-IR), -.wp-block-latest-posts li > a:lang(fa-IR), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(fa-IR), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(fa-IR), .wp-caption dd:lang(fa-IR), .wp-block-freeform blockquote cite:lang(fa-IR) { +.wp-block-latest-posts li > a:lang(fa-IR), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(fa-IR), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(fa-IR), .wp-caption dd:lang(fa-IR), .wp-block-freeform blockquote cite:lang(fa-IR), .wp-calendar-table:lang(fa-IR) { font-family: Tahoma, Arial, sans-serif; } @@ -126,7 +126,7 @@ h6:lang(haz), figcaption:lang(haz), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(haz), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(haz), .wp-block-file:lang(haz), ul.wp-block-archives li > a:lang(haz), .wp-block-categories li > a:lang(haz), -.wp-block-latest-posts li > a:lang(haz), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(haz), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(haz), .wp-caption dd:lang(haz), .wp-block-freeform blockquote cite:lang(haz) { +.wp-block-latest-posts li > a:lang(haz), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(haz), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(haz), .wp-caption dd:lang(haz), .wp-block-freeform blockquote cite:lang(haz), .wp-calendar-table:lang(haz) { font-family: Tahoma, Arial, sans-serif; } @@ -144,7 +144,7 @@ h6:lang(ps), figcaption:lang(ps), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(ps), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(ps), .wp-block-file:lang(ps), ul.wp-block-archives li > a:lang(ps), .wp-block-categories li > a:lang(ps), -.wp-block-latest-posts li > a:lang(ps), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ps), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ps), .wp-caption dd:lang(ps), .wp-block-freeform blockquote cite:lang(ps) { +.wp-block-latest-posts li > a:lang(ps), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ps), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ps), .wp-caption dd:lang(ps), .wp-block-freeform blockquote cite:lang(ps), .wp-calendar-table:lang(ps) { font-family: Tahoma, Arial, sans-serif; } @@ -162,7 +162,7 @@ h6:lang(be), figcaption:lang(be), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(be), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(be), .wp-block-file:lang(be), ul.wp-block-archives li > a:lang(be), .wp-block-categories li > a:lang(be), -.wp-block-latest-posts li > a:lang(be), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(be), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(be), .wp-caption dd:lang(be), .wp-block-freeform blockquote cite:lang(be) { +.wp-block-latest-posts li > a:lang(be), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(be), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(be), .wp-caption dd:lang(be), .wp-block-freeform blockquote cite:lang(be), .wp-calendar-table:lang(be) { font-family: "Helvetica Neue", Helvetica, "Segoe UI", Arial, sans-serif; } @@ -180,7 +180,7 @@ h6:lang(bg-BG), figcaption:lang(bg-BG), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(bg-BG), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(bg-BG), .wp-block-file:lang(bg-BG), ul.wp-block-archives li > a:lang(bg-BG), .wp-block-categories li > a:lang(bg-BG), -.wp-block-latest-posts li > a:lang(bg-BG), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(bg-BG), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(bg-BG), .wp-caption dd:lang(bg-BG), .wp-block-freeform blockquote cite:lang(bg-BG) { +.wp-block-latest-posts li > a:lang(bg-BG), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(bg-BG), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(bg-BG), .wp-caption dd:lang(bg-BG), .wp-block-freeform blockquote cite:lang(bg-BG), .wp-calendar-table:lang(bg-BG) { font-family: "Helvetica Neue", Helvetica, "Segoe UI", Arial, sans-serif; } @@ -198,7 +198,7 @@ h6:lang(kk), figcaption:lang(kk), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(kk), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(kk), .wp-block-file:lang(kk), ul.wp-block-archives li > a:lang(kk), .wp-block-categories li > a:lang(kk), -.wp-block-latest-posts li > a:lang(kk), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(kk), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(kk), .wp-caption dd:lang(kk), .wp-block-freeform blockquote cite:lang(kk) { +.wp-block-latest-posts li > a:lang(kk), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(kk), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(kk), .wp-caption dd:lang(kk), .wp-block-freeform blockquote cite:lang(kk), .wp-calendar-table:lang(kk) { font-family: "Helvetica Neue", Helvetica, "Segoe UI", Arial, sans-serif; } @@ -216,7 +216,7 @@ h6:lang(mk-MK), figcaption:lang(mk-MK), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(mk-MK), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(mk-MK), .wp-block-file:lang(mk-MK), ul.wp-block-archives li > a:lang(mk-MK), .wp-block-categories li > a:lang(mk-MK), -.wp-block-latest-posts li > a:lang(mk-MK), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(mk-MK), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(mk-MK), .wp-caption dd:lang(mk-MK), .wp-block-freeform blockquote cite:lang(mk-MK) { +.wp-block-latest-posts li > a:lang(mk-MK), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(mk-MK), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(mk-MK), .wp-caption dd:lang(mk-MK), .wp-block-freeform blockquote cite:lang(mk-MK), .wp-calendar-table:lang(mk-MK) { font-family: "Helvetica Neue", Helvetica, "Segoe UI", Arial, sans-serif; } @@ -234,7 +234,7 @@ h6:lang(mn), figcaption:lang(mn), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(mn), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(mn), .wp-block-file:lang(mn), ul.wp-block-archives li > a:lang(mn), .wp-block-categories li > a:lang(mn), -.wp-block-latest-posts li > a:lang(mn), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(mn), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(mn), .wp-caption dd:lang(mn), .wp-block-freeform blockquote cite:lang(mn) { +.wp-block-latest-posts li > a:lang(mn), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(mn), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(mn), .wp-caption dd:lang(mn), .wp-block-freeform blockquote cite:lang(mn), .wp-calendar-table:lang(mn) { font-family: "Helvetica Neue", Helvetica, "Segoe UI", Arial, sans-serif; } @@ -252,7 +252,7 @@ h6:lang(ru-RU), figcaption:lang(ru-RU), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(ru-RU), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(ru-RU), .wp-block-file:lang(ru-RU), ul.wp-block-archives li > a:lang(ru-RU), .wp-block-categories li > a:lang(ru-RU), -.wp-block-latest-posts li > a:lang(ru-RU), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ru-RU), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ru-RU), .wp-caption dd:lang(ru-RU), .wp-block-freeform blockquote cite:lang(ru-RU) { +.wp-block-latest-posts li > a:lang(ru-RU), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ru-RU), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ru-RU), .wp-caption dd:lang(ru-RU), .wp-block-freeform blockquote cite:lang(ru-RU), .wp-calendar-table:lang(ru-RU) { font-family: "Helvetica Neue", Helvetica, "Segoe UI", Arial, sans-serif; } @@ -270,7 +270,7 @@ h6:lang(sah), figcaption:lang(sah), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(sah), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(sah), .wp-block-file:lang(sah), ul.wp-block-archives li > a:lang(sah), .wp-block-categories li > a:lang(sah), -.wp-block-latest-posts li > a:lang(sah), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(sah), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(sah), .wp-caption dd:lang(sah), .wp-block-freeform blockquote cite:lang(sah) { +.wp-block-latest-posts li > a:lang(sah), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(sah), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(sah), .wp-caption dd:lang(sah), .wp-block-freeform blockquote cite:lang(sah), .wp-calendar-table:lang(sah) { font-family: "Helvetica Neue", Helvetica, "Segoe UI", Arial, sans-serif; } @@ -288,7 +288,7 @@ h6:lang(sr-RS), figcaption:lang(sr-RS), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(sr-RS), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(sr-RS), .wp-block-file:lang(sr-RS), ul.wp-block-archives li > a:lang(sr-RS), .wp-block-categories li > a:lang(sr-RS), -.wp-block-latest-posts li > a:lang(sr-RS), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(sr-RS), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(sr-RS), .wp-caption dd:lang(sr-RS), .wp-block-freeform blockquote cite:lang(sr-RS) { +.wp-block-latest-posts li > a:lang(sr-RS), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(sr-RS), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(sr-RS), .wp-caption dd:lang(sr-RS), .wp-block-freeform blockquote cite:lang(sr-RS), .wp-calendar-table:lang(sr-RS) { font-family: "Helvetica Neue", Helvetica, "Segoe UI", Arial, sans-serif; } @@ -306,7 +306,7 @@ h6:lang(tt-RU), figcaption:lang(tt-RU), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(tt-RU), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(tt-RU), .wp-block-file:lang(tt-RU), ul.wp-block-archives li > a:lang(tt-RU), .wp-block-categories li > a:lang(tt-RU), -.wp-block-latest-posts li > a:lang(tt-RU), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(tt-RU), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(tt-RU), .wp-caption dd:lang(tt-RU), .wp-block-freeform blockquote cite:lang(tt-RU) { +.wp-block-latest-posts li > a:lang(tt-RU), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(tt-RU), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(tt-RU), .wp-caption dd:lang(tt-RU), .wp-block-freeform blockquote cite:lang(tt-RU), .wp-calendar-table:lang(tt-RU) { font-family: "Helvetica Neue", Helvetica, "Segoe UI", Arial, sans-serif; } @@ -324,7 +324,7 @@ h6:lang(uk), figcaption:lang(uk), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(uk), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(uk), .wp-block-file:lang(uk), ul.wp-block-archives li > a:lang(uk), .wp-block-categories li > a:lang(uk), -.wp-block-latest-posts li > a:lang(uk), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(uk), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(uk), .wp-caption dd:lang(uk), .wp-block-freeform blockquote cite:lang(uk) { +.wp-block-latest-posts li > a:lang(uk), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(uk), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(uk), .wp-caption dd:lang(uk), .wp-block-freeform blockquote cite:lang(uk), .wp-calendar-table:lang(uk) { font-family: "Helvetica Neue", Helvetica, "Segoe UI", Arial, sans-serif; } @@ -342,7 +342,7 @@ h6:lang(zh-HK), figcaption:lang(zh-HK), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(zh-HK), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(zh-HK), .wp-block-file:lang(zh-HK), ul.wp-block-archives li > a:lang(zh-HK), .wp-block-categories li > a:lang(zh-HK), -.wp-block-latest-posts li > a:lang(zh-HK), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(zh-HK), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(zh-HK), .wp-caption dd:lang(zh-HK), .wp-block-freeform blockquote cite:lang(zh-HK) { +.wp-block-latest-posts li > a:lang(zh-HK), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(zh-HK), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(zh-HK), .wp-caption dd:lang(zh-HK), .wp-block-freeform blockquote cite:lang(zh-HK), .wp-calendar-table:lang(zh-HK) { font-family: -apple-system, BlinkMacSystemFont, "PingFang HK", "Helvetica Neue", "Microsoft YaHei New", STHeiti Light, sans-serif; } @@ -360,7 +360,7 @@ h6:lang(zh-TW), figcaption:lang(zh-TW), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(zh-TW), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(zh-TW), .wp-block-file:lang(zh-TW), ul.wp-block-archives li > a:lang(zh-TW), .wp-block-categories li > a:lang(zh-TW), -.wp-block-latest-posts li > a:lang(zh-TW), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(zh-TW), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(zh-TW), .wp-caption dd:lang(zh-TW), .wp-block-freeform blockquote cite:lang(zh-TW) { +.wp-block-latest-posts li > a:lang(zh-TW), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(zh-TW), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(zh-TW), .wp-caption dd:lang(zh-TW), .wp-block-freeform blockquote cite:lang(zh-TW), .wp-calendar-table:lang(zh-TW) { font-family: -apple-system, BlinkMacSystemFont, "PingFang TC", "Helvetica Neue", "Microsoft YaHei New", STHeiti Light, sans-serif; } @@ -378,7 +378,7 @@ h6:lang(zh-CN), figcaption:lang(zh-CN), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(zh-CN), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(zh-CN), .wp-block-file:lang(zh-CN), ul.wp-block-archives li > a:lang(zh-CN), .wp-block-categories li > a:lang(zh-CN), -.wp-block-latest-posts li > a:lang(zh-CN), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(zh-CN), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(zh-CN), .wp-caption dd:lang(zh-CN), .wp-block-freeform blockquote cite:lang(zh-CN) { +.wp-block-latest-posts li > a:lang(zh-CN), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(zh-CN), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(zh-CN), .wp-caption dd:lang(zh-CN), .wp-block-freeform blockquote cite:lang(zh-CN), .wp-calendar-table:lang(zh-CN) { font-family: -apple-system, BlinkMacSystemFont, "PingFang SC", "Helvetica Neue", "Microsoft YaHei New", STHeiti Light, sans-serif; } @@ -396,7 +396,7 @@ h6:lang(bn-BD), figcaption:lang(bn-BD), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(bn-BD), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(bn-BD), .wp-block-file:lang(bn-BD), ul.wp-block-archives li > a:lang(bn-BD), .wp-block-categories li > a:lang(bn-BD), -.wp-block-latest-posts li > a:lang(bn-BD), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(bn-BD), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(bn-BD), .wp-caption dd:lang(bn-BD), .wp-block-freeform blockquote cite:lang(bn-BD) { +.wp-block-latest-posts li > a:lang(bn-BD), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(bn-BD), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(bn-BD), .wp-caption dd:lang(bn-BD), .wp-block-freeform blockquote cite:lang(bn-BD), .wp-calendar-table:lang(bn-BD) { font-family: Arial, sans-serif; } @@ -414,7 +414,7 @@ h6:lang(hi-IN), figcaption:lang(hi-IN), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(hi-IN), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(hi-IN), .wp-block-file:lang(hi-IN), ul.wp-block-archives li > a:lang(hi-IN), .wp-block-categories li > a:lang(hi-IN), -.wp-block-latest-posts li > a:lang(hi-IN), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(hi-IN), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(hi-IN), .wp-caption dd:lang(hi-IN), .wp-block-freeform blockquote cite:lang(hi-IN) { +.wp-block-latest-posts li > a:lang(hi-IN), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(hi-IN), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(hi-IN), .wp-caption dd:lang(hi-IN), .wp-block-freeform blockquote cite:lang(hi-IN), .wp-calendar-table:lang(hi-IN) { font-family: Arial, sans-serif; } @@ -432,7 +432,7 @@ h6:lang(mr), figcaption:lang(mr), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(mr), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(mr), .wp-block-file:lang(mr), ul.wp-block-archives li > a:lang(mr), .wp-block-categories li > a:lang(mr), -.wp-block-latest-posts li > a:lang(mr), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(mr), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(mr), .wp-caption dd:lang(mr), .wp-block-freeform blockquote cite:lang(mr) { +.wp-block-latest-posts li > a:lang(mr), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(mr), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(mr), .wp-caption dd:lang(mr), .wp-block-freeform blockquote cite:lang(mr), .wp-calendar-table:lang(mr) { font-family: Arial, sans-serif; } @@ -450,7 +450,7 @@ h6:lang(ne-NP), figcaption:lang(ne-NP), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(ne-NP), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(ne-NP), .wp-block-file:lang(ne-NP), ul.wp-block-archives li > a:lang(ne-NP), .wp-block-categories li > a:lang(ne-NP), -.wp-block-latest-posts li > a:lang(ne-NP), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ne-NP), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ne-NP), .wp-caption dd:lang(ne-NP), .wp-block-freeform blockquote cite:lang(ne-NP) { +.wp-block-latest-posts li > a:lang(ne-NP), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ne-NP), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ne-NP), .wp-caption dd:lang(ne-NP), .wp-block-freeform blockquote cite:lang(ne-NP), .wp-calendar-table:lang(ne-NP) { font-family: Arial, sans-serif; } @@ -468,7 +468,7 @@ h6:lang(el), figcaption:lang(el), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(el), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(el), .wp-block-file:lang(el), ul.wp-block-archives li > a:lang(el), .wp-block-categories li > a:lang(el), -.wp-block-latest-posts li > a:lang(el), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(el), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(el), .wp-caption dd:lang(el), .wp-block-freeform blockquote cite:lang(el) { +.wp-block-latest-posts li > a:lang(el), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(el), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(el), .wp-caption dd:lang(el), .wp-block-freeform blockquote cite:lang(el), .wp-calendar-table:lang(el) { font-family: "Helvetica Neue", Helvetica, Arial, sans-serif; } @@ -486,7 +486,7 @@ h6:lang(gu), figcaption:lang(gu), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(gu), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(gu), .wp-block-file:lang(gu), ul.wp-block-archives li > a:lang(gu), .wp-block-categories li > a:lang(gu), -.wp-block-latest-posts li > a:lang(gu), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(gu), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(gu), .wp-caption dd:lang(gu), .wp-block-freeform blockquote cite:lang(gu) { +.wp-block-latest-posts li > a:lang(gu), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(gu), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(gu), .wp-caption dd:lang(gu), .wp-block-freeform blockquote cite:lang(gu), .wp-calendar-table:lang(gu) { font-family: Arial, sans-serif; } @@ -504,7 +504,7 @@ h6:lang(he-IL), figcaption:lang(he-IL), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(he-IL), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(he-IL), .wp-block-file:lang(he-IL), ul.wp-block-archives li > a:lang(he-IL), .wp-block-categories li > a:lang(he-IL), -.wp-block-latest-posts li > a:lang(he-IL), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(he-IL), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(he-IL), .wp-caption dd:lang(he-IL), .wp-block-freeform blockquote cite:lang(he-IL) { +.wp-block-latest-posts li > a:lang(he-IL), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(he-IL), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(he-IL), .wp-caption dd:lang(he-IL), .wp-block-freeform blockquote cite:lang(he-IL), .wp-calendar-table:lang(he-IL) { font-family: "Arial Hebrew", Arial, sans-serif; } @@ -522,7 +522,7 @@ h6:lang(ja), figcaption:lang(ja), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(ja), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(ja), .wp-block-file:lang(ja), ul.wp-block-archives li > a:lang(ja), .wp-block-categories li > a:lang(ja), -.wp-block-latest-posts li > a:lang(ja), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ja), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ja), .wp-caption dd:lang(ja), .wp-block-freeform blockquote cite:lang(ja) { +.wp-block-latest-posts li > a:lang(ja), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ja), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ja), .wp-caption dd:lang(ja), .wp-block-freeform blockquote cite:lang(ja), .wp-calendar-table:lang(ja) { font-family: -apple-system, BlinkMacSystemFont, "Hiragino Sans", Meiryo, "Helvetica Neue", sans-serif; } @@ -540,7 +540,7 @@ h6:lang(ko-KR), figcaption:lang(ko-KR), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(ko-KR), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(ko-KR), .wp-block-file:lang(ko-KR), ul.wp-block-archives li > a:lang(ko-KR), .wp-block-categories li > a:lang(ko-KR), -.wp-block-latest-posts li > a:lang(ko-KR), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ko-KR), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ko-KR), .wp-caption dd:lang(ko-KR), .wp-block-freeform blockquote cite:lang(ko-KR) { +.wp-block-latest-posts li > a:lang(ko-KR), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(ko-KR), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(ko-KR), .wp-caption dd:lang(ko-KR), .wp-block-freeform blockquote cite:lang(ko-KR), .wp-calendar-table:lang(ko-KR) { font-family: "Apple SD Gothic Neo", "Malgun Gothic", "Nanum Gothic", Dotum, sans-serif; } @@ -558,7 +558,7 @@ h6:lang(th), figcaption:lang(th), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(th), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(th), .wp-block-file:lang(th), ul.wp-block-archives li > a:lang(th), .wp-block-categories li > a:lang(th), -.wp-block-latest-posts li > a:lang(th), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(th), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(th), .wp-caption dd:lang(th), .wp-block-freeform blockquote cite:lang(th) { +.wp-block-latest-posts li > a:lang(th), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(th), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(th), .wp-caption dd:lang(th), .wp-block-freeform blockquote cite:lang(th), .wp-calendar-table:lang(th) { font-family: "Sukhumvit Set", "Helvetica Neue", helvetica, arial, sans-serif; } @@ -576,7 +576,7 @@ h6:lang(vi), figcaption:lang(vi), .wp-block[data-type="core/pullquote"][data-align="left"] .wp-block-pullquote__citation:lang(vi), .wp-block[data-type="core/pullquote"][data-align="right"] .wp-block-pullquote__citation:lang(vi), .wp-block-file:lang(vi), ul.wp-block-archives li > a:lang(vi), .wp-block-categories li > a:lang(vi), -.wp-block-latest-posts li > a:lang(vi), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(vi), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(vi), .wp-caption dd:lang(vi), .wp-block-freeform blockquote cite:lang(vi) { +.wp-block-latest-posts li > a:lang(vi), .wp-block-latest-posts .wp-block-latest-posts__post-date:lang(vi), .wp-block-latest-comments .wp-block-latest-comments__comment-meta:lang(vi), .wp-caption dd:lang(vi), .wp-block-freeform blockquote cite:lang(vi), .wp-calendar-table:lang(vi) { font-family: "Libre Franklin", sans-serif; } @@ -1649,3 +1649,8 @@ ul.wp-block-archives li ul, .wp-block-post-author__avatar img { border-radius: 100%; } + +/** === Calendar Block === */ +.wp-calendar-table { + font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", "Roboto", "Oxygen", "Ubuntu", "Cantarell", "Fira Sans", "Droid Sans", "Helvetica Neue", sans-serif; +} diff --git a/src/wp-content/themes/twentynineteen/style-editor.scss b/src/wp-content/themes/twentynineteen/style-editor.scss index 8af5dddbf5034..fae0662938092 100644 --- a/src/wp-content/themes/twentynineteen/style-editor.scss +++ b/src/wp-content/themes/twentynineteen/style-editor.scss @@ -1095,3 +1095,9 @@ $group-block-background__padding: $font__size_base; .wp-block-post-author__avatar img { border-radius: 100%; } + +/** === Calendar Block === */ + +.wp-calendar-table { + @include font-family( $font__heading ); +} From 0c6af7832c49d8ea057eba9bd5fdb9c38eb1caba Mon Sep 17 00:00:00 2001 From: Aki Hamano Date: Tue, 16 Dec 2025 08:18:21 +0000 Subject: [PATCH 035/126] Customizer: Add admin color scheme class to body element. This changeset injects a CSS class called `admin-color-{slug}` into the `body` element in the Customizer screen based on the admin color scheme setting. Props soyebsalar01, westonruter, wildworks. Fixes #64415. git-svn-id: https://develop.svn.wordpress.org/trunk@61385 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/customize.php | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/wp-admin/customize.php b/src/wp-admin/customize.php index 1fc376f68c008..141fb93dc3198 100644 --- a/src/wp-admin/customize.php +++ b/src/wp-admin/customize.php @@ -147,6 +147,8 @@ $body_class .= ' rtl'; } $body_class .= ' locale-' . sanitize_html_class( strtolower( str_replace( '_', '-', get_user_locale() ) ) ); +$admin_color = get_user_option( 'admin_color' ); +$body_class .= ' admin-color-' . sanitize_html_class( is_string( $admin_color ) ? $admin_color : '', 'fresh' ); if ( wp_use_widgets_block_editor() ) { $body_class .= ' wp-embed-responsive'; From bb8d4a79729a9d4ad214cdd2d49db369c0aab05b Mon Sep 17 00:00:00 2001 From: John Blackbourn Date: Tue, 16 Dec 2025 11:51:05 +0000 Subject: [PATCH 036/126] Mail: Update some docblocks relating to inline email attachments. See #28059, #64224 git-svn-id: https://develop.svn.wordpress.org/trunk@61386 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/pluggable.php | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/src/wp-includes/pluggable.php b/src/wp-includes/pluggable.php index 1d5ee194c9f10..a2a062c70d49f 100644 --- a/src/wp-includes/pluggable.php +++ b/src/wp-includes/pluggable.php @@ -173,7 +173,7 @@ function cache_users( $user_ids ) { * @since 1.2.1 * @since 5.5.0 is_email() is used for email validation, * instead of PHPMailer's default validator. - * @since 6.9.0 Added $embeds parameter. + * @since 6.9.0 The `$embeds` parameter was added. * @since 6.9.0 Improved Content-Type header handling for multipart messages. * * @global PHPMailer\PHPMailer\PHPMailer $phpmailer @@ -193,6 +193,7 @@ function wp_mail( $to, $subject, $message, $headers = '', $attachments = array() * Filters the wp_mail() arguments. * * @since 2.2.0 + * @since 6.9.0 The `$embeds` element was added to the `$args` array. * * @param array $args { * Array of the `wp_mail()` arguments. @@ -215,6 +216,7 @@ function wp_mail( $to, $subject, $message, $headers = '', $attachments = array() * the email was successfully sent. * * @since 5.7.0 + * @since 6.9.0 The `$embeds` element was added to the `$atts` array. * * @param null|bool $return Short-circuit return value. * @param array $atts { @@ -573,7 +575,8 @@ function wp_mail( $to, $subject, $message, $headers = '', $attachments = array() * @since 6.9.0 * * @param array $args { - * An array of arguments for `addEmbeddedImage()`. + * An array of arguments for PHPMailer's addEmbeddedImage() method. + * * @type string $path The path to the file. * @type string $cid The Content-ID of the image. Default: The key in the embeds array. * @type string $name The filename of the image. @@ -632,9 +635,10 @@ function wp_mail( $to, $subject, $message, $headers = '', $attachments = array() * process the request without any errors. * * @since 5.9.0 + * @since 6.9.0 The `$embeds` element was added to the `$mail_data` array. * * @param array $mail_data { - * An array containing the email recipient(s), subject, message, headers, and attachments. + * An array containing the email recipient(s), subject, message, headers, attachments, and embeds. * * @type string[] $to Email addresses to send message. * @type string $subject Email subject. @@ -656,7 +660,7 @@ function wp_mail( $to, $subject, $message, $headers = '', $attachments = array() * @since 4.4.0 * * @param WP_Error $error A WP_Error object with the PHPMailer\PHPMailer\Exception message, and an array - * containing the mail recipient, subject, message, headers, and attachments. + * containing the mail recipient, subject, message, headers, attachments, and embeds. */ do_action( 'wp_mail_failed', new WP_Error( 'wp_mail_failed', $e->getMessage(), $mail_data ) ); From 3f21ada570de5a994b1035cd7d9f41a4beee3ca2 Mon Sep 17 00:00:00 2001 From: John Blackbourn Date: Tue, 16 Dec 2025 20:19:55 +0000 Subject: [PATCH 037/126] Docs: Miscellaneous improvements and corrections to inline documentation. See #64224 git-svn-id: https://develop.svn.wordpress.org/trunk@61387 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/class-wp-upgrader.php | 2 +- src/wp-admin/includes/post.php | 2 +- .../class-wp-customize-setting.php | 2 +- src/wp-includes/class-wp-image-editor.php | 2 +- src/wp-includes/class-wp-query.php | 4 ++-- src/wp-includes/class-wp-user-query.php | 2 +- src/wp-includes/class-wp-user.php | 2 +- src/wp-includes/comment.php | 2 +- src/wp-includes/cron.php | 11 +++++----- src/wp-includes/functions.php | 6 +++--- src/wp-includes/link-template.php | 2 +- src/wp-includes/load.php | 2 +- src/wp-includes/media.php | 10 ++++----- src/wp-includes/option.php | 21 ++++++++++--------- src/wp-includes/pluggable.php | 4 ++-- src/wp-includes/post.php | 6 +++--- src/wp-includes/revision.php | 2 +- src/wp-includes/taxonomy.php | 4 ++-- src/wp-includes/user.php | 4 +++- src/wp-login.php | 4 ++-- 20 files changed, 49 insertions(+), 45 deletions(-) diff --git a/src/wp-admin/includes/class-wp-upgrader.php b/src/wp-admin/includes/class-wp-upgrader.php index d5a430d25a3d4..eeb32b438cee2 100644 --- a/src/wp-admin/includes/class-wp-upgrader.php +++ b/src/wp-admin/includes/class-wp-upgrader.php @@ -590,7 +590,7 @@ public function install_package( $args = array() ) { * Filters the source file location for the upgrade package. * * @since 2.8.0 - * @since 4.4.0 The $hook_extra parameter became available. + * @since 4.4.0 The `$hook_extra` parameter became available. * * @param string $source File source location. * @param string $remote_source Remote file source location. diff --git a/src/wp-admin/includes/post.php b/src/wp-admin/includes/post.php index ab8fb62a7b4f0..fdd873a88899b 100644 --- a/src/wp-admin/includes/post.php +++ b/src/wp-admin/includes/post.php @@ -1894,7 +1894,7 @@ function _admin_notice_post_locked() { * Fires inside the post locked dialog before the buttons are displayed. * * @since 3.6.0 - * @since 5.4.0 The $user parameter was added. + * @since 5.4.0 The `$user` parameter was added. * * @param WP_Post $post Post object. * @param WP_User $user The user with the lock for the post. diff --git a/src/wp-includes/class-wp-customize-setting.php b/src/wp-includes/class-wp-customize-setting.php index 95f6b26972682..de2dbdadeb19c 100644 --- a/src/wp-includes/class-wp-customize-setting.php +++ b/src/wp-includes/class-wp-customize-setting.php @@ -765,7 +765,7 @@ public function value() { * functions for available hooks. * * @since 3.4.0 - * @since 4.6.0 Added the `$this` setting instance as the second parameter. + * @since 4.6.0 Added the `$setting` instance as the second parameter. * * @param mixed $default_value The setting default value. Default empty. * @param WP_Customize_Setting $setting The setting instance. diff --git a/src/wp-includes/class-wp-image-editor.php b/src/wp-includes/class-wp-image-editor.php index 87a9d91f4ffc5..d7fe151a0d94a 100644 --- a/src/wp-includes/class-wp-image-editor.php +++ b/src/wp-includes/class-wp-image-editor.php @@ -255,7 +255,7 @@ public function set_quality( $quality = null, $dims = array() ) { * The WP_Image_Editor::set_quality() method has priority over the filter. * * @since 3.5.0 - * @since 6.8.0 Added the size parameter. + * @since 6.8.0 Added the `$size` parameter. * * @param int $quality Quality level between 1 (low) and 100 (high). * @param string $mime_type Image mime type. diff --git a/src/wp-includes/class-wp-query.php b/src/wp-includes/class-wp-query.php index 07852fc8a5607..d29c5a43758d0 100644 --- a/src/wp-includes/class-wp-query.php +++ b/src/wp-includes/class-wp-query.php @@ -1900,8 +1900,8 @@ public function get_posts() { * Fires after the query variable object is created, but before the actual query is run. * * Note: If using conditional tags, use the method versions within the passed instance - * (e.g. $this->is_main_query() instead of is_main_query()). This is because the functions - * like is_main_query() test against the global $wp_query instance, not the passed one. + * (e.g. `$query->is_main_query()` instead of `is_main_query()`). This is because the functions + * like `is_main_query()` test against the global `$wp_query` instance, not the passed one. * * @since 2.0.0 * diff --git a/src/wp-includes/class-wp-user-query.php b/src/wp-includes/class-wp-user-query.php index 014cfb2ac56d9..d704dc70340bc 100644 --- a/src/wp-includes/class-wp-user-query.php +++ b/src/wp-includes/class-wp-user-query.php @@ -851,7 +851,7 @@ public function query() { * Filters SELECT FOUND_ROWS() query for the current WP_User_Query instance. * * @since 3.2.0 - * @since 5.1.0 Added the `$this` parameter. + * @since 5.1.0 Added the `$query` parameter. * * @global wpdb $wpdb WordPress database abstraction object. * diff --git a/src/wp-includes/class-wp-user.php b/src/wp-includes/class-wp-user.php index 3b039ffb9d8b4..687c910a08076 100644 --- a/src/wp-includes/class-wp-user.php +++ b/src/wp-includes/class-wp-user.php @@ -654,7 +654,7 @@ public function set_role( $role ) { * Fires after the user's role has changed. * * @since 2.9.0 - * @since 3.6.0 Added $old_roles to include an array of the user's previous roles. + * @since 3.6.0 Added `$old_roles` to include an array of the user's previous roles. * * @param int $user_id The user ID. * @param string $role The new role. diff --git a/src/wp-includes/comment.php b/src/wp-includes/comment.php index bb4abf2cd7f7f..03fed10fa23f6 100644 --- a/src/wp-includes/comment.php +++ b/src/wp-includes/comment.php @@ -598,7 +598,7 @@ function wp_set_comment_cookies( $comment, $user, $cookies_consent = true ) { * Filters the lifetime of the comment cookie in seconds. * * @since 2.8.0 - * @since 6.6.0 The default $seconds value changed from 30000000 to YEAR_IN_SECONDS. + * @since 6.6.0 The default `$seconds` value changed from 30000000 to YEAR_IN_SECONDS. * * @param int $seconds Comment cookie lifetime. Default YEAR_IN_SECONDS. */ diff --git a/src/wp-includes/cron.php b/src/wp-includes/cron.php index afea4bce9771f..c6eab59a20e40 100644 --- a/src/wp-includes/cron.php +++ b/src/wp-includes/cron.php @@ -74,7 +74,7 @@ function wp_schedule_single_event( $timestamp, $hook, $args = array(), $wp_error * Return true if the event was scheduled, false or a WP_Error if not. * * @since 5.1.0 - * @since 5.7.0 The `$wp_error` parameter was added, and a `WP_Error` object can now be returned. + * @since 5.7.0 The `$wp_error` parameter was added, and a WP_Error object can now be returned. * * @param null|bool|WP_Error $result The value to return instead. Default null to continue adding the event. * @param object $event { @@ -385,7 +385,7 @@ function wp_reschedule_event( $timestamp, $recurrence, $hook, $args = array(), $ * rescheduled, false or a WP_Error if not. * * @since 5.1.0 - * @since 5.7.0 The `$wp_error` parameter was added, and a `WP_Error` object can now be returned. + * @since 5.7.0 The `$wp_error` parameter was added, and a WP_Error object can now be returned. * * @param null|bool|WP_Error $pre Value to return instead. Default null to continue adding the event. * @param object $event { @@ -482,7 +482,7 @@ function wp_unschedule_event( $timestamp, $hook, $args = array(), $wp_error = fa * unscheduled, false or a WP_Error if not. * * @since 5.1.0 - * @since 5.7.0 The `$wp_error` parameter was added, and a `WP_Error` object can now be returned. + * @since 5.7.0 The `$wp_error` parameter was added, and a WP_Error object can now be returned. * * @param null|bool|WP_Error $pre Value to return instead. Default null to continue unscheduling the event. * @param int $timestamp Unix timestamp (UTC) for when to run the event. @@ -573,7 +573,7 @@ function wp_clear_scheduled_hook( $hook, $args = array(), $wp_error = false ) { * or a WP_Error if unscheduling one or more events fails. * * @since 5.1.0 - * @since 5.7.0 The `$wp_error` parameter was added, and a `WP_Error` object can now be returned. + * @since 5.7.0 The `$wp_error` parameter was added, and a WP_Error object can now be returned. * * @param null|int|false|WP_Error $pre Value to return instead. Default null to continue unscheduling the event. * @param string $hook Action hook, the execution of which will be unscheduled. @@ -664,7 +664,7 @@ function wp_unschedule_hook( $hook, $wp_error = false ) { * on the value of the `$wp_error` parameter. * * @since 5.1.0 - * @since 5.7.0 The `$wp_error` parameter was added, and a `WP_Error` object can now be returned. + * @since 5.7.0 The `$wp_error` parameter was added, and a WP_Error object can now be returned. * * @param null|int|false|WP_Error $pre Value to return instead. Default null to continue unscheduling the hook. * @param string $hook Action hook, the execution of which will be unscheduled. @@ -853,6 +853,7 @@ function wp_next_scheduled( $hook, $args = array() ) { * @type int $interval Optional. The interval time in seconds for the schedule. Only * present for recurring events. * } + * @param string $hook Action hook of the event. * @param array $args Array containing each separate argument to pass to the hook * callback function. */ diff --git a/src/wp-includes/functions.php b/src/wp-includes/functions.php index 68a29f444fd48..ee10bb78e1d37 100644 --- a/src/wp-includes/functions.php +++ b/src/wp-includes/functions.php @@ -3300,7 +3300,7 @@ function wp_check_filetype_and_ext( $file, $filename, $mimes = null ) { * Filters the "real" file type of the given file. * * @since 3.0.0 - * @since 5.1.0 The $real_mime parameter was added. + * @since 5.1.0 The `$real_mime` parameter was added. * * @param array $wp_check_filetype_and_ext { * Values for the extension, mime type, and corrected filename. @@ -3610,7 +3610,7 @@ function wp_get_ext_types() { */ function wp_filesize( $path ) { /** - * Filters the result of wp_filesize before the PHP function is run. + * Filters the result of wp_filesize() before the file_exists() PHP function is run. * * @since 6.0.0 * @@ -6023,7 +6023,7 @@ function _doing_it_wrong( $function_name, $message, $version ) { * Filters whether to trigger an error for _doing_it_wrong() calls. * * @since 3.1.0 - * @since 5.1.0 Added the $function_name, $message and $version parameters. + * @since 5.1.0 Added the `$function_name`, `$message`, and `$version` parameters. * * @param bool $trigger Whether to trigger the error for _doing_it_wrong() calls. Default true. * @param string $function_name The function that was called. diff --git a/src/wp-includes/link-template.php b/src/wp-includes/link-template.php index 1434d87a25fef..d1af2996bc7fb 100644 --- a/src/wp-includes/link-template.php +++ b/src/wp-includes/link-template.php @@ -1625,7 +1625,7 @@ function get_edit_comment_link( $comment_id = 0, $context = 'display' ) { * Filters the comment edit link. * * @since 2.3.0 - * @since 6.7.0 The $comment_id and $context parameters are now being passed to the filter. + * @since 6.7.0 The `$comment_id` and `$context` parameters are now being passed to the filter. * * @param string $location The edit link. * @param int $comment_id Unique ID of the comment to generate an edit link. diff --git a/src/wp-includes/load.php b/src/wp-includes/load.php index 095affd67747a..434d836f67ba9 100644 --- a/src/wp-includes/load.php +++ b/src/wp-includes/load.php @@ -1804,7 +1804,7 @@ function is_wp_error( $thing ) { if ( $is_wp_error ) { /** - * Fires when `is_wp_error()` is called and its parameter is an instance of `WP_Error`. + * Fires when `is_wp_error()` is called and its parameter is an instance of WP_Error. * * @since 5.6.0 * diff --git a/src/wp-includes/media.php b/src/wp-includes/media.php index 229d22b849ec6..5eb72d16c3b5e 100644 --- a/src/wp-includes/media.php +++ b/src/wp-includes/media.php @@ -1618,7 +1618,7 @@ function wp_calculate_image_sizes( $size, $image_src = null, $image_meta = null, $sizes = sprintf( '(max-width: %1$dpx) 100vw, %1$dpx', $width ); /** - * Filters the output of 'wp_calculate_image_sizes()'. + * Filters the output of wp_calculate_image_sizes(). * * @since 4.4.0 * @@ -1742,7 +1742,7 @@ function wp_image_src_get_dimensions( $image_src, $image_meta, $attachment_id = } /** - * Filters the 'wp_image_src_get_dimensions' value. + * Filters the wp_image_src_get_dimensions() value. * * @since 5.7.0 * @@ -2156,7 +2156,7 @@ function wp_img_tag_add_loading_optimization_attrs( $image, $context ) { if ( empty( $decoding_val ) ) { /** - * Filters the `decoding` attribute value to add to an image. Default `async`. + * Filters the `decoding` attribute value to add to an image. Default 'async'. * * Returning a falsey value will omit the attribute. * @@ -2199,7 +2199,7 @@ function wp_img_tag_add_loading_optimization_attrs( $image, $context ) { if ( empty( $loading_val ) && $loading_attrs_enabled ) { /** - * Filters the `loading` attribute value to add to an image. Default `lazy`. + * Filters the `loading` attribute value to add to an image. Default 'lazy'. * * Returning `false` or an empty string will not add the attribute. * Returning `true` will add the default value. @@ -2383,7 +2383,7 @@ function wp_iframe_tag_add_loading_attr( $iframe, $context ) { $value = isset( $optimization_attrs['loading'] ) ? $optimization_attrs['loading'] : false; /** - * Filters the `loading` attribute value to add to an iframe. Default `lazy`. + * Filters the `loading` attribute value to add to an iframe. Default 'lazy'. * * Returning `false` or an empty string will not add the attribute. * Returning `true` will add the default value. diff --git a/src/wp-includes/option.php b/src/wp-includes/option.php index 7cb4736c2840b..735a1c6539085 100644 --- a/src/wp-includes/option.php +++ b/src/wp-includes/option.php @@ -245,7 +245,7 @@ function get_option( $option, $default_value = false ) { * * The dynamic portion of the hook name, `$option`, refers to the option name. * - * @since 1.5.0 As 'option_' . $setting + * @since 1.5.0 As `option_{$setting}`. * @since 3.0.0 * @since 4.4.0 The `$option` parameter was added. * @@ -1325,10 +1325,11 @@ function wp_determine_option_autoload_value( $option, $value, $serialized_value, * * @since 6.6.0 * - * @param bool|null $autoload The default autoload value to set. Returning true will be set as 'auto-on' in the - * database, false will be set as 'auto-off', and null will be set as 'auto'. - * @param string $option The passed option name. - * @param mixed $value The passed option value to be saved. + * @param bool|null $autoload The default autoload value to set. Returning true will be set as 'auto-on' in the + * database, false will be set as 'auto-off', and null will be set as 'auto'. + * @param string $option The passed option name. + * @param mixed $value The passed option value to be saved. + * @param mixed $serialized_value The passed option value to be saved, in serialized form. */ $autoload = apply_filters( 'wp_default_autoload_value', null, $option, $value, $serialized_value ); if ( is_bool( $autoload ) ) { @@ -2020,7 +2021,7 @@ function get_network_option( $network_id, $option, $default_value = false ) { * Returning a value other than false from the filter will short-circuit retrieval * and return that value instead. * - * @since 2.9.0 As 'pre_site_option_' . $key + * @since 2.9.0 As `pre_site_option_{$key}`. * @since 3.0.0 * @since 4.4.0 The `$option` parameter was added. * @since 4.7.0 The `$network_id` parameter was added. @@ -2123,7 +2124,7 @@ function get_network_option( $network_id, $option, $default_value = false ) { * * The dynamic portion of the hook name, `$option`, refers to the option name. * - * @since 2.9.0 As 'site_option_' . $key + * @since 2.9.0 As `site_option_{$key}`. * @since 3.0.0 * @since 4.4.0 The `$option` parameter was added. * @since 4.7.0 The `$network_id` parameter was added. @@ -2172,7 +2173,7 @@ function add_network_option( $network_id, $option, $value ) { * * The dynamic portion of the hook name, `$option`, refers to the option name. * - * @since 2.9.0 As 'pre_add_site_option_' . $key + * @since 2.9.0 As `pre_add_site_option_{$key}`. * @since 3.0.0 * @since 4.4.0 The `$option` parameter was added. * @since 4.7.0 The `$network_id` parameter was added. @@ -2236,7 +2237,7 @@ function add_network_option( $network_id, $option, $value ) { * * The dynamic portion of the hook name, `$option`, refers to the option name. * - * @since 2.9.0 As "add_site_option_{$key}" + * @since 2.9.0 As `add_site_option_{$key}`. * @since 3.0.0 * @since 4.7.0 The `$network_id` parameter was added. * @@ -2342,7 +2343,7 @@ function delete_network_option( $network_id, $option ) { * * The dynamic portion of the hook name, `$option`, refers to the option name. * - * @since 2.9.0 As "delete_site_option_{$key}" + * @since 2.9.0 As `delete_site_option_{$key}`. * @since 3.0.0 * @since 4.7.0 The `$network_id` parameter was added. * diff --git a/src/wp-includes/pluggable.php b/src/wp-includes/pluggable.php index a2a062c70d49f..99c23540d8983 100644 --- a/src/wp-includes/pluggable.php +++ b/src/wp-includes/pluggable.php @@ -655,7 +655,7 @@ function wp_mail( $to, $subject, $message, $headers = '', $attachments = array() $mail_data['phpmailer_exception_code'] = $e->getCode(); /** - * Fires after a PHPMailer\PHPMailer\Exception is caught. + * Fires after a PHPMailer exception is caught. * * @since 4.4.0 * @@ -1520,7 +1520,7 @@ function wp_redirect( $location, $status = 302, $x_redirect_by = 'WordPress' ) { } /** - * Filters the X-Redirect-By header. + * Filters the value of the `X-Redirect-By` HTTP header. * * Allows applications to identify themselves when they're doing a redirect. * diff --git a/src/wp-includes/post.php b/src/wp-includes/post.php index b646a2116cc63..a88d1afd57332 100644 --- a/src/wp-includes/post.php +++ b/src/wp-includes/post.php @@ -1841,7 +1841,7 @@ function register_post_type( $post_type, $args = array() ) { * Fires after a post type is registered. * * @since 3.3.0 - * @since 4.6.0 Converted the `$post_type` parameter to accept a `WP_Post_Type` object. + * @since 4.6.0 Converted the `$post_type` parameter to accept a WP_Post_Type object. * * @param string $post_type Post type. * @param WP_Post_Type $post_type_object Arguments used to register the post type. @@ -4792,7 +4792,7 @@ function wp_insert_post( $postarr, $wp_error = false, $fire_after_hooks = true ) // If a trashed post has the desired slug, change it and let this post have it. if ( 'trash' !== $post_status && $post_name ) { /** - * Filters whether or not to add a `__trashed` suffix to trashed posts that match the name of the updated post. + * Filters whether or not to add a `__trashed` suffix to the name of trashed posts that match the name of the updated post. * * @since 5.4.0 * @@ -6545,7 +6545,7 @@ static function ( $orderby_field ) { } /** - * Filters query arguments passed to WP_Query in get_pages. + * Filters query arguments passed to WP_Query in get_pages(). * * @since 6.3.0 * diff --git a/src/wp-includes/revision.php b/src/wp-includes/revision.php index f292ad9150c31..2ae82b051145c 100644 --- a/src/wp-includes/revision.php +++ b/src/wp-includes/revision.php @@ -379,7 +379,7 @@ function _wp_put_post_revision( $post = null, $autosave = false ) { * Fires once a revision has been saved. * * @since 2.6.0 - * @since 6.4.0 The post_id parameter was added. + * @since 6.4.0 The `$post_id` parameter was added. * * @param int $revision_id Post revision ID. * @param int $post_id Post ID. diff --git a/src/wp-includes/taxonomy.php b/src/wp-includes/taxonomy.php index c314d474e6734..003b414f4f13b 100644 --- a/src/wp-includes/taxonomy.php +++ b/src/wp-includes/taxonomy.php @@ -1013,7 +1013,7 @@ function get_term( $term, $taxonomy = '', $output = OBJECT, $filter = 'raw' ) { * taxonomy. * * @since 2.3.0 - * @since 4.4.0 `$_term` is now a `WP_Term` object. + * @since 4.4.0 `$_term` is now a WP_Term object. * * @param WP_Term $_term Term object. * @param string $taxonomy The taxonomy slug. @@ -1032,7 +1032,7 @@ function get_term( $term, $taxonomy = '', $output = OBJECT, $filter = 'raw' ) { * - `get_post_tag` * * @since 2.3.0 - * @since 4.4.0 `$_term` is now a `WP_Term` object. + * @since 4.4.0 `$_term` is now a WP_Term object. * * @param WP_Term $_term Term object. * @param string $taxonomy The taxonomy slug. diff --git a/src/wp-includes/user.php b/src/wp-includes/user.php index 0e491d666087a..9871f3b18c088 100644 --- a/src/wp-includes/user.php +++ b/src/wp-includes/user.php @@ -3175,7 +3175,9 @@ function check_password_reset_key( * Filters the return value of check_password_reset_key() when an * old-style key or an expired key is used. * - * @since 3.7.0 Previously plain-text keys were stored in the database. + * Prior to 3.7, plain-text keys were stored in the database. + * + * @since 3.7.0 * @since 4.3.0 Previously key hashes were stored without an expiration time. * * @param WP_Error $return A WP_Error object denoting an expired key. diff --git a/src/wp-login.php b/src/wp-login.php index 429032a43a402..94231427017aa 100644 --- a/src/wp-login.php +++ b/src/wp-login.php @@ -397,13 +397,13 @@ function login_footer( $input_id = '' ) { ); /** - * Filters default arguments for the Languages select input on the login screen. + * Filters default arguments for the Language select input on the login screen. * * The arguments get passed to the wp_dropdown_languages() function. * * @since 5.9.0 * - * @param array $args Arguments for the Languages select input on the login screen. + * @param array $args Arguments for the Language select input on the login screen. */ wp_dropdown_languages( apply_filters( 'login_language_dropdown_args', $args ) ); ?> From ae2d0a831369f087ad25bc3a932569fd97060256 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Tue, 16 Dec 2025 23:36:47 +0000 Subject: [PATCH 038/126] Script Loader: Check if `$_wp_admin_css_colors` is set in `wp_style_loader_src()`. This aims to avoid PHP warnings if the `colors` dependency is loaded or the `style_loader_src` filter is used in a context where the `$_wp_admin_css_colors` global does not exist. Follow-up to [7976]. Props crstauf, petitphp, SergeyBiryukov. Fixes #61302. git-svn-id: https://develop.svn.wordpress.org/trunk@61388 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/script-loader.php | 4 +-- .../tests/dependencies/wpStyleLoaderSrc.php | 26 +++++++++++++++++++ 2 files changed, 28 insertions(+), 2 deletions(-) create mode 100644 tests/phpunit/tests/dependencies/wpStyleLoaderSrc.php diff --git a/src/wp-includes/script-loader.php b/src/wp-includes/script-loader.php index 7dccff9775731..56986c3d80a79 100644 --- a/src/wp-includes/script-loader.php +++ b/src/wp-includes/script-loader.php @@ -2090,8 +2090,8 @@ function wp_style_loader_src( $src, $handle ) { $color = 'fresh'; } - $color = $_wp_admin_css_colors[ $color ]; - $url = $color->url; + $color = $_wp_admin_css_colors[ $color ] ?? null; + $url = $color->url ?? ''; if ( ! $url ) { return false; diff --git a/tests/phpunit/tests/dependencies/wpStyleLoaderSrc.php b/tests/phpunit/tests/dependencies/wpStyleLoaderSrc.php new file mode 100644 index 0000000000000..6155ab0d178c3 --- /dev/null +++ b/tests/phpunit/tests/dependencies/wpStyleLoaderSrc.php @@ -0,0 +1,26 @@ +assertFalse( wp_style_loader_src( '', 'colors' ) ); + } +} From a8f5ae8ade2c08851d659e86516621ff3c7ff4fe Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Wed, 17 Dec 2025 06:55:51 +0000 Subject: [PATCH 039/126] Coding Standards: Improve formatting/readability of `if` statement in `WP_Styles` constructor. Follow-up to [46287]. See #64226, #42804. git-svn-id: https://develop.svn.wordpress.org/trunk@61389 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/class-wp-styles.php | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/src/wp-includes/class-wp-styles.php b/src/wp-includes/class-wp-styles.php index 2af3581d9aae1..2e037f128809f 100644 --- a/src/wp-includes/class-wp-styles.php +++ b/src/wp-includes/class-wp-styles.php @@ -118,9 +118,15 @@ class WP_Styles extends WP_Dependencies { */ public function __construct() { if ( - function_exists( 'is_admin' ) && ! is_admin() - && - function_exists( 'current_theme_supports' ) && ! current_theme_supports( 'html5', 'style' ) + ( + function_exists( 'is_admin' ) && + ! is_admin() + ) + && + ( + function_exists( 'current_theme_supports' ) && + ! current_theme_supports( 'html5', 'style' ) + ) ) { $this->type_attr = " type='text/css'"; } From be5b96db0707f864ba334d3d7dc3bb56642c2fb5 Mon Sep 17 00:00:00 2001 From: Jorge Costa Date: Wed, 17 Dec 2025 15:27:28 +0000 Subject: [PATCH 040/126] Abilities API: Enhance WP_Ability validation for execute_callback and permission_callback. Abilities API allows for extending WP_Ability by providing ability_class during the ability registration. This is meant to unlock complex abilities holding some sort of state or logic that requires multiple helper methods. In all of those scenarios you would ovewrite execute or do_execute method. However, because the check for execute_callback is in constructor, then in order to register an ability with ability_class overwrite, you have to BOTH: provide do_execute and provide a dummy execute_callback. The same need happens for permission_callback. This commit fixes the issue execute_callback and permission_callback are now optional when a class is provided. Props artpi, swissspidy, jorgefilipecosta, mindctrl. Fixes #64407. git-svn-id: https://develop.svn.wordpress.org/trunk@61390 602fd350-edb4-49c9-b593-d223f7449a82 --- .../abilities-api/class-wp-ability.php | 6 ++-- .../class-tests-custom-ability-class.php | 29 +++++++++++++++++ .../abilities-api/wpAbilitiesRegistry.php | 32 +++++++++++++++++++ 3 files changed, 65 insertions(+), 2 deletions(-) create mode 100644 tests/phpunit/includes/class-tests-custom-ability-class.php diff --git a/src/wp-includes/abilities-api/class-wp-ability.php b/src/wp-includes/abilities-api/class-wp-ability.php index d116080c1ccdc..3af7f7fc9844e 100644 --- a/src/wp-includes/abilities-api/class-wp-ability.php +++ b/src/wp-includes/abilities-api/class-wp-ability.php @@ -277,13 +277,15 @@ protected function prepare_properties( array $args ): array { ); } - if ( empty( $args['execute_callback'] ) || ! is_callable( $args['execute_callback'] ) ) { + // If we are not overriding `ability_class` parameter during instantiation, then we need to validate the execute_callback. + if ( get_class( $this ) === self::class && ( empty( $args['execute_callback'] ) || ! is_callable( $args['execute_callback'] ) ) ) { throw new InvalidArgumentException( __( 'The ability properties must contain a valid `execute_callback` function.' ) ); } - if ( empty( $args['permission_callback'] ) || ! is_callable( $args['permission_callback'] ) ) { + // If we are not overriding `ability_class` parameter during instantiation, then we need to validate the permission_callback. + if ( get_class( $this ) === self::class && ( empty( $args['permission_callback'] ) || ! is_callable( $args['permission_callback'] ) ) ) { throw new InvalidArgumentException( __( 'The ability properties must provide a valid `permission_callback` function.' ) ); diff --git a/tests/phpunit/includes/class-tests-custom-ability-class.php b/tests/phpunit/includes/class-tests-custom-ability-class.php new file mode 100644 index 0000000000000..6e600e5c013e1 --- /dev/null +++ b/tests/phpunit/includes/class-tests-custom-ability-class.php @@ -0,0 +1,29 @@ +registry = new WP_Abilities_Registry(); @@ -257,6 +259,36 @@ public function test_register_incorrect_execute_callback_type() { $this->assertNull( $result ); } + /** + * Should allow ability registration with custom ability_class that overrides do_execute. + * + * @ticket 64407 + * + * @covers WP_Abilities_Registry::register + * @covers WP_Ability::prepare_properties + */ + public function test_register_with_custom_ability_class_without_execute_callback() { + // Remove execute_callback and permission_callback since the custom class provides its own implementation. + unset( self::$test_ability_args['execute_callback'] ); + unset( self::$test_ability_args['permission_callback'] ); + + self::$test_ability_args['ability_class'] = 'Tests_Custom_Ability_Class'; + + $result = $this->registry->register( self::$test_ability_name, self::$test_ability_args ); + + $this->assertInstanceOf( WP_Ability::class, $result, 'Should return a WP_Ability instance.' ); + $this->assertInstanceOf( Tests_Custom_Ability_Class::class, $result, 'Should return an instance of the custom class.' ); + + // Verify the custom execute method works. + $execute_result = $result->execute( + array( + 'a' => 5, + 'b' => 3, + ) + ); + $this->assertSame( 15, $execute_result, 'Custom do_execute should multiply instead of add.' ); + } + /** * Should reject ability registration without an execute callback. * From 24382174792e0a665e2f69ab2153c530a8f1aef5 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Wed, 17 Dec 2025 23:37:39 +0000 Subject: [PATCH 041/126] Tests: Use `assertEqualHTML()` in Script Modules HTML tests. This aims to make the tests more robust. Follow-up to [58579]. Props jonsurrell. See #64225. git-svn-id: https://develop.svn.wordpress.org/trunk@61391 602fd350-edb4-49c9-b593-d223f7449a82 --- tests/phpunit/tests/script-modules/wpScriptModules.php | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/phpunit/tests/script-modules/wpScriptModules.php b/tests/phpunit/tests/script-modules/wpScriptModules.php index c80d1e745779c..aafaa47cc35e6 100644 --- a/tests/phpunit/tests/script-modules/wpScriptModules.php +++ b/tests/phpunit/tests/script-modules/wpScriptModules.php @@ -1234,7 +1234,7 @@ function ( $data ) { HTML; - $this->assertSame( $expected, $actual ); + $this->assertEqualHTML( $expected, $actual ); } /** @@ -1259,7 +1259,7 @@ function ( $data ) { HTML; - $this->assertSame( $expected, $actual ); + $this->assertEqualHTML( $expected, $actual ); } /** @@ -1332,7 +1332,7 @@ function ( $data ) use ( $input ) { HTML; - $this->assertSame( $expected, $actual ); + $this->assertEqualHTML( $expected, $actual ); } /** From 944178a1e729150819a6e4fdcde2dd97d8d7a013 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Thu, 18 Dec 2025 21:56:44 +0000 Subject: [PATCH 042/126] Tests: Use `assertEqualHTML()` in styles HTML tests. This aims to make the tests more robust. Follow-up to [287/tests], [749/tests], [25786], [31031], [36550], [46164], [48937], [52036], [61084], [61391]. Props jonsurrell. See #64225. git-svn-id: https://develop.svn.wordpress.org/trunk@61392 602fd350-edb4-49c9-b593-d223f7449a82 --- tests/phpunit/tests/dependencies/styles.php | 28 ++++++++++----------- 1 file changed, 13 insertions(+), 15 deletions(-) diff --git a/tests/phpunit/tests/dependencies/styles.php b/tests/phpunit/tests/dependencies/styles.php index 74e4db47330b4..ee33f4d4bf1b3 100644 --- a/tests/phpunit/tests/dependencies/styles.php +++ b/tests/phpunit/tests/dependencies/styles.php @@ -68,7 +68,7 @@ public function test_wp_enqueue_style() { $expected .= "\n"; $expected .= "\n"; - $this->assertSame( $expected, get_echo( 'wp_print_styles' ) ); + $this->assertEqualHTML( $expected, get_echo( 'wp_print_styles' ) ); // No styles left to print. $this->assertSame( '', get_echo( 'wp_print_styles' ) ); @@ -88,7 +88,7 @@ public function test_wp_enqueue_style_with_html5_support_does_not_contain_type_a $ver = get_bloginfo( 'version' ); $expected = "\n"; - $this->assertSame( $expected, get_echo( 'wp_print_styles' ) ); + $this->assertEqualHTML( $expected, get_echo( 'wp_print_styles' ) ); } /** @@ -103,7 +103,7 @@ public function test_awkward_handles_are_supported_consistently( $handle ) { $expected = "\n"; - $this->assertSame( $expected, get_echo( 'wp_print_styles' ) ); + $this->assertEqualHTML( $expected, get_echo( 'wp_print_styles' ) ); } /** @@ -157,7 +157,7 @@ public function test_protocols() { $expected .= "\n"; // Go! - $this->assertSame( $expected, get_echo( 'wp_print_styles' ) ); + $this->assertEqualHTML( $expected, get_echo( 'wp_print_styles' ) ); // No styles left to print. $this->assertSame( '', get_echo( 'wp_print_styles' ) ); @@ -186,8 +186,7 @@ public function test_inline_styles() { wp_enqueue_style( 'handle', 'http://example.com', array(), 1 ); wp_add_inline_style( 'handle', $style ); - // No styles left to print. - $this->assertSame( $expected, get_echo( 'wp_print_styles' ) ); + $this->assertEqualHTML( $expected, get_echo( 'wp_print_styles' ) ); } /** @@ -215,7 +214,7 @@ public function test_inline_styles_concat() { wp_add_inline_style( 'handle', $style ); wp_print_styles(); - $this->assertSame( $expected, $wp_styles->print_html ); + $this->assertEqualHTML( $expected, $wp_styles->print_html ); } /** @@ -233,7 +232,7 @@ public function test_inline_styles_concat() { * @param string $expected Expected result. */ public function test_normalize_relative_css_links( $css, $expected ) { - $this->assertSame( + $this->assertEqualHTML( $expected, _wp_normalize_relative_css_links( $css, site_url( 'wp-content/themes/test/style.css' ) ) ); @@ -311,8 +310,7 @@ public function test_multiple_inline_styles() { wp_add_inline_style( 'handle', $style1 ); wp_add_inline_style( 'handle', $style2 ); - // No styles left to print. - $this->assertSame( $expected, get_echo( 'wp_print_styles' ) ); + $this->assertEqualHTML( $expected, get_echo( 'wp_print_styles' ) ); } /** @@ -337,7 +335,7 @@ public function test_plugin_doing_inline_styles_wrong() { wp_add_inline_style( 'handle', "" ); - $this->assertSame( $expected, get_echo( 'wp_print_styles' ) ); + $this->assertEqualHTML( $expected, get_echo( 'wp_print_styles' ) ); } /** @@ -351,7 +349,7 @@ public function test_unnecessary_style_tags() { wp_enqueue_style( 'handle', 'http://example.com', array(), 1 ); - $this->assertSame( $expected, get_echo( 'wp_print_styles' ) ); + $this->assertEqualHTML( $expected, get_echo( 'wp_print_styles' ) ); } /** @@ -361,12 +359,12 @@ public function test_unnecessary_style_tags() { * @expectedDeprecated WP_Dependencies->add_data() */ public function test_conditional_inline_styles_are_also_conditional() { - $expected = ''; wp_enqueue_style( 'handle', 'http://example.com', array(), 1 ); wp_style_add_data( 'handle', 'conditional', 'IE' ); wp_add_inline_style( 'handle', 'a { color: blue; }' ); - $this->assertSameIgnoreEOL( $expected, get_echo( 'wp_print_styles' ) ); + // Conditional styles are disabled. + $this->assertSame( '', get_echo( 'wp_print_styles' ) ); } /** @@ -399,7 +397,7 @@ public function test_wp_add_inline_style_for_handle_without_source() { wp_enqueue_style( 'handle-three' ); wp_add_inline_style( 'handle-three', $style ); - $this->assertSame( $expected, get_echo( 'wp_print_styles' ) ); + $this->assertEqualHTML( $expected, get_echo( 'wp_print_styles' ) ); } /** From b8f0e63c326924950dfa24b35fd9ce6d691eff14 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Fri, 19 Dec 2025 23:16:42 +0000 Subject: [PATCH 043/126] Tests: Update scripts tests to use semantic HTML comparison. This aims to make the tests more robust. Follow-up to [50167], [60295], [61391], [61392]. Props jonsurrell. See #64225. git-svn-id: https://develop.svn.wordpress.org/trunk@61394 602fd350-edb4-49c9-b593-d223f7449a82 --- tests/phpunit/tests/dependencies/scripts.php | 63 ++++++++++++++----- .../tests/dependencies/wpScriptTag.php | 10 +-- 2 files changed, 54 insertions(+), 19 deletions(-) diff --git a/tests/phpunit/tests/dependencies/scripts.php b/tests/phpunit/tests/dependencies/scripts.php index a3c8b92695f4f..c01cdad6ef94d 100644 --- a/tests/phpunit/tests/dependencies/scripts.php +++ b/tests/phpunit/tests/dependencies/scripts.php @@ -69,6 +69,44 @@ public function tear_down() { parent::tear_down(); } + /** + * Asserts that two HTML SCRIPT tags are semantically equal within a larger HTML text. + * + * The expected string should contain a single SCRIPT tag with an ID attribute. This ID will + * be used to locate the corresponding SCRIPT tag within the provided HTML. + * + * The provided HTML will be traversed to locate the SCRIPT tag with the matcing ID. + * + * These two tags will be compared for semantic equality of their HTML. + * + * @since 7.0.0 + * + * @param string $expected The expected SCRIPT tag HTML. + * @param string $html The HTML to search within. + * @param string $message Optional. Message to display upon failure. Default 'The SCRIPT tag did not match.'. + */ + private function assertEqualHTMLScriptTagById( string $expected, string $html, string $message = 'The SCRIPT tag did not match.' ) { + $find_id_tag_processor = new WP_HTML_Tag_Processor( $expected ); + $find_id_tag_processor->next_token(); + $id = $find_id_tag_processor->get_attribute( 'id' ); + assert( is_string( $id ) ); + + $processor = ( new class('', WP_HTML_Processor::CONSTRUCTOR_UNLOCK_CODE ) extends WP_HTML_Processor { + public function get_script_html() { + assert( 'SCRIPT' === $this->get_tag() ); + $this->set_bookmark( 'here' ); + $span = $this->bookmarks['_here']; + return substr( $this->html, $span->start, $span->length ); + } + } )::create_fragment( $html ); + + while ( $processor->next_tag( 'SCRIPT' ) && $processor->get_attribute( 'id' ) !== $id ) { + // Loop until we find the right script tag. + } + $this->assertSame( 'SCRIPT', $processor->get_tag(), "Matching tag `script#{$id}` could not be found." ); + $this->assertEqualHTML( $expected, $processor->get_script_html(), '', $message ); + } + /** * Test versioning * @@ -1558,15 +1596,13 @@ public function test_loading_strategy_with_valid_blocking_registration() { wp_enqueue_script( 'main-script-b1', '/main-script-b1.js', array(), null ); $output = get_echo( 'wp_print_scripts' ); $expected = "\n"; - $expected = str_replace( "'", '"', $expected ); - $this->assertSame( $expected, $output, 'Scripts registered with a "blocking" strategy, and who have no dependencies, should have no loading strategy attributes printed.' ); + $this->assertEqualHTML( $expected, $output, '', 'Scripts registered with a "blocking" strategy, and who have no dependencies, should have no loading strategy attributes printed.' ); // strategy args not set. wp_enqueue_script( 'main-script-b2', '/main-script-b2.js', array(), null, array() ); $output = get_echo( 'wp_print_scripts' ); $expected = "\n"; - $expected = str_replace( "'", '"', $expected ); - $this->assertSame( $expected, $output, 'Scripts registered with no strategy assigned, and who have no dependencies, should have no loading strategy attributes printed.' ); + $this->assertEqualHTML( $expected, $output, '', 'Scripts registered with no strategy assigned, and who have no dependencies, should have no loading strategy attributes printed.' ); } /** @@ -2616,14 +2652,6 @@ public function test_wp_add_inline_script_customize_dependency() { $wp_scripts->base_url = ''; $wp_scripts->do_concat = true; - $expected_tail = "\n"; - $expected_tail .= "\n"; - $handle = 'customize-dependency'; wp_enqueue_script( $handle, '/customize-dependency.js', array( 'customize-controls' ), null ); wp_add_inline_script( $handle, 'tryCustomizeDependency()' ); @@ -2635,9 +2663,16 @@ public function test_wp_add_inline_script_customize_dependency() { _print_scripts(); $print_scripts = $this->getActualOutput(); - $tail = substr( $print_scripts, strrpos( $print_scripts, '\n"; + $this->assertEqualHTMLScriptTagById( $expected, $print_scripts ); - $this->assertEqualHTML( $expected_tail, $tail ); + $expected = "\n"; + $this->assertEqualHTMLScriptTagById( $expected, $print_scripts ); } /** diff --git a/tests/phpunit/tests/dependencies/wpScriptTag.php b/tests/phpunit/tests/dependencies/wpScriptTag.php index ee273f8fb3687..ea963a383b29e 100644 --- a/tests/phpunit/tests/dependencies/wpScriptTag.php +++ b/tests/phpunit/tests/dependencies/wpScriptTag.php @@ -11,7 +11,7 @@ class Tests_Functions_wpScriptTag extends WP_UnitTestCase { public function get_script_tag_type_set() { add_theme_support( 'html5', array( 'script' ) ); - $this->assertSame( + $this->assertEqualHTML( '' . "\n", wp_get_script_tag( array( @@ -25,7 +25,7 @@ public function get_script_tag_type_set() { remove_theme_support( 'html5' ); - $this->assertSame( + $this->assertEqualHTML( '' . "\n", wp_get_script_tag( array( @@ -44,7 +44,7 @@ public function get_script_tag_type_set() { public function test_get_script_tag_type_not_set() { add_theme_support( 'html5', array( 'script' ) ); - $this->assertSame( + $this->assertEqualHTML( '' . "\n", wp_get_script_tag( array( @@ -80,7 +80,7 @@ static function ( $attributes ) { 'nomodule' => true, ); - $this->assertSame( + $this->assertEqualHTML( wp_get_script_tag( $attributes ), get_echo( 'wp_print_script_tag', @@ -90,7 +90,7 @@ static function ( $attributes ) { remove_theme_support( 'html5' ); - $this->assertSame( + $this->assertEqualHTML( wp_get_script_tag( $attributes ), get_echo( 'wp_print_script_tag', From c235aa938b26c741673ee2b37ad8451fbf6ad2da Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Sat, 20 Dec 2025 23:14:44 +0000 Subject: [PATCH 044/126] Tests: Correst some test class names per the naming conventions. Follow-up to [50167], [50409], [56748]. See #64225. git-svn-id: https://develop.svn.wordpress.org/trunk@61395 602fd350-edb4-49c9-b593-d223f7449a82 --- tests/phpunit/tests/dependencies/wpInlineScriptTag.php | 2 +- .../tests/dependencies/wpRemoveSurroundingEmptyScriptTags.php | 2 +- tests/phpunit/tests/dependencies/wpSanitizeScriptAttributes.php | 2 +- tests/phpunit/tests/dependencies/wpScriptTag.php | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/tests/phpunit/tests/dependencies/wpInlineScriptTag.php b/tests/phpunit/tests/dependencies/wpInlineScriptTag.php index 7192570838ae7..9f3eb3c8cfb90 100644 --- a/tests/phpunit/tests/dependencies/wpInlineScriptTag.php +++ b/tests/phpunit/tests/dependencies/wpInlineScriptTag.php @@ -8,7 +8,7 @@ * @covers ::wp_get_inline_script_tag * @covers ::wp_print_inline_script_tag */ -class Tests_Functions_wpInlineScriptTag extends WP_UnitTestCase { +class Tests_Dependencies_wpInlineScriptTag extends WP_UnitTestCase { private $original_theme_features = array(); diff --git a/tests/phpunit/tests/dependencies/wpRemoveSurroundingEmptyScriptTags.php b/tests/phpunit/tests/dependencies/wpRemoveSurroundingEmptyScriptTags.php index 39b0480ccb73f..6bd8036c38d1d 100644 --- a/tests/phpunit/tests/dependencies/wpRemoveSurroundingEmptyScriptTags.php +++ b/tests/phpunit/tests/dependencies/wpRemoveSurroundingEmptyScriptTags.php @@ -8,7 +8,7 @@ * @ticket 58664 * @covers ::wp_remove_surrounding_empty_script_tags */ -class Tests_Functions_wpRemoveSurroundingEmptyScriptTags extends WP_UnitTestCase { +class Tests_Dependencies_wpRemoveSurroundingEmptyScriptTags extends WP_UnitTestCase { /** * Data provider for test. diff --git a/tests/phpunit/tests/dependencies/wpSanitizeScriptAttributes.php b/tests/phpunit/tests/dependencies/wpSanitizeScriptAttributes.php index 3ff79fc5d83d3..0c96d9ee47654 100644 --- a/tests/phpunit/tests/dependencies/wpSanitizeScriptAttributes.php +++ b/tests/phpunit/tests/dependencies/wpSanitizeScriptAttributes.php @@ -7,7 +7,7 @@ * @group scripts * @covers ::wp_sanitize_script_attributes */ -class Tests_Functions_wpSanitizeScriptAttributes extends WP_UnitTestCase { +class Tests_Dependencies_wpSanitizeScriptAttributes extends WP_UnitTestCase { public function test_sanitize_script_attributes_type_set() { add_theme_support( 'html5', array( 'script' ) ); diff --git a/tests/phpunit/tests/dependencies/wpScriptTag.php b/tests/phpunit/tests/dependencies/wpScriptTag.php index ea963a383b29e..c06a86b2db57f 100644 --- a/tests/phpunit/tests/dependencies/wpScriptTag.php +++ b/tests/phpunit/tests/dependencies/wpScriptTag.php @@ -6,7 +6,7 @@ * @group dependencies * @group scripts */ -class Tests_Functions_wpScriptTag extends WP_UnitTestCase { +class Tests_Dependencies_wpScriptTag extends WP_UnitTestCase { public function get_script_tag_type_set() { add_theme_support( 'html5', array( 'script' ) ); From 2b6329c28eb9c8251bf3ac1f2efda0d7036d9782 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Sun, 21 Dec 2025 23:46:29 +0000 Subject: [PATCH 045/126] Docs: Correct DocBlock formatting for `png:IHDR.color-type-orig` property test. Follow-up to [60246]. Props mukesh27, adamsilverstein. See #64224. git-svn-id: https://develop.svn.wordpress.org/trunk@61396 602fd350-edb4-49c9-b593-d223f7449a82 --- tests/phpunit/tests/image/editorImagick.php | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/tests/phpunit/tests/image/editorImagick.php b/tests/phpunit/tests/image/editorImagick.php index 5816cc6b5a6d9..e120c32502ad5 100644 --- a/tests/phpunit/tests/image/editorImagick.php +++ b/tests/phpunit/tests/image/editorImagick.php @@ -836,14 +836,15 @@ public static function data_resizes_are_small_for_16bit_images() { } /** - * Tests that the 'png:IHDR.color-type-orig' property is preserved after resizing + * Tests that the 'png:IHDR.color-type-orig' property is preserved after resizing. * Used to identify indexed PNG images, see https://www.w3.org/TR/PNG-Chunks.html#C.IHDR. * * @ticket 63448 + * * @dataProvider data_png_color_type_after_resize * - * @param string $file_path Path to the image file. - * @param int $expected_color_type The expected original color type. + * @param string $file_path Path to the image file. + * @param int $expected_color_type The expected original color type. */ public function test_png_color_type_is_preserved_after_resize( $file_path, $expected_color_type ) { @@ -902,6 +903,7 @@ public static function data_png_color_type_after_resize() { * Tests that alpha transparency is preserved after resizing. * * @ticket 63448 + * * @dataProvider data_alpha_transparency_is_preserved_after_resize * * @param string $file_path Path to the image file. From 0ad7a187d17a5a73377ee66a9960604f71890d69 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Mon, 22 Dec 2025 00:54:50 +0000 Subject: [PATCH 046/126] Script Loader: Fix adding default version to script/style URL when args are supplied via enqueued handle. Also fixes phpdoc for some member variables of `WP_Scripts` and `WP_Styles`. Developed in https://github.com/WordPress/wordpress-develop/pull/10608 Follow-up to [61358]. Props westonruter, peterwilsoncc. See #64224, #64238. Fixes #64372. git-svn-id: https://develop.svn.wordpress.org/trunk@61397 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/class-wp-scripts.php | 24 ++- src/wp-includes/class-wp-styles.php | 33 +++- tests/phpunit/tests/dependencies/scripts.php | 163 +++++++++++++++---- tests/phpunit/tests/dependencies/styles.php | 101 +++++++++++- 4 files changed, 274 insertions(+), 47 deletions(-) diff --git a/src/wp-includes/class-wp-scripts.php b/src/wp-includes/class-wp-scripts.php index 13266274048ea..03829a20bde63 100644 --- a/src/wp-includes/class-wp-scripts.php +++ b/src/wp-includes/class-wp-scripts.php @@ -22,7 +22,8 @@ class WP_Scripts extends WP_Dependencies { * Full URL with trailing slash. * * @since 2.6.0 - * @var string + * @see wp_default_scripts() + * @var string|null */ public $base_url; @@ -30,7 +31,8 @@ class WP_Scripts extends WP_Dependencies { * URL of the content directory. * * @since 2.8.0 - * @var string + * @see wp_default_scripts() + * @var string|null */ public $content_url; @@ -38,7 +40,8 @@ class WP_Scripts extends WP_Dependencies { * Default version string for scripts. * * @since 2.6.0 - * @var string + * @see wp_default_scripts() + * @var string|null */ public $default_version; @@ -118,6 +121,7 @@ class WP_Scripts extends WP_Dependencies { * List of default directories. * * @since 2.8.0 + * @see wp_default_scripts() * @var string[]|null */ public $default_dirs; @@ -413,9 +417,19 @@ public function do_item( $handle, $group = false ) { $src = $this->base_url . $src; } - if ( ! empty( $ver ) ) { - $src = add_query_arg( 'ver', $ver, $src ); + $query_args = array(); + if ( empty( $obj->ver ) && null !== $obj->ver && is_string( $this->default_version ) ) { + $query_args['ver'] = $this->default_version; + } elseif ( is_scalar( $obj->ver ) ) { + $query_args['ver'] = (string) $obj->ver; + } + if ( isset( $this->args[ $handle ] ) ) { + parse_str( $this->args[ $handle ], $parsed_args ); + if ( $parsed_args ) { + $query_args = array_merge( $query_args, $parsed_args ); + } } + $src = add_query_arg( rawurlencode_deep( $query_args ), $src ); /** This filter is documented in wp-includes/class-wp-scripts.php */ $src = esc_url_raw( apply_filters( 'script_loader_src', $src, $handle ) ); diff --git a/src/wp-includes/class-wp-styles.php b/src/wp-includes/class-wp-styles.php index 2e037f128809f..9b210b2df9d30 100644 --- a/src/wp-includes/class-wp-styles.php +++ b/src/wp-includes/class-wp-styles.php @@ -22,7 +22,8 @@ class WP_Styles extends WP_Dependencies { * Full URL with trailing slash. * * @since 2.6.0 - * @var string + * @see wp_default_styles() + * @var string|null */ public $base_url; @@ -30,7 +31,8 @@ class WP_Styles extends WP_Dependencies { * URL of the content directory. * * @since 2.8.0 - * @var string + * @see wp_default_styles() + * @var string|null */ public $content_url; @@ -38,7 +40,8 @@ class WP_Styles extends WP_Dependencies { * Default version string for stylesheets. * * @since 2.6.0 - * @var string + * @see wp_default_styles() + * @var string|null */ public $default_version; @@ -46,6 +49,7 @@ class WP_Styles extends WP_Dependencies { * The current text direction. * * @since 2.6.0 + * @see wp_default_styles() * @var string */ public $text_direction = 'ltr'; @@ -96,6 +100,7 @@ class WP_Styles extends WP_Dependencies { * List of default directories. * * @since 2.8.0 + * @see wp_default_styles() * @var string[]|null */ public $default_dirs; @@ -218,7 +223,7 @@ public function do_item( $handle, $group = false ) { return true; } - $href = $this->_css_href( $src, $ver, $handle ); + $href = $this->_css_href( $src, $obj->ver, $handle ); if ( ! $href ) { return true; } @@ -425,9 +430,9 @@ public function all_deps( $handles, $recursion = false, $group = false ) { * * @since 2.6.0 * - * @param string $src The source of the enqueued style. - * @param string $ver The version of the enqueued style. - * @param string $handle The style's registered handle. + * @param string $src The source of the enqueued style. + * @param string|false|null $ver The version of the enqueued style. + * @param string $handle The style's registered handle. * @return string Style's fully-qualified URL. */ public function _css_href( $src, $ver, $handle ) { @@ -435,9 +440,19 @@ public function _css_href( $src, $ver, $handle ) { $src = $this->base_url . $src; } - if ( ! empty( $ver ) ) { - $src = add_query_arg( 'ver', $ver, $src ); + $query_args = array(); + if ( empty( $ver ) && null !== $ver && is_string( $this->default_version ) ) { + $query_args['ver'] = $this->default_version; + } elseif ( is_scalar( $ver ) ) { + $query_args['ver'] = (string) $ver; + } + if ( isset( $this->args[ $handle ] ) ) { + parse_str( $this->args[ $handle ], $parsed_args ); + if ( $parsed_args ) { + $query_args = array_merge( $query_args, $parsed_args ); + } } + $src = add_query_arg( rawurlencode_deep( $query_args ), $src ); /** * Filters an enqueued style's fully-qualified URL. diff --git a/tests/phpunit/tests/dependencies/scripts.php b/tests/phpunit/tests/dependencies/scripts.php index c01cdad6ef94d..c4983b82a4ede 100644 --- a/tests/phpunit/tests/dependencies/scripts.php +++ b/tests/phpunit/tests/dependencies/scripts.php @@ -111,19 +111,27 @@ public function get_script_html() { * Test versioning * * @ticket 11315 + * @ticket 64372 */ public function test_wp_enqueue_script() { global $wp_version; wp_enqueue_script( 'no-deps-no-version', 'example.com', array() ); wp_enqueue_script( 'empty-deps-no-version', 'example.com' ); - wp_enqueue_script( 'empty-deps-version', 'example.com', array(), 1.2 ); + wp_enqueue_script( 'empty-deps-version', 'example.com', array(), '1.2' ); wp_enqueue_script( 'empty-deps-null-version', 'example.com', array(), null ); + wp_enqueue_script( 'empty-deps-arg-in-handle-with-ver?arg1=foo&arg2=bar', 'https://example.com/test.js', array(), '2.0' ); + wp_enqueue_script( 'empty-deps-arg-in-handle-without-ver?arg1=foo&arg2=bar', 'https://example.com/test.js', array(), null ); + wp_register_script( 'registered-no-qs-handle-null-version-enqueued-with-qs', 'https://example.com/test.js' ); + wp_enqueue_script( 'registered-no-qs-handle-null-version-enqueued-with-qs?arg1=foo&arg2=bar' ); $expected = "\n"; $expected .= "\n"; $expected .= "\n"; $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); @@ -564,7 +572,7 @@ public function data_provider_to_test_various_strategy_dependency_chains() { //# sourceURL=blocking-not-async-without-dependency-js-before /* ]]> */ - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + HTML , ), @@ -1060,7 +1068,7 @@ public function data_provider_to_test_various_strategy_dependency_chains() { $this->add_test_inline_script( $handle, 'after' ); }, 'expected_markup' => << + - - + + + - + - - + + + HTML , ), @@ -4157,4 +4165,95 @@ public function test_wp_scripts_doing_it_wrong_for_missing_dependencies() { 'Expected _doing_it_wrong() notice to indicate missing dependencies for enqueued script.' ); } + + /** + * Test query string on handle when enqueuing script directly. + * + * @ticket 64372 + * + * @covers WP_Scripts::do_item + * + * @dataProvider data_varying_versions_handle_args + * + * @param mixed $version Version to pass when enqueuing. + * @param string $expected_query_string Expected query string portion of the script src URL. + */ + public function test_varying_versions_added_to_handle_args_enqueued_scripts( $version, $expected_query_string ) { + wp_enqueue_script( 'test-script?qs1=q1&qs2=q2', '/test-script.js', array(), $version ); + $markup = get_echo( 'wp_print_scripts' ); + + $expected = ""; + $this->assertEqualHTML( $expected, $markup, '', 'Expected equal snapshot for wp_print_scripts() with version ' . var_export( $version, true ) . ":\n$markup" ); + } + + /** + * Test query string on handle when registering then enqueuing script. + * + * @ticket 64372 + * + * @covers WP_Scripts::do_item + * + * @dataProvider data_varying_versions_handle_args + * + * @param mixed $version Version to pass when enqueuing. + * @param string $expected_query_string Expected query string portion of the script src URL. + */ + public function test_varying_versions_added_to_handle_args_registered_then_enqueued_scripts( $version, $expected_query_string ) { + wp_register_script( 'test-script', '/test-script.js', array(), $version ); + wp_enqueue_script( 'test-script?qs1=q1&qs2=q2' ); + $markup = get_echo( 'wp_print_scripts' ); + + $expected = ""; + $this->assertEqualHTML( $expected, $markup, '', 'Expected equal snapshot for wp_print_scripts() with version ' . var_export( $version, true ) . ":\n$markup" ); + } + + /** + * Data provider for: + * - test_varying_versions_added_to_handle_args_enqueued_scripts + * - test_varying_versions_added_to_handle_args_registered_then_enqueued_scripts + * + * @return array[] Data provider. + */ + public function data_varying_versions_handle_args() { + $default_version = get_bloginfo( 'version' ); + + return array( + 'string' => array( + '1.0.0', + 'ver=1.0.0&qs1=q1&qs2=q2', + ), + 'null' => array( + null, + 'qs1=q1&qs2=q2', + ), + 'false' => array( + false, + "ver={$default_version}&qs1=q1&qs2=q2", + ), + 'empty-string' => array( + '', + "ver={$default_version}&qs1=q1&qs2=q2", + ), + 'zero-string' => array( + '0', + "ver={$default_version}&qs1=q1&qs2=q2", + ), + 'integer' => array( + 123, + 'ver=123&qs1=q1&qs2=q2', + ), + 'zero-integer' => array( + 0, + "ver={$default_version}&qs1=q1&qs2=q2", + ), + 'float' => array( + 1.23, + 'ver=1.23&qs1=q1&qs2=q2', + ), + 'zero-float' => array( + 0.0, + "ver={$default_version}&qs1=q1&qs2=q2", + ), + ); + } } diff --git a/tests/phpunit/tests/dependencies/styles.php b/tests/phpunit/tests/dependencies/styles.php index ee33f4d4bf1b3..3828c8246e528 100644 --- a/tests/phpunit/tests/dependencies/styles.php +++ b/tests/phpunit/tests/dependencies/styles.php @@ -55,18 +55,26 @@ public function tear_down() { * Test versioning * * @ticket 11315 + * @ticket 64372 */ public function test_wp_enqueue_style() { wp_enqueue_style( 'no-deps-no-version', 'example.com' ); - wp_enqueue_style( 'no-deps-version', 'example.com', array(), 1.2 ); + wp_enqueue_style( 'no-deps-version', 'example.com', array(), '1.2' ); wp_enqueue_style( 'no-deps-null-version', 'example.com', array(), null ); wp_enqueue_style( 'no-deps-null-version-print-media', 'example.com', array(), null, 'print' ); + wp_enqueue_style( 'no-deps-arg-in-handle-with-ver?arg1=foo&arg2=bar', 'https://example.com/test.css', array(), '2.0' ); + wp_enqueue_style( 'no-deps-arg-in-handle-without-ver?arg1=foo&arg2=bar', 'https://example.com/test.css', array(), null ); + wp_register_style( 'registered-no-qs-handle-null-version-enqueued-with-qs', 'https://example.com/test.css' ); + wp_enqueue_style( 'registered-no-qs-handle-null-version-enqueued-with-qs?arg1=foo&arg2=bar' ); $ver = get_bloginfo( 'version' ); $expected = "\n"; $expected .= "\n"; $expected .= "\n"; $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_styles' ) ); @@ -844,4 +852,95 @@ public function test_wp_style_doing_it_wrong_for_missing_dependencies() { 'Expected _doing_it_wrong() notice to indicate missing dependencies for enqueued styles.' ); } + + /** + * Test query string on handle when enqueuing styles directly. + * + * @ticket 64372 + * + * @covers WP_Styles::do_item + * + * @dataProvider data_varying_versions_handle_args + * + * @param mixed $version Version to pass when enqueuing. + * @param string $expected_query_string Expected query string portion of the style sheet URL. + */ + public function test_varying_versions_added_to_handle_args_enqueued_styles( $version, $expected_query_string ) { + wp_enqueue_style( 'test-style?qs1=q1&qs2=q2', '/test-style.css', array(), $version ); + $markup = get_echo( 'wp_print_styles' ); + + $expected = ""; + $this->assertEqualHTML( $expected, $markup, '', 'Expected equal snapshot for wp_print_styles() with version ' . var_export( $version, true ) . ":\n$markup" ); + } + + /** + * Test query string on handle when registering then enqueuing styles. + * + * @ticket 64372 + * + * @covers WP_Styles::do_item + * + * @dataProvider data_varying_versions_handle_args + * + * @param mixed $version Version to pass when enqueuing. + * @param string $expected_query_string Expected query string portion of the style sheet URL. + */ + public function test_varying_versions_added_to_handle_args_registered_then_enqueued_styles( $version, $expected_query_string ) { + wp_register_style( 'test-style', '/test-style.css', array(), $version ); + wp_enqueue_style( 'test-style?qs1=q1&qs2=q2' ); + $markup = get_echo( 'wp_print_styles' ); + + $expected = ""; + $this->assertEqualHTML( $expected, $markup, '', 'Expected equal snapshot for wp_print_styles() with version ' . var_export( $version, true ) . ":\n$markup" ); + } + + /** + * Data provider for: + * - test_varying_versions_added_to_handle_args_enqueued_styles + * - test_varying_versions_added_to_handle_args_registered_then_enqueued_styles + * + * @return array[] Data provider. + */ + public function data_varying_versions_handle_args() { + $default_version = get_bloginfo( 'version' ); + + return array( + 'string' => array( + '1.0.0', + 'ver=1.0.0&qs1=q1&qs2=q2', + ), + 'null' => array( + null, + 'qs1=q1&qs2=q2', + ), + 'false' => array( + false, + "ver={$default_version}&qs1=q1&qs2=q2", + ), + 'empty-string' => array( + '', + "ver={$default_version}&qs1=q1&qs2=q2", + ), + 'zero-string' => array( + '0', + "ver={$default_version}&qs1=q1&qs2=q2", + ), + 'integer' => array( + 123, + 'ver=123&qs1=q1&qs2=q2', + ), + 'zero-integer' => array( + 0, + "ver={$default_version}&qs1=q1&qs2=q2", + ), + 'float' => array( + 1.23, + 'ver=1.23&qs1=q1&qs2=q2', + ), + 'zero-float' => array( + 0.0, + "ver={$default_version}&qs1=q1&qs2=q2", + ), + ); + } } From 43039c2ffb91a0890ca93ad575d38140c48fa46d Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Mon, 22 Dec 2025 01:16:28 +0000 Subject: [PATCH 047/126] Filesystem API: Resolve FIXME comment for `WP_Filesystem_Direct::getchmod()` by explicitly returning '0' in error case. Developed in https://github.com/WordPress/wordpress-develop/pull/10637 Follow-up to [11831]. Props vietcgi, westonruter. See #10304. Fixes #64426. git-svn-id: https://develop.svn.wordpress.org/trunk@61398 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/class-wp-filesystem-direct.php | 11 +++++++---- .../tests/filesystem/wpFilesystemDirect/getchmod.php | 7 ++++--- 2 files changed, 11 insertions(+), 7 deletions(-) diff --git a/src/wp-admin/includes/class-wp-filesystem-direct.php b/src/wp-admin/includes/class-wp-filesystem-direct.php index 2efd5b000ab07..ed22a821a14b0 100644 --- a/src/wp-admin/includes/class-wp-filesystem-direct.php +++ b/src/wp-admin/includes/class-wp-filesystem-direct.php @@ -249,15 +249,18 @@ public function owner( $file ) { /** * Gets the permissions of the specified file or filepath in their octal format. * - * FIXME does not handle errors in fileperms() - * * @since 2.5.0 * * @param string $file Path to the file. - * @return string Mode of the file (the last 3 digits). + * @return string Mode of the file (the last 3 digits), or the string "0" on failure. */ public function getchmod( $file ) { - return substr( decoct( @fileperms( $file ) ), -3 ); + $perms = @fileperms( $file ); + if ( false === $perms ) { + return '0'; + } + + return substr( decoct( $perms ), -3 ); } /** diff --git a/tests/phpunit/tests/filesystem/wpFilesystemDirect/getchmod.php b/tests/phpunit/tests/filesystem/wpFilesystemDirect/getchmod.php index 2b0c2ce327afc..c81349e7503e7 100644 --- a/tests/phpunit/tests/filesystem/wpFilesystemDirect/getchmod.php +++ b/tests/phpunit/tests/filesystem/wpFilesystemDirect/getchmod.php @@ -33,16 +33,17 @@ public function test_should_get_chmod_for_a_path_that_exists( $path ) { /** * Tests that `WP_Filesystem_Direct::getchmod()` returns - * the permissions for a path that does not exist. + * "0" for a path that does not exist. * * @dataProvider data_paths_that_do_not_exist * * @ticket 57774 + * @ticket 64426 * * @param string $path The path. */ - public function test_should_get_chmod_for_a_path_that_does_not_exist( $path ) { + public function test_should_return_zero_for_a_path_that_does_not_exist( $path ) { $actual = self::$filesystem->getchmod( self::$file_structure['test_dir']['path'] . $path ); - $this->assertNotSame( '', $actual ); + $this->assertSame( '0', $actual ); } } From a32b6fd2c5a8c935e14cbf5763f0698f7f826613 Mon Sep 17 00:00:00 2001 From: Aki Hamano Date: Mon, 22 Dec 2025 10:40:05 +0000 Subject: [PATCH 048/126] Widgets: Insert widgets into the selected sidebar correctly in accessibility mode. Renames variables to resolve conflict with outer scope variables, fixing widget placement in selected sidebars. Props joedolson, sabernhardt, vybiral, wildworks. Fixes #64380. git-svn-id: https://develop.svn.wordpress.org/trunk@61399 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/widgets-form.php | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/wp-admin/widgets-form.php b/src/wp-admin/widgets-form.php index cabbb80bb437a..cde09ca47c115 100644 --- a/src/wp-admin/widgets-form.php +++ b/src/wp-admin/widgets-form.php @@ -187,9 +187,9 @@ // Remove old position. if ( ! isset( $_POST['delete_widget'] ) ) { - foreach ( $sidebars_widgets as $sidebar_id => $sidebar ) { - if ( is_array( $sidebar ) ) { - $sidebars_widgets[ $sidebar_id ] = array_diff( $sidebar, array( $widget_id ) ); + foreach ( $sidebars_widgets as $sidebar_widget_id => $sidebar_widget ) { + if ( is_array( $sidebar_widget ) ) { + $sidebars_widgets[ $sidebar_widget_id ] = array_diff( $sidebar_widget, array( $widget_id ) ); } } From 696f25fec8092ebf723ddbc895307719e5c5e77d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Andr=C3=83=C2=A9=20Maneiro?= Date: Mon, 22 Dec 2025 15:55:50 +0000 Subject: [PATCH 049/126] Theme_JSON_Resolver: check for WP_Post in query. Props oandregal, mcsf, westonruter, mukesh27. Fixes #64434. git-svn-id: https://develop.svn.wordpress.org/trunk@61400 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/class-wp-theme-json-resolver.php | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/src/wp-includes/class-wp-theme-json-resolver.php b/src/wp-includes/class-wp-theme-json-resolver.php index 1924d1a47190a..e696eef894783 100644 --- a/src/wp-includes/class-wp-theme-json-resolver.php +++ b/src/wp-includes/class-wp-theme-json-resolver.php @@ -515,7 +515,7 @@ public static function get_user_data_from_wp_global_styles( $theme, $create_post $global_style_query = new WP_Query(); $recent_posts = $global_style_query->query( $args ); - if ( count( $recent_posts ) === 1 ) { + if ( count( $recent_posts ) === 1 && $recent_posts[0] instanceof WP_Post ) { $user_cpt = get_object_vars( $recent_posts[0] ); } elseif ( $create_post ) { $cpt_post_id = wp_insert_post( @@ -532,7 +532,10 @@ public static function get_user_data_from_wp_global_styles( $theme, $create_post true ); if ( ! is_wp_error( $cpt_post_id ) ) { - $user_cpt = get_object_vars( get_post( $cpt_post_id ) ); + $post = get_post( $cpt_post_id ); + if ( $post instanceof WP_Post ) { + $user_cpt = get_object_vars( $post ); + } } } From 6269da7080f2fcab9707decee78fefc862c4ba47 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Mon, 22 Dec 2025 20:18:36 +0000 Subject: [PATCH 050/126] Script Loader: Fix script module `fetchpriority` calculation when dependent with higher priority is not enqueued. Developed in https://github.com/WordPress/wordpress-develop/pull/10651 Follow-up to [60931], [60704]. Props westonruter, jonsurrell, youknowriad. See #61734. Fixes #64429. git-svn-id: https://develop.svn.wordpress.org/trunk@61401 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/class-wp-script-modules.php | 6 +- src/wp-includes/class-wp-scripts.php | 2 +- tests/phpunit/tests/dependencies/scripts.php | 46 ++++++++++++++ .../tests/script-modules/wpScriptModules.php | 60 ++++++++++++++++--- 4 files changed, 102 insertions(+), 12 deletions(-) diff --git a/src/wp-includes/class-wp-script-modules.php b/src/wp-includes/class-wp-script-modules.php index ff3973999581b..6889b5f09a166 100644 --- a/src/wp-includes/class-wp-script-modules.php +++ b/src/wp-includes/class-wp-script-modules.php @@ -461,9 +461,9 @@ private function print_script_module( string $id ) { 'id' => $id . '-js-module', ); - $script_module = $this->registered[ $id ]; - $dependents = $this->get_recursive_dependents( $id ); - $fetchpriority = $this->get_highest_fetchpriority( array_merge( array( $id ), $dependents ) ); + $script_module = $this->registered[ $id ]; + $queued_dependents = array_intersect( $this->queue, $this->get_recursive_dependents( $id ) ); + $fetchpriority = $this->get_highest_fetchpriority( array_merge( array( $id ), $queued_dependents ) ); if ( 'auto' !== $fetchpriority ) { $attributes['fetchpriority'] = $fetchpriority; } diff --git a/src/wp-includes/class-wp-scripts.php b/src/wp-includes/class-wp-scripts.php index 03829a20bde63..7628db0a875b7 100644 --- a/src/wp-includes/class-wp-scripts.php +++ b/src/wp-includes/class-wp-scripts.php @@ -1092,7 +1092,7 @@ private function filter_eligible_strategies( $handle, $eligible_strategies = nul * * @since 6.9.0 * @see self::filter_eligible_strategies() - * @see WP_Script_Modules::get_highest_fetchpriority_with_dependents() + * @see WP_Script_Modules::get_highest_fetchpriority() * * @param string $handle Script module ID. * @param array $checked Optional. An array of already checked script handles, used to avoid recursive loops. diff --git a/tests/phpunit/tests/dependencies/scripts.php b/tests/phpunit/tests/dependencies/scripts.php index c4983b82a4ede..5975149a6e675 100644 --- a/tests/phpunit/tests/dependencies/scripts.php +++ b/tests/phpunit/tests/dependencies/scripts.php @@ -1516,6 +1516,30 @@ public function test_highest_fetchpriority_with_dependents_uses_cached_result() ); } + /** + * Tests expected priority is used when a dependent is registered but not enqueued. + * + * @ticket 64429 + * + * @covers WP_Scripts::print_scripts + * @covers WP_Scripts::get_highest_fetchpriority_with_dependents + */ + public function test_priority_of_dependency_for_non_enqueued_dependent() { + $wp_scripts = wp_scripts(); + wp_default_scripts( $wp_scripts ); + + $wp_scripts->add( 'not-enqueued', 'https://example.com/not-enqueued.js', array( 'comment-reply' ), null, array( 'priority' => 'high' ) ); + $wp_scripts->enqueue( 'comment-reply' ); + + $actual = $this->normalize_markup_for_snapshot( get_echo( array( $wp_scripts, 'print_scripts' ) ) ); + $this->assertEqualHTML( + '', + $actual, + '', + "Snapshot:\n$actual" + ); + } + /** * Tests that printing a script without enqueueing has the same output as when it is enqueued. * @@ -4256,4 +4280,26 @@ public function data_varying_versions_handle_args() { ), ); } + + /** + * Normalizes markup for snapshot. + * + * @param string $markup Markup. + * @return string Normalized markup. + */ + private function normalize_markup_for_snapshot( string $markup ): string { + $processor = new WP_HTML_Tag_Processor( $markup ); + $clean_url = static function ( string $url ): string { + $url = preg_replace( '#^https?://[^/]+#', '', $url ); + return remove_query_arg( 'ver', $url ); + }; + while ( $processor->next_tag() ) { + if ( 'LINK' === $processor->get_tag() && is_string( $processor->get_attribute( 'href' ) ) ) { + $processor->set_attribute( 'href', $clean_url( $processor->get_attribute( 'href' ) ) ); + } elseif ( 'SCRIPT' === $processor->get_tag() && is_string( $processor->get_attribute( 'src' ) ) ) { + $processor->set_attribute( 'src', $clean_url( $processor->get_attribute( 'src' ) ) ); + } + } + return $processor->get_updated_html(); + } } diff --git a/tests/phpunit/tests/script-modules/wpScriptModules.php b/tests/phpunit/tests/script-modules/wpScriptModules.php index aafaa47cc35e6..4b103953c8451 100644 --- a/tests/phpunit/tests/script-modules/wpScriptModules.php +++ b/tests/phpunit/tests/script-modules/wpScriptModules.php @@ -1553,24 +1553,46 @@ public function test_set_fetchpriority_with_invalid_value() { */ public function data_provider_to_test_fetchpriority_bumping(): array { return array( - 'enqueue_bajo' => array( + 'enqueue_bajo' => array( 'enqueues' => array( 'bajo' ), + 'expected' => array( + 'preload_links' => array(), + 'script_tags' => array( + 'bajo' => array( + 'url' => '/bajo.js', + 'fetchpriority' => 'low', // Priority of 'low' not 'high' because the 'auto' dependent was not enqueued. + 'in_footer' => false, + ), + ), + 'import_map' => array( + 'dyno' => '/dyno.js', + ), + ), + ), + 'enqueue_bajo_and_auto' => array( + 'enqueues' => array( 'bajo', 'auto' ), 'expected' => array( 'preload_links' => array(), 'script_tags' => array( 'bajo' => array( 'url' => '/bajo.js', - 'fetchpriority' => 'high', + 'fetchpriority' => 'auto', 'in_footer' => false, 'data-wp-fetchpriority' => 'low', ), + 'auto' => array( + 'url' => '/auto.js', + 'fetchpriority' => 'auto', + 'in_footer' => false, + ), ), 'import_map' => array( 'dyno' => '/dyno.js', + 'bajo' => '/bajo.js', ), ), ), - 'enqueue_auto' => array( + 'enqueue_auto' => array( 'enqueues' => array( 'auto' ), 'expected' => array( 'preload_links' => array( @@ -1582,10 +1604,9 @@ public function data_provider_to_test_fetchpriority_bumping(): array { ), 'script_tags' => array( 'auto' => array( - 'url' => '/auto.js', - 'fetchpriority' => 'high', - 'in_footer' => false, - 'data-wp-fetchpriority' => 'auto', + 'url' => '/auto.js', + 'fetchpriority' => 'auto', // Priority of 'auto' not 'high' because the 'alto' dependent was not enqueued. + 'in_footer' => false, ), ), 'import_map' => array( @@ -1594,7 +1615,7 @@ public function data_provider_to_test_fetchpriority_bumping(): array { ), ), ), - 'enqueue_alto' => array( + 'enqueue_alto' => array( 'enqueues' => array( 'alto' ), 'expected' => array( 'preload_links' => array( @@ -1829,6 +1850,29 @@ public function test_default_script_modules() { ); } + /** + * Tests expected priority is used when a dependent is registered but not enqueued. + * + * @ticket 64429 + * + * @covers ::wp_default_script_modules + * @covers WP_Script_Modules::print_enqueued_script_modules + * @covers WP_Script_Modules::get_highest_fetchpriority + */ + public function test_priority_of_dependency_for_non_enqueued_dependent() { + wp_default_script_modules(); + wp_register_script_module( 'not-enqueued', 'https://example.com/not-enqueued.js', array( '@wordpress/a11y' ), null, array( 'priority' => 'high' ) ); + wp_enqueue_script_module( '@wordpress/a11y' ); + + $actual = $this->normalize_markup_for_snapshot( get_echo( array( wp_script_modules(), 'print_enqueued_script_modules' ) ) ); + $this->assertEqualHTML( + '', + $actual, + '', + "Snapshot:\n$actual" + ); + } + /** * Tests that a dependent with high priority for default script modules with a low fetch priority are printed as expected. * From a3460db276f9b982a037ca3259b795df2a82e22b Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Mon, 22 Dec 2025 20:43:17 +0000 Subject: [PATCH 051/126] Docs: Improve specificity of PHP types in `functions.wp-scripts.php` and `functions.wp-styles.php`. These files now adhere to PHPStan level 8. Developed in https://github.com/WordPress/wordpress-develop/pull/10652 Follow-up to [61362], [61358]. See #64238. git-svn-id: https://develop.svn.wordpress.org/trunk@61402 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/functions.wp-scripts.php | 46 ++++++++++++------------ src/wp-includes/functions.wp-styles.php | 4 +-- 2 files changed, 25 insertions(+), 25 deletions(-) diff --git a/src/wp-includes/functions.wp-scripts.php b/src/wp-includes/functions.wp-scripts.php index f86b456d5f69a..f1a9b2afd6b7c 100644 --- a/src/wp-includes/functions.wp-scripts.php +++ b/src/wp-includes/functions.wp-scripts.php @@ -141,7 +141,7 @@ function wp_add_inline_script( $handle, $data, $position = 'after' ) { ), '4.5.0' ); - $data = trim( preg_replace( '#]*>(.*)#is', '$1', $data ) ); + $data = trim( (string) preg_replace( '#]*>(.*)#is', '$1', $data ) ); } return wp_scripts()->add_inline_script( $handle, $data, $position ); @@ -160,15 +160,15 @@ function wp_add_inline_script( $handle, $data, $position = 'after' ) { * @since 6.3.0 The $in_footer parameter of type boolean was overloaded to be an $args parameter of type array. * @since 6.9.0 The $fetchpriority parameter of type string was added to the $args parameter of type array. * - * @param string $handle Name of the script. Should be unique. - * @param string|false $src Full URL of the script, or path of the script relative to the WordPress root directory. - * If source is set to false, script is an alias of other scripts it depends on. - * @param string[] $deps Optional. An array of registered script handles this script depends on. Default empty array. - * @param string|bool|null $ver Optional. String specifying script version number, if it has one, which is added to the URL - * as a query string for cache busting purposes. If version is set to false, a version - * number is automatically added equal to current installed WordPress version. - * If set to null, no version is added. - * @param array|bool $args { + * @param string $handle Name of the script. Should be unique. + * @param string|false $src Full URL of the script, or path of the script relative to the WordPress root directory. + * If source is set to false, script is an alias of other scripts it depends on. + * @param string[] $deps Optional. An array of registered script handles this script depends on. Default empty array. + * @param string|bool|null $ver Optional. String specifying script version number, if it has one, which is added to the URL + * as a query string for cache busting purposes. If version is set to false, a version + * number is automatically added equal to current installed WordPress version. + * If set to null, no version is added. + * @param array|bool $args { * Optional. An array of additional script loading strategies. Default empty array. * Otherwise, it may be a boolean in which case it determines whether the script is printed in the footer. Default false. * @@ -221,10 +221,10 @@ function wp_register_script( $handle, $src, $deps = array(), $ver = false, $args * * @todo Documentation cleanup * - * @param string $handle Script handle the data will be attached to. - * @param string $object_name Name for the JavaScript object. Passed directly, so it should be qualified JS variable. - * Example: '/[a-zA-Z0-9_]+/'. - * @param array $l10n The data itself. The data can be either a single or multi-dimensional array. + * @param string $handle Script handle the data will be attached to. + * @param string $object_name Name for the JavaScript object. Passed directly, so it should be qualified JS variable. + * Example: '/[a-zA-Z0-9_]+/'. + * @param array $l10n The data itself. The data can be either a single or multi-dimensional array. * @return bool True if the script was successfully localized, false otherwise. */ function wp_localize_script( $handle, $object_name, $l10n ) { @@ -346,15 +346,15 @@ function wp_deregister_script( $handle ) { * @since 6.3.0 The $in_footer parameter of type boolean was overloaded to be an $args parameter of type array. * @since 6.9.0 The $fetchpriority parameter of type string was added to the $args parameter of type array. * - * @param string $handle Name of the script. Should be unique. - * @param string $src Full URL of the script, or path of the script relative to the WordPress root directory. - * Default empty. - * @param string[] $deps Optional. An array of registered script handles this script depends on. Default empty array. - * @param string|bool|null $ver Optional. String specifying script version number, if it has one, which is added to the URL - * as a query string for cache busting purposes. If version is set to false, a version - * number is automatically added equal to current installed WordPress version. - * If set to null, no version is added. - * @param array|bool $args { + * @param string $handle Name of the script. Should be unique. + * @param string $src Full URL of the script, or path of the script relative to the WordPress root directory. + * Default empty. + * @param string[] $deps Optional. An array of registered script handles this script depends on. Default empty array. + * @param string|bool|null $ver Optional. String specifying script version number, if it has one, which is added to the URL + * as a query string for cache busting purposes. If version is set to false, a version + * number is automatically added equal to current installed WordPress version. + * If set to null, no version is added. + * @param array|bool $args { * Optional. An array of additional script loading strategies. Default empty array. * Otherwise, it may be a boolean in which case it determines whether the script is printed in the footer. Default false. * diff --git a/src/wp-includes/functions.wp-styles.php b/src/wp-includes/functions.wp-styles.php index f84b931866818..903097c313a4a 100644 --- a/src/wp-includes/functions.wp-styles.php +++ b/src/wp-includes/functions.wp-styles.php @@ -38,7 +38,7 @@ function wp_styles() { * * @global WP_Styles $wp_styles The WP_Styles object for printing styles. * - * @param string|bool|array $handles Styles to be printed. Default 'false'. + * @param string|false|string[] $handles Styles to be printed. Default 'false'. * @return string[] On success, an array of handles of processed WP_Dependencies items; otherwise, an empty array. */ function wp_print_styles( $handles = false ) { @@ -98,7 +98,7 @@ function wp_add_inline_style( $handle, $data ) { ), '3.7.0' ); - $data = trim( preg_replace( '#]*>(.*)#is', '$1', $data ) ); + $data = trim( (string) preg_replace( '#]*>(.*)#is', '$1', $data ) ); } return wp_styles()->add_inline_style( $handle, $data ); From cfb4181067f382afd020aa654172241fb698d9f7 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Mon, 22 Dec 2025 23:12:59 +0000 Subject: [PATCH 052/126] Code Modernization: Replace some `isset()` ternary checks with null coalescing. Since PHP 7.0 introduced the [https://www.php.net/manual/en/migration70.new-features.php#migration70.new-features.null-coalesce-op null coalescing operator], and WordPress now requires at least PHP 7.2.24, `isset( $var ) ? $var : null` ternary checks can be safely replaced with the more concise `$var ?? null` syntax. As some new code using the null coalescing operator has already been introduced into core in recent releases, this commit continues with the code modernization by implementing incremental changes for easier review. Props seanwei, getsyash, krupalpanchal, wildworks, jorbin, SergeyBiryukov. Fixes #63430. See #58874. git-svn-id: https://develop.svn.wordpress.org/trunk@61403 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/class-wp-comment-query.php | 12 ++++---- .../class-wp-customize-manager.php | 14 +++++----- .../class-wp-http-requests-response.php | 8 +++--- src/wp-includes/class-wp-network-query.php | 12 ++++---- src/wp-includes/class-wp-query.php | 28 +++++++++---------- src/wp-includes/class-wp-site-query.php | 12 ++++---- src/wp-includes/class-wp-term-query.php | 14 +++++----- 7 files changed, 50 insertions(+), 50 deletions(-) diff --git a/src/wp-includes/class-wp-comment-query.php b/src/wp-includes/class-wp-comment-query.php index b2a9275c525c8..cfabfd7e6b964 100644 --- a/src/wp-includes/class-wp-comment-query.php +++ b/src/wp-includes/class-wp-comment-query.php @@ -949,12 +949,12 @@ protected function get_comment_ids() { */ $clauses = apply_filters_ref_array( 'comments_clauses', array( compact( $pieces ), &$this ) ); - $fields = isset( $clauses['fields'] ) ? $clauses['fields'] : ''; - $join = isset( $clauses['join'] ) ? $clauses['join'] : ''; - $where = isset( $clauses['where'] ) ? $clauses['where'] : ''; - $orderby = isset( $clauses['orderby'] ) ? $clauses['orderby'] : ''; - $limits = isset( $clauses['limits'] ) ? $clauses['limits'] : ''; - $groupby = isset( $clauses['groupby'] ) ? $clauses['groupby'] : ''; + $fields = $clauses['fields'] ?? ''; + $join = $clauses['join'] ?? ''; + $where = $clauses['where'] ?? ''; + $orderby = $clauses['orderby'] ?? ''; + $limits = $clauses['limits'] ?? ''; + $groupby = $clauses['groupby'] ?? ''; $this->filtered_where_clause = $where; diff --git a/src/wp-includes/class-wp-customize-manager.php b/src/wp-includes/class-wp-customize-manager.php index 3026d3b039136..6ecc5c33e3fca 100644 --- a/src/wp-includes/class-wp-customize-manager.php +++ b/src/wp-includes/class-wp-customize-manager.php @@ -1226,9 +1226,9 @@ public function import_theme_starter_content( $starter_content = array() ) { $sidebars_widgets = isset( $starter_content['widgets'] ) && ! empty( $this->widgets ) ? $starter_content['widgets'] : array(); $attachments = isset( $starter_content['attachments'] ) && ! empty( $this->nav_menus ) ? $starter_content['attachments'] : array(); $posts = isset( $starter_content['posts'] ) && ! empty( $this->nav_menus ) ? $starter_content['posts'] : array(); - $options = isset( $starter_content['options'] ) ? $starter_content['options'] : array(); + $options = $starter_content['options'] ?? array(); $nav_menus = isset( $starter_content['nav_menus'] ) && ! empty( $this->nav_menus ) ? $starter_content['nav_menus'] : array(); - $theme_mods = isset( $starter_content['theme_mods'] ) ? $starter_content['theme_mods'] : array(); + $theme_mods = $starter_content['theme_mods'] ?? array(); // Widgets. $max_widget_numbers = array(); @@ -1495,7 +1495,7 @@ public function import_theme_starter_content( $starter_content = array() ) { $this->set_post_value( $nav_menu_setting_id, array( - 'name' => isset( $nav_menu['name'] ) ? $nav_menu['name'] : $nav_menu_location, + 'name' => $nav_menu['name'] ?? $nav_menu_location, ) ); $this->pending_starter_content_settings_ids[] = $nav_menu_setting_id; @@ -5239,10 +5239,10 @@ public function register_controls() { 'label' => __( 'Logo' ), 'section' => 'title_tagline', 'priority' => 8, - 'height' => isset( $custom_logo_args[0]['height'] ) ? $custom_logo_args[0]['height'] : null, - 'width' => isset( $custom_logo_args[0]['width'] ) ? $custom_logo_args[0]['width'] : null, - 'flex_height' => isset( $custom_logo_args[0]['flex-height'] ) ? $custom_logo_args[0]['flex-height'] : null, - 'flex_width' => isset( $custom_logo_args[0]['flex-width'] ) ? $custom_logo_args[0]['flex-width'] : null, + 'height' => $custom_logo_args[0]['height'] ?? null, + 'width' => $custom_logo_args[0]['width'] ?? null, + 'flex_height' => $custom_logo_args[0]['flex-height'] ?? null, + 'flex_width' => $custom_logo_args[0]['flex-width'] ?? null, 'button_labels' => array( 'select' => __( 'Select logo' ), 'change' => __( 'Change logo' ), diff --git a/src/wp-includes/class-wp-http-requests-response.php b/src/wp-includes/class-wp-http-requests-response.php index 8032c54d875a7..c27a3053f2183 100644 --- a/src/wp-includes/class-wp-http-requests-response.php +++ b/src/wp-includes/class-wp-http-requests-response.php @@ -164,10 +164,10 @@ public function get_cookies() { array( 'name' => $cookie->name, 'value' => urldecode( $cookie->value ), - 'expires' => isset( $cookie->attributes['expires'] ) ? $cookie->attributes['expires'] : null, - 'path' => isset( $cookie->attributes['path'] ) ? $cookie->attributes['path'] : null, - 'domain' => isset( $cookie->attributes['domain'] ) ? $cookie->attributes['domain'] : null, - 'host_only' => isset( $cookie->flags['host-only'] ) ? $cookie->flags['host-only'] : null, + 'expires' => $cookie->attributes['expires'] ?? null, + 'path' => $cookie->attributes['path'] ?? null, + 'domain' => $cookie->attributes['domain'] ?? null, + 'host_only' => $cookie->flags['host-only'] ?? null, ) ); } diff --git a/src/wp-includes/class-wp-network-query.php b/src/wp-includes/class-wp-network-query.php index 2ad05435a84cb..15600998adf4e 100644 --- a/src/wp-includes/class-wp-network-query.php +++ b/src/wp-includes/class-wp-network-query.php @@ -460,12 +460,12 @@ protected function get_network_ids() { */ $clauses = apply_filters_ref_array( 'networks_clauses', array( compact( $pieces ), &$this ) ); - $fields = isset( $clauses['fields'] ) ? $clauses['fields'] : ''; - $join = isset( $clauses['join'] ) ? $clauses['join'] : ''; - $where = isset( $clauses['where'] ) ? $clauses['where'] : ''; - $orderby = isset( $clauses['orderby'] ) ? $clauses['orderby'] : ''; - $limits = isset( $clauses['limits'] ) ? $clauses['limits'] : ''; - $groupby = isset( $clauses['groupby'] ) ? $clauses['groupby'] : ''; + $fields = $clauses['fields'] ?? ''; + $join = $clauses['join'] ?? ''; + $where = $clauses['where'] ?? ''; + $orderby = $clauses['orderby'] ?? ''; + $limits = $clauses['limits'] ?? ''; + $groupby = $clauses['groupby'] ?? ''; if ( $where ) { $where = 'WHERE ' . $where; diff --git a/src/wp-includes/class-wp-query.php b/src/wp-includes/class-wp-query.php index d29c5a43758d0..3268351e99347 100644 --- a/src/wp-includes/class-wp-query.php +++ b/src/wp-includes/class-wp-query.php @@ -3019,13 +3019,13 @@ public function get_posts() { */ $clauses = (array) apply_filters_ref_array( 'posts_clauses', array( compact( $pieces ), &$this ) ); - $where = isset( $clauses['where'] ) ? $clauses['where'] : ''; - $groupby = isset( $clauses['groupby'] ) ? $clauses['groupby'] : ''; - $join = isset( $clauses['join'] ) ? $clauses['join'] : ''; - $orderby = isset( $clauses['orderby'] ) ? $clauses['orderby'] : ''; - $distinct = isset( $clauses['distinct'] ) ? $clauses['distinct'] : ''; - $fields = isset( $clauses['fields'] ) ? $clauses['fields'] : ''; - $limits = isset( $clauses['limits'] ) ? $clauses['limits'] : ''; + $where = $clauses['where'] ?? ''; + $groupby = $clauses['groupby'] ?? ''; + $join = $clauses['join'] ?? ''; + $orderby = $clauses['orderby'] ?? ''; + $distinct = $clauses['distinct'] ?? ''; + $fields = $clauses['fields'] ?? ''; + $limits = $clauses['limits'] ?? ''; } /** @@ -3153,13 +3153,13 @@ public function get_posts() { */ $clauses = (array) apply_filters_ref_array( 'posts_clauses_request', array( compact( $pieces ), &$this ) ); - $where = isset( $clauses['where'] ) ? $clauses['where'] : ''; - $groupby = isset( $clauses['groupby'] ) ? $clauses['groupby'] : ''; - $join = isset( $clauses['join'] ) ? $clauses['join'] : ''; - $orderby = isset( $clauses['orderby'] ) ? $clauses['orderby'] : ''; - $distinct = isset( $clauses['distinct'] ) ? $clauses['distinct'] : ''; - $fields = isset( $clauses['fields'] ) ? $clauses['fields'] : ''; - $limits = isset( $clauses['limits'] ) ? $clauses['limits'] : ''; + $where = $clauses['where'] ?? ''; + $groupby = $clauses['groupby'] ?? ''; + $join = $clauses['join'] ?? ''; + $orderby = $clauses['orderby'] ?? ''; + $distinct = $clauses['distinct'] ?? ''; + $fields = $clauses['fields'] ?? ''; + $limits = $clauses['limits'] ?? ''; } if ( ! empty( $groupby ) ) { diff --git a/src/wp-includes/class-wp-site-query.php b/src/wp-includes/class-wp-site-query.php index d89be175045b4..52ae228d90af0 100644 --- a/src/wp-includes/class-wp-site-query.php +++ b/src/wp-includes/class-wp-site-query.php @@ -674,12 +674,12 @@ protected function get_site_ids() { */ $clauses = apply_filters_ref_array( 'sites_clauses', array( compact( $pieces ), &$this ) ); - $fields = isset( $clauses['fields'] ) ? $clauses['fields'] : ''; - $join = isset( $clauses['join'] ) ? $clauses['join'] : ''; - $where = isset( $clauses['where'] ) ? $clauses['where'] : ''; - $orderby = isset( $clauses['orderby'] ) ? $clauses['orderby'] : ''; - $limits = isset( $clauses['limits'] ) ? $clauses['limits'] : ''; - $groupby = isset( $clauses['groupby'] ) ? $clauses['groupby'] : ''; + $fields = $clauses['fields'] ?? ''; + $join = $clauses['join'] ?? ''; + $where = $clauses['where'] ?? ''; + $orderby = $clauses['orderby'] ?? ''; + $limits = $clauses['limits'] ?? ''; + $groupby = $clauses['groupby'] ?? ''; if ( $where ) { $where = 'WHERE ' . $where; diff --git a/src/wp-includes/class-wp-term-query.php b/src/wp-includes/class-wp-term-query.php index 9c308f3dc768e..a30d887aa56d1 100644 --- a/src/wp-includes/class-wp-term-query.php +++ b/src/wp-includes/class-wp-term-query.php @@ -727,13 +727,13 @@ public function get_terms() { */ $clauses = apply_filters( 'terms_clauses', compact( $pieces ), $taxonomies, $args ); - $fields = isset( $clauses['fields'] ) ? $clauses['fields'] : ''; - $join = isset( $clauses['join'] ) ? $clauses['join'] : ''; - $where = isset( $clauses['where'] ) ? $clauses['where'] : ''; - $distinct = isset( $clauses['distinct'] ) ? $clauses['distinct'] : ''; - $orderby = isset( $clauses['orderby'] ) ? $clauses['orderby'] : ''; - $order = isset( $clauses['order'] ) ? $clauses['order'] : ''; - $limits = isset( $clauses['limits'] ) ? $clauses['limits'] : ''; + $fields = $clauses['fields'] ?? ''; + $join = $clauses['join'] ?? ''; + $where = $clauses['where'] ?? ''; + $distinct = $clauses['distinct'] ?? ''; + $orderby = $clauses['orderby'] ?? ''; + $order = $clauses['order'] ?? ''; + $limits = $clauses['limits'] ?? ''; $fields_is_filtered = implode( ', ', $selects ) !== $fields; From 6f226806eb22a5265d35ab2b83e6ff233b812af3 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Tue, 23 Dec 2025 21:18:57 +0000 Subject: [PATCH 053/126] Code Modernization: Replace `isset()` with null coalescing in `WP_Roles::get_role()`. Since PHP 7.0 introduced the [https://www.php.net/manual/en/migration70.new-features.php#migration70.new-features.null-coalesce-op null coalescing operator], and WordPress now requires at least PHP 7.2.24, `isset( $var ) ? $var : null` ternary checks can be safely replaced with the more concise `$var ?? null` syntax. As some new code using the null coalescing operator has already been introduced into core in recent releases, this commit continues with the code modernization by implementing incremental changes for easier review. Follow-up to [2703], [61403]. Props dilipbheda, mukesh27, spacedmonkey, SergeyBiryukov. Fixes #63216. See #58874. git-svn-id: https://develop.svn.wordpress.org/trunk@61404 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/class-wp-roles.php | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/src/wp-includes/class-wp-roles.php b/src/wp-includes/class-wp-roles.php index f620fb5a05ac7..6f7a7fbc84ba4 100644 --- a/src/wp-includes/class-wp-roles.php +++ b/src/wp-includes/class-wp-roles.php @@ -268,11 +268,7 @@ public function remove_cap( $role, $cap ) { * @return WP_Role|null WP_Role object if found, null if the role does not exist. */ public function get_role( $role ) { - if ( isset( $this->role_objects[ $role ] ) ) { - return $this->role_objects[ $role ]; - } else { - return null; - } + return $this->role_objects[ $role ] ?? null; } /** From aad47726bf51200758ffa17857e6dd821e103155 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Wed, 24 Dec 2025 06:46:29 +0000 Subject: [PATCH 054/126] Export: Fix fatal error when passing `null` to `wxr_cdata()` by casting passed value to `string`. This ensures that `wp_is_valid_utf8()` does not cause a type error since it only accepts strings. Developed in https://github.com/WordPress/wordpress-develop/pull/10595 Follow-up to [60630]. Props hbhalodia, westonruter, desrosj, albigdd, jorbin. See #38044. Fixes #64347. git-svn-id: https://develop.svn.wordpress.org/trunk@61405 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/export.php | 4 +- tests/phpunit/tests/admin/exportWp.php | 151 +++++++++++++++++++++++++ 2 files changed, 154 insertions(+), 1 deletion(-) diff --git a/src/wp-admin/includes/export.php b/src/wp-admin/includes/export.php index 4fe697e7e6d4d..a77cb804f0780 100644 --- a/src/wp-admin/includes/export.php +++ b/src/wp-admin/includes/export.php @@ -239,10 +239,12 @@ function export_wp( $args = array() ) { * * @since 2.1.0 * - * @param string $str String to wrap in XML CDATA tag. + * @param string|null $str String to wrap in XML CDATA tag. May be null. * @return string */ function wxr_cdata( $str ) { + $str = (string) $str; + if ( ! wp_is_valid_utf8( $str ) ) { $str = utf8_encode( $str ); } diff --git a/tests/phpunit/tests/admin/exportWp.php b/tests/phpunit/tests/admin/exportWp.php index 059dcab1a8351..11c615af6f497 100644 --- a/tests/phpunit/tests/admin/exportWp.php +++ b/tests/phpunit/tests/admin/exportWp.php @@ -323,4 +323,155 @@ public function test_export_wp_includes_comments_when_not_filtered() { $comment_tags = $xml_obj->xpath( '//wp:comment' ); $this->assertCount( $comment_count, $comment_tags, 'Export should include all comments when not filtered.' ); } + + /** + * Tests that export handles posts with NULL postmeta values without fatal errors. + * + * @ticket 64347 + */ + public function test_export_with_null_postmeta_values() { + global $wpdb; + + $post_id = self::factory()->post->create( + array( + 'post_title' => 'Test Post with NULL Meta', + 'post_content' => 'Test content', + 'post_type' => 'post', + ) + ); + + // Add multiple types of postmeta values. + add_post_meta( $post_id, 'string_meta', 'normal string' ); + add_post_meta( $post_id, 'numeric_string_meta', 123 ); + add_post_meta( $post_id, 'empty_string_meta', '' ); + add_post_meta( + $post_id, + 'array_meta', + array( + 'key' => 'value', + ) + ); + + // Directly insert NULL and non-string values into postmeta. + $wpdb->insert( + $wpdb->postmeta, + array( + 'post_id' => $post_id, + 'meta_key' => 'null_meta', + 'meta_value' => null, + ), + array( '%d', '%s', '%s' ) + ); + + $xml = $this->get_the_export( + array( + 'content' => 'post', + ) + ); + + $this->assertNotFalse( $xml, 'Export should not fail with NULL postmeta values' ); + $this->assertGreaterThan( 0, count( $xml->channel->item ), 'Export should contain items' ); + + // Post should be present in export. + $found_post = false; + foreach ( $xml->channel->item as $item ) { + $wp_item = $item->children( 'wp', true ); + if ( (int) $wp_item->post_id === $post_id ) { + $found_post = true; + break; + } + } + + $this->assertTrue( $found_post, 'Post with NULL metadata should be included in export' ); + } + + /** + * Tests that export handles comments with NULL values without fatal errors. + * + * @ticket 64347 + */ + public function test_export_with_null_comment_values() { + global $wpdb; + + $post_id = self::factory()->post->create( + array( + 'post_title' => 'Test Post for Comments', + 'post_type' => 'post', + ) + ); + + $comment_id = self::factory()->comment->create( + array( + 'comment_post_ID' => $post_id, + 'comment_content' => 'Test comment', + ) + ); + + // Insert NULL comment meta. + $wpdb->insert( + $wpdb->commentmeta, + array( + 'comment_id' => $comment_id, + 'meta_key' => 'null_comment_meta', + 'meta_value' => null, + ), + array( '%d', '%s', '%s' ) + ); + + $xml = $this->get_the_export( + array( + 'content' => 'post', + ) + ); + + $this->assertNotFalse( $xml, 'Export should not fail with NULL comment meta values' ); + $this->assertGreaterThan( 0, count( $xml->channel->item ), 'Export should contain items' ); + } + + /** + * Tests that export handles term meta with NULL values without fatal errors. + * + * @ticket 64347 + */ + public function test_export_with_null_term_meta_values() { + global $wpdb; + + // Create term. + $term = self::factory()->term->create( + array( + 'taxonomy' => 'category', + 'name' => 'Test Category', + ) + ); + + $post_id = self::factory()->post->create( + array( + 'post_title' => 'Test Post with Category', + 'post_type' => 'post', + 'post_status' => 'publish', + ) + ); + + wp_set_object_terms( $post_id, $term, 'category' ); + + // Insert NULL term meta. + $wpdb->insert( + $wpdb->termmeta, + array( + 'term_id' => $term, + 'meta_key' => 'null_term_meta', + 'meta_value' => null, + ), + array( '%d', '%s', '%s' ) + ); + + $xml = $this->get_the_export( + array( + 'content' => 'all', + ) + ); + + $this->assertNotFalse( $xml, 'Export should not fail with NULL term meta values' ); + $this->assertGreaterThan( 0, count( $xml->channel->item ), 'Export should contain items' ); + } } From f34e265645242b7cb1a531501a97b115249eae98 Mon Sep 17 00:00:00 2001 From: John Blackbourn Date: Wed, 24 Dec 2025 17:06:43 +0000 Subject: [PATCH 055/126] Upgrade/Install: Correct and improve various docblocks relating to upgrades. See #64224 git-svn-id: https://develop.svn.wordpress.org/trunk@61406 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/class-wp-upgrader.php | 29 +++++++++++---------- 1 file changed, 15 insertions(+), 14 deletions(-) diff --git a/src/wp-admin/includes/class-wp-upgrader.php b/src/wp-admin/includes/class-wp-upgrader.php index eeb32b438cee2..695ce50bf0d7e 100644 --- a/src/wp-admin/includes/class-wp-upgrader.php +++ b/src/wp-admin/includes/class-wp-upgrader.php @@ -292,30 +292,32 @@ public function fs_connect( $directories = array(), $allow_relaxed_file_ownershi } /** - * Downloads a package. + * Downloads a package for a WordPress core, plugin, theme, or translation upgrade. * * @since 2.8.0 * @since 5.2.0 Added the `$check_signatures` parameter. * @since 5.5.0 Added the `$hook_extra` parameter. * - * @param string $package The URI of the package. If this is the full path to an - * existing local file, it will be returned untouched. + * @param string $package The URI of the package. May be a remote URL or local file path. If this is the full + * path to an existing local file, it will be returned untouched. * @param bool $check_signatures Whether to validate file signatures. Default false. * @param array $hook_extra Extra arguments to pass to the filter hooks. Default empty array. * @return string|WP_Error The full path to the downloaded package file, or a WP_Error object. */ public function download_package( $package, $check_signatures = false, $hook_extra = array() ) { /** - * Filters whether to return the package. + * Filters whether to download a package for a WordPress core, plugin, theme, or translation upgrade. + * + * Return a non-false value to short-circuit the download and return that value instead. * * @since 3.7.0 * @since 5.5.0 Added the `$hook_extra` parameter. * - * @param bool $reply Whether to bail without returning the package. - * Default false. - * @param string $package The package file name. - * @param WP_Upgrader $upgrader The WP_Upgrader instance. - * @param array $hook_extra Extra arguments passed to hooked filters. + * @param false|string|WP_Error $reply Whether to short-circuit the download, the path to the downloaded package, + * or a WP_Error object. Default false. + * @param string $package The package URI. May be a remote URL or local file path. + * @param WP_Upgrader $upgrader The WP_Upgrader instance. + * @param array $hook_extra Extra arguments passed to hooked filters. */ $reply = apply_filters( 'upgrader_pre_download', false, $package, $this, $hook_extra ); if ( false !== $reply ) { @@ -519,7 +521,6 @@ public function install_package( $args = array() ) { $args = wp_parse_args( $args, $defaults ); - // These were previously extract()'d. $source = $args['source']; $destination = $args['destination']; $clear_destination = $args['clear_destination']; @@ -592,10 +593,10 @@ public function install_package( $args = array() ) { * @since 2.8.0 * @since 4.4.0 The `$hook_extra` parameter became available. * - * @param string $source File source location. - * @param string $remote_source Remote file source location. - * @param WP_Upgrader $upgrader WP_Upgrader instance. - * @param array $hook_extra Extra arguments passed to hooked filters. + * @param string|WP_Error $source File source location or a WP_Error object. + * @param string $remote_source Remote file source location. + * @param WP_Upgrader $upgrader WP_Upgrader instance. + * @param array $hook_extra Extra arguments passed to hooked filters. */ $source = apply_filters( 'upgrader_source_selection', $source, $remote_source, $this, $args['hook_extra'] ); From 700accc4116e7c31464dca68bcff1014a3337f98 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Wed, 24 Dec 2025 23:51:16 +0000 Subject: [PATCH 056/126] Tests: Rename the `admin/includesUser.php` test file to be more descriptive. * Include the path, file name, and function name to better indicate the tested function. * Move `@covers` annotation to the test class level. Follow-up to [49109]. Props poena. See #53010. git-svn-id: https://develop.svn.wordpress.org/trunk@61407 602fd350-edb4-49c9-b593-d223f7449a82 --- ...r_WpIsAuthorizeApplicationPasswordRequestValid_Test.php} | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) rename tests/phpunit/tests/admin/{includesUser.php => Admin_Includes_User_WpIsAuthorizeApplicationPasswordRequestValid_Test.php} (94%) diff --git a/tests/phpunit/tests/admin/includesUser.php b/tests/phpunit/tests/admin/Admin_Includes_User_WpIsAuthorizeApplicationPasswordRequestValid_Test.php similarity index 94% rename from tests/phpunit/tests/admin/includesUser.php rename to tests/phpunit/tests/admin/Admin_Includes_User_WpIsAuthorizeApplicationPasswordRequestValid_Test.php index c4f6f0c9c1aeb..42bc1af3841f2 100644 --- a/tests/phpunit/tests/admin/includesUser.php +++ b/tests/phpunit/tests/admin/Admin_Includes_User_WpIsAuthorizeApplicationPasswordRequestValid_Test.php @@ -3,8 +3,10 @@ /** * @group admin * @group user + * + * @covers ::wp_is_authorize_application_password_request_valid */ -class Tests_Admin_IncludesUser extends WP_UnitTestCase { +class Admin_Includes_User_WpIsAuthorizeApplicationPasswordRequestValid_Test extends WP_UnitTestCase { /** * Test redirect URLs for application password authorization requests. @@ -12,8 +14,6 @@ class Tests_Admin_IncludesUser extends WP_UnitTestCase { * @ticket 42790 * @ticket 52617 * - * @covers ::wp_is_authorize_application_password_request_valid - * * @dataProvider data_is_authorize_application_password_request_valid * * @param array $request The request data to validate. From dbf08ef04928f15488fd0cdd7afb03f757797ca9 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Thu, 25 Dec 2025 23:30:19 +0000 Subject: [PATCH 057/126] Help/About: Simplify help text on Updates screen to account for third-party updates. Follow-up to [14837], [26818], [33704]. Props NekoJonez, costdev, oglekler, SergeyBiryukov. Fixes #57672. git-svn-id: https://develop.svn.wordpress.org/trunk@61408 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/update-core.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/wp-admin/update-core.php b/src/wp-admin/update-core.php index 308f7e661fb3e..564b22d431ab2 100644 --- a/src/wp-admin/update-core.php +++ b/src/wp-admin/update-core.php @@ -987,7 +987,7 @@ function do_undismiss_core_update() { $title = __( 'WordPress Updates' ); $parent_file = 'index.php'; -$updates_overview = '

' . __( 'On this screen, you can update to the latest version of WordPress, as well as update your themes, plugins, and translations from the WordPress.org repositories.' ) . '

'; +$updates_overview = '

' . __( 'On this screen, you can update to the latest version of WordPress, as well as update your themes, plugins, and translations.' ) . '

'; $updates_overview .= '

' . __( 'If an update is available, you᾿ll see a notification appear in the Toolbar and navigation menu.' ) . ' ' . __( 'Keeping your site updated is important for security. It also makes the internet a safer place for you and your readers.' ) . '

'; get_current_screen()->add_help_tab( From 27714773c0ca9f938634ae0e089b7ff7bc0d12e7 Mon Sep 17 00:00:00 2001 From: Jon Surrell Date: Fri, 26 Dec 2025 11:51:28 +0000 Subject: [PATCH 058/126] Tests: Update fonts tests to use semantic HTML comparison. This aims to make the tests more robust. Follow-up to [60295], [61391], [61392]. Props jonsurrell. See #64225. git-svn-id: https://develop.svn.wordpress.org/trunk@61409 602fd350-edb4-49c9-b593-d223f7449a82 --- .../fonts/font-face/wpFontFace/generateAndPrint.php | 4 ++-- .../tests/fonts/font-face/wpPrintFontFaces.php | 12 ++++++------ .../wpPrintFontFacesFromStyleVariations.php | 4 ++-- 3 files changed, 10 insertions(+), 10 deletions(-) diff --git a/tests/phpunit/tests/fonts/font-face/wpFontFace/generateAndPrint.php b/tests/phpunit/tests/fonts/font-face/wpFontFace/generateAndPrint.php index d10ea500e8707..a6454c11d1883 100644 --- a/tests/phpunit/tests/fonts/font-face/wpFontFace/generateAndPrint.php +++ b/tests/phpunit/tests/fonts/font-face/wpFontFace/generateAndPrint.php @@ -34,7 +34,7 @@ public function test_should_generate_and_print_given_fonts( array $fonts, $expec $style_element = "\n"; $expected_output = sprintf( $style_element, $expected ); - $this->expectOutputString( $expected_output ); - $font_face->generate_and_print( $fonts ); + $output = get_echo( array( $font_face, 'generate_and_print' ), array( $fonts ) ); + $this->assertEqualHTML( $expected_output, $output ); } } diff --git a/tests/phpunit/tests/fonts/font-face/wpPrintFontFaces.php b/tests/phpunit/tests/fonts/font-face/wpPrintFontFaces.php index 2fa64559c2049..71cd964ca1bd8 100644 --- a/tests/phpunit/tests/fonts/font-face/wpPrintFontFaces.php +++ b/tests/phpunit/tests/fonts/font-face/wpPrintFontFaces.php @@ -37,8 +37,8 @@ public function test_should_not_print_when_no_fonts() { public function test_should_print_given_fonts( array $fonts, $expected ) { $expected_output = $this->get_expected_styles_output( $expected ); - $this->expectOutputString( $expected_output ); - wp_print_font_faces( $fonts ); + $output = get_echo( 'wp_print_font_faces', array( $fonts ) ); + $this->assertEqualHTML( $expected_output, $output ); } public function test_should_escape_tags() { @@ -60,9 +60,9 @@ public function test_should_escape_tags() { CSS; - $this->expectOutputString( $expected_output ); - wp_print_font_faces( $fonts ); + $output = get_echo( 'wp_print_font_faces', array( $fonts ) ); + $this->assertEqualHTML( $expected_output, $output ); } public function test_should_print_fonts_in_merged_data() { @@ -71,8 +71,8 @@ public function test_should_print_fonts_in_merged_data() { $expected = $this->get_expected_fonts_for_fonts_block_theme( 'font_face_styles' ); $expected_output = $this->get_expected_styles_output( $expected ); - $this->expectOutputString( $expected_output ); - wp_print_font_faces(); + $output = get_echo( 'wp_print_font_faces' ); + $this->assertEqualHTML( $expected_output, $output ); } private function get_expected_styles_output( $styles ) { diff --git a/tests/phpunit/tests/fonts/font-face/wpPrintFontFacesFromStyleVariations.php b/tests/phpunit/tests/fonts/font-face/wpPrintFontFacesFromStyleVariations.php index a59ba882a4e86..5dd6304fd2f7b 100644 --- a/tests/phpunit/tests/fonts/font-face/wpPrintFontFacesFromStyleVariations.php +++ b/tests/phpunit/tests/fonts/font-face/wpPrintFontFacesFromStyleVariations.php @@ -43,8 +43,8 @@ public function test_should_print_fonts_in_style_variations() { $expected = $this->get_custom_style_variations( 'expected_styles' ); $expected_output = $this->get_expected_styles_output( $expected ); - $this->expectOutputString( $expected_output ); - wp_print_font_faces_from_style_variations(); + $output = get_echo( 'wp_print_font_faces_from_style_variations' ); + $this->assertEqualHTML( $expected_output, $output ); } private function get_expected_styles_output( $styles ) { From 4c803dd6022025986ad96f2cb2e2e5cecf7e39ec Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Fri, 26 Dec 2025 13:05:01 +0000 Subject: [PATCH 059/126] Plugins: Update plugin compatibility text to remove obsolete percentage-based number. Follow-up to [12157], [12407], [42631]. Props danieltj, bridgetwillard, davidbaumwald, subrataemfluence, garrett-eclipse, SergeyBiryukov. Fixes #44090. git-svn-id: https://develop.svn.wordpress.org/trunk@61410 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/update-core.php | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/wp-admin/update-core.php b/src/wp-admin/update-core.php index 564b22d431ab2..aab3bdd259528 100644 --- a/src/wp-admin/update-core.php +++ b/src/wp-admin/update-core.php @@ -526,19 +526,19 @@ function list_plugin_updates() { // Get plugin compat for running version of WordPress. if ( isset( $plugin_data->update->tested ) && version_compare( $plugin_data->update->tested, $cur_wp_version, '>=' ) ) { /* translators: %s: WordPress version. */ - $compat = '
' . sprintf( __( 'Compatibility with WordPress %s: 100%% (according to its author)' ), $cur_wp_version ); + $compat = '
' . sprintf( __( 'Compatibility with WordPress %s: Yes (according to its author)' ), $cur_wp_version ); } else { /* translators: %s: WordPress version. */ - $compat = '
' . sprintf( __( 'Compatibility with WordPress %s: Unknown' ), $cur_wp_version ); + $compat = '
' . sprintf( __( 'Compatibility with WordPress %s: Not tested' ), $cur_wp_version ); } // Get plugin compat for updated version of WordPress. if ( $core_update_version ) { if ( isset( $plugin_data->update->tested ) && version_compare( $plugin_data->update->tested, $core_update_version, '>=' ) ) { /* translators: %s: WordPress version. */ - $compat .= '
' . sprintf( __( 'Compatibility with WordPress %s: 100%% (according to its author)' ), $core_update_version ); + $compat .= '
' . sprintf( __( 'Compatibility with WordPress %s: Yes (according to its author)' ), $core_update_version ); } else { /* translators: %s: WordPress version. */ - $compat .= '
' . sprintf( __( 'Compatibility with WordPress %s: Unknown' ), $core_update_version ); + $compat .= '
' . sprintf( __( 'Compatibility with WordPress %s: Not tested' ), $core_update_version ); } } From 87dbee1bf6f58e6c065a1cf1464f79f599e59415 Mon Sep 17 00:00:00 2001 From: Jon Surrell Date: Fri, 26 Dec 2025 13:14:22 +0000 Subject: [PATCH 060/126] Scripts: Remove default type attribute from tags. `SCRIPT`, `STYLE`, and stylesheet `LINK` tags do not require a type attribute since the HTML5 standard was released in 2008. Removing the type attribute simplifies logic and normalizes the produced HTML content. Developed in https://github.com/WordPress/wordpress-develop/pull/10658. Follow-up to [46164]. Props hardikhuptechdev, jonsurrell, dmsnell, westonruter. Fixes #64428. See #59883, #64442. git-svn-id: https://develop.svn.wordpress.org/trunk@61411 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-activate.php | 2 +- src/wp-admin/includes/ajax-actions.php | 2 +- src/wp-admin/includes/plugin-install.php | 2 +- src/wp-admin/includes/privacy-tools.php | 2 +- .../themes/twentyeleven/functions.php | 2 +- src/wp-content/themes/twentyeleven/header.php | 2 +- .../twentyfifteen/inc/custom-header.php | 2 +- .../twentyfourteen/inc/custom-header.php | 2 +- .../themes/twentynineteen/functions.php | 2 +- .../themes/twentyseventeen/functions.php | 2 +- .../twentyseventeen/inc/custom-header.php | 2 +- .../themes/twentysixteen/inc/customizer.php | 2 +- src/wp-content/themes/twentyten/functions.php | 2 +- src/wp-content/themes/twentyten/header.php | 2 +- .../twentythirteen/inc/custom-header.php | 2 +- .../themes/twentytwelve/inc/custom-header.php | 2 +- src/wp-includes/class-wp-styles.php | 37 +- src/wp-includes/deprecated.php | 14 +- src/wp-includes/fonts/class-wp-font-face.php | 45 +- src/wp-includes/functions.php | 2 +- src/wp-includes/general-template.php | 4 +- src/wp-includes/media.php | 4 +- src/wp-includes/ms-deprecated.php | 2 +- src/wp-includes/script-loader.php | 32 +- src/wp-includes/theme-compat/header.php | 4 +- src/wp-includes/theme.php | 7 +- .../class-wp-widget-recent-comments.php | 7 +- src/wp-login.php | 2 +- src/wp-signup.php | 2 +- tests/phpunit/tests/dependencies/scripts.php | 560 +++++++++--------- tests/phpunit/tests/dependencies/styles.php | 60 +- .../tests/dependencies/wpInlineScriptTag.php | 2 +- .../font-face/wpFontFace/generateAndPrint.php | 2 +- .../fonts/font-face/wpPrintFontFaces.php | 4 +- .../wpPrintFontFacesFromStyleVariations.php | 2 +- ...pPrivacyGeneratePersonalDataExportFile.php | 2 +- 36 files changed, 359 insertions(+), 467 deletions(-) diff --git a/src/wp-activate.php b/src/wp-activate.php index 0c3321f74618c..103df0364e973 100644 --- a/src/wp-activate.php +++ b/src/wp-activate.php @@ -100,7 +100,7 @@ function do_activate_header() { */ function wpmu_activate_stylesheet() { ?> - - - \n", + "\n", esc_attr( $handle ), - $this->type_attr, $inline_style ); } else { @@ -232,12 +206,11 @@ public function do_item( $handle, $group = false ) { $title = isset( $obj->extra['title'] ) ? $obj->extra['title'] : ''; $tag = sprintf( - "\n", + "\n", $rel, esc_attr( $handle ), $title ? sprintf( " title='%s'", esc_attr( $title ) ) : '', $href, - $this->type_attr, esc_attr( $media ) ); @@ -264,12 +237,11 @@ public function do_item( $handle, $group = false ) { } $rtl_tag = sprintf( - "\n", + "\n", $rel, esc_attr( $handle ), $title ? sprintf( " title='%s'", esc_attr( $title ) ) : '', $rtl_href, - $this->type_attr, esc_attr( $media ) ); @@ -365,9 +337,8 @@ public function print_inline_style( $handle, $display = true ) { } printf( - "\n", + "\n", esc_attr( $handle ), - $this->type_attr, $output ); diff --git a/src/wp-includes/deprecated.php b/src/wp-includes/deprecated.php index 2569e5ad308c0..0b721715120de 100644 --- a/src/wp-includes/deprecated.php +++ b/src/wp-includes/deprecated.php @@ -5897,10 +5897,9 @@ function _wp_theme_json_webfonts_handler() { function print_embed_styles() { _deprecated_function( __FUNCTION__, '6.4.0', 'wp_enqueue_embed_styles' ); - $type_attr = current_theme_supports( 'html5', 'style' ) ? '' : ' type="text/css"'; - $suffix = SCRIPT_DEBUG ? '' : '.min'; + $suffix = SCRIPT_DEBUG ? '' : '.min'; ?> - > + - > + + - media="screen"> + \n"; - } - - /** - * Gets the defined \n"; } /** diff --git a/src/wp-includes/functions.php b/src/wp-includes/functions.php index ee10bb78e1d37..cfec0b6df6d45 100644 --- a/src/wp-includes/functions.php +++ b/src/wp-includes/functions.php @@ -3921,7 +3921,7 @@ function _default_wp_die_handler( $message, $title = '', $args = array() ) { } ?> <?php echo $title; ?> - \n"; @@ -2905,13 +2903,6 @@ function wp_sanitize_script_attributes( $attributes ) { * @return string String containing `\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); @@ -172,7 +172,7 @@ public function test_after_inline_script_with_delayed_main_script( $strategy ) { wp_enqueue_script( 'ms-isa-1', 'http://example.org/ms-isa-1.js', array(), null, compact( 'strategy' ) ); wp_add_inline_script( 'ms-isa-1', 'console.log(\'after one\');', 'after' ); $output = get_echo( 'wp_print_scripts' ); - $expected = "\n"; + $expected = "\n"; $expected .= wp_get_inline_script_tag( "console.log('after one');\n//# sourceURL=ms-isa-1-js-after", array( @@ -185,9 +185,6 @@ public function test_after_inline_script_with_delayed_main_script( $strategy ) { /** * Tests that inline scripts in the `after` position, attached to a blocking main script, are rendered as javascript. * - * If a main script with a `blocking` strategy has an `after` inline script, - * the inline script should be rendered as type='text/javascript'. - * * @ticket 12009 * * @covers WP_Scripts::do_item @@ -200,7 +197,7 @@ public function test_after_inline_script_with_blocking_main_script() { wp_add_inline_script( 'ms-insa-3', 'console.log(\'after one\');', 'after' ); $output = get_echo( 'wp_print_scripts' ); - $expected = "\n"; + $expected = "\n"; $expected .= wp_get_inline_script_tag( "console.log('after one');\n//# sourceURL=ms-insa-3-js-after", array( @@ -241,17 +238,16 @@ public function test_before_inline_scripts_with_delayed_main_script( $strategy ) 'id' => 'ds-i1-1-js-before', ) ); - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $expected .= wp_get_inline_script_tag( "console.log('before last');\n//# sourceURL=ms-i1-1-js-before", array( - 'id' => 'ms-i1-1-js-before', - 'type' => 'text/javascript', + 'id' => 'ms-i1-1-js-before', ) ); - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, $output, '', 'Inline scripts in the "before" position, that are attached to a deferred main script, are failing to print/execute.' ); } @@ -270,7 +266,7 @@ public function test_loading_strategy_with_valid_async_registration() { // No dependents, No dependencies then async. wp_enqueue_script( 'main-script-a1', '/main-script-a1.js', array(), null, array( 'strategy' => 'async' ) ); $output = get_echo( 'wp_print_scripts' ); - $expected = "\n"; + $expected = "\n"; $this->assertEqualHTML( $expected, $output, '', 'Scripts enqueued with an async loading strategy are failing to have the async attribute applied to the script handle when being printed.' ); } @@ -292,8 +288,8 @@ public function test_delayed_dependent_with_blocking_dependency( $strategy ) { wp_enqueue_script( 'dependency-script-a2', '/dependency-script-a2.js', array(), null ); wp_enqueue_script( 'main-script-a2', '/main-script-a2.js', array( 'dependency-script-a2' ), null, compact( 'strategy' ) ); $output = get_echo( 'wp_print_scripts' ); - $expected = "\n"; - $expected .= ""; + $expected = "\n"; + $expected .= ""; $this->assertEqualHTML( $expected, $output, '', 'Dependents of a blocking dependency are free to have any strategy.' ); } @@ -315,8 +311,8 @@ public function test_blocking_dependent_with_delayed_dependency( $strategy ) { wp_enqueue_script( 'dependent-script-a3', '/dependent-script-a3.js', array( 'main-script-a3' ), null ); $output = get_echo( 'wp_print_scripts' ); $expected = << - + + JS; $this->assertEqualHTML( $expected, $output, '', 'Blocking dependents must force delayed dependencies to become blocking.' ); } @@ -566,27 +562,27 @@ public function data_provider_to_test_various_strategy_dependency_chains() { } }, 'expected_markup' => << + - - + - - - + - - + - - - + - - - + - - + - - - + - - + - - - + - - - - + - - + - - - + - - - + - - - - + - - + - - - + - - - + - - + - - - + - - - + - - + - - - + - + HTML , ), @@ -1068,8 +1064,8 @@ public function data_provider_to_test_various_strategy_dependency_chains() { $this->add_test_inline_script( $handle, 'after' ); }, 'expected_markup' => << - + - - + + + HTML , ), @@ -1114,17 +1110,17 @@ public function data_provider_to_test_various_strategy_dependency_chains() { $this->add_test_inline_script( 'defer-dependent-of-nested-aliases', 'after' ); }, 'expected_markup' => << - - - + + + - - + - - + + + HTML , ), @@ -1280,10 +1276,10 @@ public function test_defer_with_async_dependent() { ); // Note: All of these scripts have fetchpriority=high because the leaf dependent script has that fetch priority. $output = get_echo( 'wp_print_scripts' ); - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, $output, '', 'Scripts registered as defer but that have dependents that are async are expected to have said dependents deferred.' ); } @@ -1399,21 +1395,21 @@ public function data_provider_to_test_fetchpriority_bumping(): array { return array( 'enqueue_bajo' => array( 'enqueues' => array( 'bajo' ), - 'expected' => '', + 'expected' => '', ), 'enqueue_auto' => array( 'enqueues' => array( 'auto' ), 'expected' => ' - - + + ', ), 'enqueue_alto' => array( 'enqueues' => array( 'alto' ), 'expected' => ' - - - + + + ', ), ); @@ -1469,14 +1465,14 @@ public function test_fetchpriority_bumping_a_to_z() { $actual = get_echo( 'wp_print_scripts' ); $expected = ' - - - - - - - - + + + + + + + + '; $this->assertEqualHTML( $expected, $actual, '', "Snapshot:\n$actual" ); } @@ -1533,7 +1529,7 @@ public function test_priority_of_dependency_for_non_enqueued_dependent() { $actual = $this->normalize_markup_for_snapshot( get_echo( array( $wp_scripts, 'print_scripts' ) ) ); $this->assertEqualHTML( - '', + '', $actual, '', "Snapshot:\n$actual" @@ -1570,7 +1566,7 @@ public function test_printing_default_script_comment_reply_enqueued_or_not_enque $this->assertEqualHTML( sprintf( - '', + '', includes_url( 'js/comment-reply.js' ) ), $markup @@ -1610,7 +1606,7 @@ public function test_loading_strategy_with_invalid_defer_registration() { wp_enqueue_script( 'dependent-script-d4-2', '/dependent-script-d4-2.js', array( 'dependent-script-d4-1' ), null ); wp_enqueue_script( 'dependent-script-d4-3', '/dependent-script-d4-3.js', array( 'dependent-script-d4-2' ), null, array( 'strategy' => 'defer' ) ); $output = get_echo( 'wp_print_scripts' ); - $expected = str_replace( "'", '"', "\n" ); + $expected = str_replace( "'", '"', "\n" ); $this->assertStringContainsString( $expected, $output, 'Scripts registered as defer but that have all dependents with no strategy, should become blocking (no strategy).' ); } @@ -1627,13 +1623,13 @@ public function test_loading_strategy_with_invalid_defer_registration() { public function test_loading_strategy_with_valid_blocking_registration() { wp_enqueue_script( 'main-script-b1', '/main-script-b1.js', array(), null ); $output = get_echo( 'wp_print_scripts' ); - $expected = "\n"; + $expected = "\n"; $this->assertEqualHTML( $expected, $output, '', 'Scripts registered with a "blocking" strategy, and who have no dependencies, should have no loading strategy attributes printed.' ); // strategy args not set. wp_enqueue_script( 'main-script-b2', '/main-script-b2.js', array(), null, array() ); $output = get_echo( 'wp_print_scripts' ); - $expected = "\n"; + $expected = "\n"; $this->assertEqualHTML( $expected, $output, '', 'Scripts registered with no strategy assigned, and who have no dependencies, should have no loading strategy attributes printed.' ); } @@ -1690,10 +1686,10 @@ public function test_scripts_targeting_head() { $actual_header = get_echo( 'wp_print_head_scripts' ); $actual_footer = get_echo( 'wp_print_scripts' ); - $expected_header = "\n"; - $expected_header .= "\n"; - $expected_header .= "\n"; - $expected_header .= "\n"; + $expected_header = "\n"; + $expected_header .= "\n"; + $expected_header .= "\n"; + $expected_header .= "\n"; $this->assertEqualHTML( $expected_header, $actual_header, '', 'Scripts registered/enqueued using the older $in_footer parameter or the newer $args parameter should have the same outcome.' ); $this->assertEmpty( $actual_footer, 'Expected footer to be empty since all scripts were for head.' ); @@ -1717,10 +1713,10 @@ public function test_scripts_targeting_footer() { $actual_header = get_echo( 'wp_print_head_scripts' ); $actual_footer = get_echo( 'wp_print_scripts' ); - $expected_footer = "\n"; - $expected_footer .= "\n"; - $expected_footer .= "\n"; - $expected_footer .= "\n"; + $expected_footer = "\n"; + $expected_footer .= "\n"; + $expected_footer .= "\n"; + $expected_footer .= "\n"; $this->assertEmpty( $actual_header, 'Expected header to be empty since all scripts targeted footer.' ); $this->assertEqualHTML( $expected_footer, $actual_footer, '', 'Scripts registered/enqueued using the older $in_footer parameter or the newer $args parameter should have the same outcome.' ); @@ -1843,7 +1839,7 @@ public function test_script_strategy_doing_it_wrong_via_register() { wp_enqueue_script( 'invalid-strategy' ); $this->assertEqualHTML( - "\n", + "\n", get_echo( 'wp_print_scripts' ) ); } @@ -1868,7 +1864,7 @@ public function test_script_strategy_doing_it_wrong_via_add_data() { wp_enqueue_script( 'invalid-strategy' ); $this->assertEqualHTML( - "\n", + "\n", get_echo( 'wp_print_scripts' ) ); } @@ -1889,7 +1885,7 @@ public function test_script_strategy_doing_it_wrong_via_enqueue() { wp_enqueue_script( 'invalid-strategy', '/defaults.js', array(), null, array( 'strategy' => 'random-strategy' ) ); $this->assertEqualHTML( - "\n", + "\n", get_echo( 'wp_print_scripts' ) ); } @@ -1919,8 +1915,8 @@ public function test_concatenate_with_defer_strategy() { wp_print_scripts(); $print_scripts = get_echo( '_print_scripts' ); - $expected = "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, $print_scripts, '', 'Scripts are being incorrectly concatenated when a main script is registered with a "defer" loading strategy. Deferred scripts should not be part of the script concat loading query.' ); } @@ -1950,8 +1946,8 @@ public function test_concatenate_with_async_strategy() { wp_print_scripts(); $print_scripts = get_echo( '_print_scripts' ); - $expected = "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, $print_scripts, '', 'Scripts are being incorrectly concatenated when a main script is registered with an "async" loading strategy. Async scripts should not be part of the script concat loading query.' ); } @@ -1985,8 +1981,8 @@ public function test_concatenate_with_blocking_script_before_and_after_script_wi wp_print_scripts(); $print_scripts = get_echo( '_print_scripts' ); - $expected = "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, $print_scripts, '', 'Scripts are being incorrectly concatenated when a main script is registered as deferred after other blocking scripts are registered. Deferred scripts should not be part of the script concat loader query string. ' ); } @@ -2025,24 +2021,24 @@ public function test_protocols() { // Try with an HTTP reference. wp_enqueue_script( 'jquery-http', 'http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js' ); - $expected .= "\n"; + $expected .= "\n"; // Try with an HTTPS reference. wp_enqueue_script( 'jquery-https', 'https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js' ); - $expected .= "\n"; + $expected .= "\n"; // Try with an automatic protocol reference (//). wp_enqueue_script( 'jquery-doubleslash', '//ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js' ); - $expected .= "\n"; + $expected .= "\n"; // Try with a local resource and an automatic protocol reference (//). $url = '//my_plugin/script.js'; wp_enqueue_script( 'plugin-script', $url ); - $expected .= "\n"; + $expected .= "\n"; // Try with a bad protocol. wp_enqueue_script( 'jquery-ftp', 'ftp://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js' ); - $expected .= "\n"; + $expected .= "\n"; // Go! $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); @@ -2070,7 +2066,7 @@ public function test_script_concatenation() { wp_print_scripts(); $print_scripts = get_echo( '_print_scripts' ); - $expected = "\n"; + $expected = "\n"; $this->assertSame( $expected, $print_scripts ); } @@ -2084,8 +2080,8 @@ public function test_wp_script_add_data_with_data_key() { // Enqueue and add data. wp_enqueue_script( 'test-only-data', 'example.com', array(), null ); wp_script_add_data( 'test-only-data', 'data', 'testing' ); - $expected = "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; // Go! $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); @@ -2120,7 +2116,7 @@ public function test_wp_script_add_data_with_invalid_key() { // Enqueue and add an invalid key. wp_enqueue_script( 'test-invalid', 'example.com', array(), null ); wp_script_add_data( 'test-invalid', 'invalid', 'testing' ); - $expected = "\n"; + $expected = "\n"; // Go! $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); @@ -2143,8 +2139,8 @@ public function test_wp_register_script() { * @ticket 35229 */ public function test_wp_register_script_with_handle_without_source() { - $expected = "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; wp_register_script( 'handle-one', 'http://example.com', array(), 1 ); wp_register_script( 'handle-two', 'http://example.com', array(), 2 ); @@ -2236,9 +2232,9 @@ public function test_wp_register_script_with_dependencies_in_head_and_footer() { $header = get_echo( 'wp_print_head_scripts' ); $footer = get_echo( 'wp_print_footer_scripts' ); - $expected_header = "\n"; - $expected_header .= "\n"; - $expected_footer = "\n"; + $expected_header = "\n"; + $expected_header .= "\n"; + $expected_footer = "\n"; $this->assertEqualHTML( $expected_header, $header, '', 'Expected same header markup.' ); $this->assertEqualHTML( $expected_footer, $footer, '', 'Expected same footer markup.' ); @@ -2257,9 +2253,9 @@ public function test_wp_register_script_with_dependencies_in_head_and_footer_in_ $header = get_echo( 'wp_print_head_scripts' ); $footer = get_echo( 'wp_print_footer_scripts' ); - $expected_header = "\n"; - $expected_footer = "\n"; - $expected_footer .= "\n"; + $expected_header = "\n"; + $expected_footer = "\n"; + $expected_footer .= "\n"; $this->assertEqualHTML( $expected_header, $header, '', 'Expected same header markup.' ); $this->assertEqualHTML( $expected_footer, $footer, '', 'Expected same footer markup.' ); @@ -2283,14 +2279,14 @@ public function test_wp_register_script_with_dependencies_in_head_and_footer_in_ $header = get_echo( 'wp_print_head_scripts' ); $footer = get_echo( 'wp_print_footer_scripts' ); - $expected_header = "\n"; - $expected_header .= "\n"; - $expected_header .= "\n"; - $expected_header .= "\n"; + $expected_header = "\n"; + $expected_header .= "\n"; + $expected_header .= "\n"; + $expected_header .= "\n"; - $expected_footer = "\n"; - $expected_footer .= "\n"; - $expected_footer .= "\n"; + $expected_footer = "\n"; + $expected_footer .= "\n"; + $expected_footer .= "\n"; $this->assertEqualHTML( $expected_header, $header, '', 'Expected same header markup.' ); $this->assertEqualHTML( $expected_footer, $footer, '', 'Expected same footer markup.' ); @@ -2321,14 +2317,14 @@ public function test_wp_add_inline_script_before() { wp_add_inline_script( 'test-example', 'console.log("before");', 'before' ); $expected = << + HTML; - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2340,9 +2336,9 @@ public function test_wp_add_inline_script_after() { wp_enqueue_script( 'test-example', 'example.com', array(), null ); wp_add_inline_script( 'test-example', 'console.log("after");' ); - $expected = "\n"; + $expected = "\n"; $expected .= << +\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2376,7 +2372,7 @@ public function test_wp_add_inline_script_before_for_handle_without_source() { wp_enqueue_script( 'test-example' ); wp_add_inline_script( 'test-example', 'console.log("before");', 'before' ); - $expected = "\n"; + $expected = "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2389,7 +2385,7 @@ public function test_wp_add_inline_script_after_for_handle_without_source() { wp_enqueue_script( 'test-example' ); wp_add_inline_script( 'test-example', 'console.log("after");' ); - $expected = "\n"; + $expected = "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2403,8 +2399,8 @@ public function test_wp_add_inline_script_before_and_after_for_handle_without_so wp_add_inline_script( 'test-example', 'console.log("before");', 'before' ); wp_add_inline_script( 'test-example', 'console.log("after");' ); - $expected = "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2419,9 +2415,9 @@ public function test_wp_add_inline_script_multiple() { wp_add_inline_script( 'test-example', 'console.log("after");' ); wp_add_inline_script( 'test-example', 'console.log("after");' ); - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2435,10 +2431,10 @@ public function test_wp_add_inline_script_localized_data_is_added_first() { wp_add_inline_script( 'test-example', 'console.log("before");', 'before' ); wp_add_inline_script( 'test-example', 'console.log("after");' ); - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2459,11 +2455,11 @@ public function test_wp_add_inline_script_before_with_concat() { wp_add_inline_script( 'one', 'console.log("before one");', 'before' ); wp_add_inline_script( 'two', 'console.log("before two");', 'before' ); - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2483,10 +2479,10 @@ public function test_wp_add_inline_script_before_with_concat2() { wp_add_inline_script( 'one', 'console.log("before one");', 'before' ); - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2508,12 +2504,12 @@ public function test_wp_add_inline_script_after_with_concat() { wp_add_inline_script( 'two', 'console.log("after two");' ); wp_add_inline_script( 'three', 'console.log("after three");' ); - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2556,9 +2552,9 @@ public function test_wp_add_inline_script_after_with_concat_and_core_dependency( $wp_scripts->base_url = ''; $wp_scripts->do_concat = true; - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; wp_enqueue_script( 'test-example', 'http://example.com', array( 'jquery' ), null ); wp_add_inline_script( 'test-example', 'console.log("after");' ); @@ -2605,9 +2601,9 @@ public function test_wp_add_inline_script_before_with_concat_and_core_dependency $wp_scripts->base_url = ''; $wp_scripts->do_concat = true; - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; wp_enqueue_script( 'test-example', 'http://example.com', array( 'jquery' ), null ); wp_add_inline_script( 'test-example', 'console.log("before");', 'before' ); @@ -2630,21 +2626,21 @@ public function test_wp_add_inline_script_before_after_concat_with_core_dependen $wp_scripts->base_url = ''; $wp_scripts->do_concat = true; - $expected = "\n"; - $expected .= "\n"; + $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; wp_enqueue_script( 'test-example', 'http://example.com', array( 'jquery' ), null ); wp_add_inline_script( 'test-example', 'console.log("before");', 'before' ); wp_enqueue_script( 'test-example2', 'http://example2.com', array( 'wp-a11y' ), null ); @@ -2695,10 +2691,10 @@ public function test_wp_add_inline_script_customize_dependency() { _print_scripts(); $print_scripts = $this->getActualOutput(); - $expected = "\n"; + $expected = "\n"; $this->assertEqualHTMLScriptTagById( $expected, $print_scripts ); - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2746,10 +2742,10 @@ public function test_wp_add_inline_script_before_third_core_script_prints_two_co wp_add_inline_script( 'three', 'console.log("before three");', 'before' ); wp_enqueue_script( 'four', '/wp-includes/js/script4.js' ); - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2768,7 +2764,7 @@ public function data_provider_to_test_get_inline_script() { ), 'delayed' => false, 'expected_data' => "/*before foo 1*/\n//# sourceURL=foo-js-before", - 'expected_tag' => "\n", + 'expected_tag' => "\n", ), 'after-blocking' => array( 'position' => 'after', @@ -2778,7 +2774,7 @@ public function data_provider_to_test_get_inline_script() { ), 'delayed' => false, 'expected_data' => "/*after foo 1*/\n/*after foo 2*/\n//# sourceURL=foo-js-after", - 'expected_tag' => "\n", + 'expected_tag' => "\n", ), 'before-delayed' => array( 'position' => 'before', @@ -2787,7 +2783,7 @@ public function data_provider_to_test_get_inline_script() { ), 'delayed' => true, 'expected_data' => "/*before foo 1*/\n//# sourceURL=foo-js-before", - 'expected_tag' => "\n", + 'expected_tag' => "\n", ), 'after-delayed' => array( 'position' => 'after', @@ -2797,7 +2793,7 @@ public function data_provider_to_test_get_inline_script() { ), 'delayed' => true, 'expected_data' => "/*after foo 1*/\n/*after foo 2*/\n//# sourceURL=foo-js-after", - 'expected_tag' => "\n", + 'expected_tag' => "\n", ), ); } @@ -2867,7 +2863,7 @@ public function test_wp_set_script_translations() { wp_enqueue_script( 'test-example', '/wp-includes/js/script.js', array(), null ); wp_set_script_translations( 'test-example', 'default', DIR_TESTDATA . '/languages' ); - $expected = "\n"; + $expected = "\n"; $expected .= str_replace( array( '__DOMAIN__', @@ -2881,7 +2877,7 @@ public function test_wp_set_script_translations() { ), $this->wp_scripts_print_translations_output ); - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2899,7 +2895,7 @@ public function test_wp_set_script_translations_uses_registered_domainpath_for_p $wp_textdomain_registry->set_custom_path( 'internationalized-plugin', DIR_TESTDATA . '/languages/plugins' ); wp_set_script_translations( 'domain-path-plugin', 'internationalized-plugin' ); - $expected = "\n"; + $expected = "\n"; $expected .= str_replace( array( '__DOMAIN__', @@ -2913,7 +2909,7 @@ public function test_wp_set_script_translations_uses_registered_domainpath_for_p ), $this->wp_scripts_print_translations_output ); - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2934,7 +2930,7 @@ public function test_wp_set_script_translations_prefers_human_readable_filename_ $wp_textdomain_registry->set_custom_path( 'admin', DIR_TESTDATA . '/languages' ); wp_set_script_translations( 'script-handle', 'admin' ); - $expected = "\n"; + $expected = "\n"; $expected .= str_replace( array( '__DOMAIN__', @@ -2948,7 +2944,7 @@ public function test_wp_set_script_translations_prefers_human_readable_filename_ ), $this->wp_scripts_print_translations_output ); - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2961,7 +2957,7 @@ public function test_wp_set_script_translations_for_plugin() { wp_enqueue_script( 'plugin-example', '/wp-content/plugins/my-plugin/js/script.js', array(), null ); wp_set_script_translations( 'plugin-example', 'internationalized-plugin', DIR_TESTDATA . '/languages/plugins' ); - $expected = "\n"; + $expected = "\n"; $expected .= str_replace( array( '__DOMAIN__', @@ -2975,7 +2971,7 @@ public function test_wp_set_script_translations_for_plugin() { ), $this->wp_scripts_print_translations_output ); - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2988,7 +2984,7 @@ public function test_wp_set_script_translations_for_theme() { wp_enqueue_script( 'theme-example', '/wp-content/themes/my-theme/js/script.js', array(), null ); wp_set_script_translations( 'theme-example', 'internationalized-theme', DIR_TESTDATA . '/languages/themes' ); - $expected = "\n"; + $expected = "\n"; $expected .= str_replace( array( '__DOMAIN__', @@ -3002,7 +2998,7 @@ public function test_wp_set_script_translations_for_theme() { ), $this->wp_scripts_print_translations_output ); - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -3015,7 +3011,7 @@ public function test_wp_set_script_translations_with_handle_file() { wp_enqueue_script( 'script-handle', '/wp-admin/js/script.js', array(), null ); wp_set_script_translations( 'script-handle', 'admin', DIR_TESTDATA . '/languages/' ); - $expected = "\n"; + $expected = "\n"; $expected .= str_replace( array( '__DOMAIN__', @@ -3029,7 +3025,7 @@ public function test_wp_set_script_translations_with_handle_file() { ), $this->wp_scripts_print_translations_output ); - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -3058,8 +3054,8 @@ public function test_wp_set_script_translations_when_translation_file_does_not_e wp_enqueue_script( 'test-example', '/wp-admin/js/script.js', array(), null ); wp_set_script_translations( 'test-example', 'admin', DIR_TESTDATA . '/languages/' ); - $expected = "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -3074,7 +3070,7 @@ public function test_wp_set_script_translations_after_register() { wp_enqueue_script( 'test-example' ); - $expected = "\n"; + $expected = "\n"; $expected .= str_replace( array( '__DOMAIN__', @@ -3088,7 +3084,7 @@ public function test_wp_set_script_translations_after_register() { ), $this->wp_scripts_print_translations_output ); - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -3103,7 +3099,7 @@ public function test_wp_set_script_translations_dependency() { wp_enqueue_script( 'test-example', '/wp-includes/js/script2.js', array( 'test-dependency' ), null ); - $expected = "\n"; + $expected = "\n"; $expected .= str_replace( array( '__DOMAIN__', @@ -3117,8 +3113,8 @@ public function test_wp_set_script_translations_dependency() { ), $this->wp_scripts_print_translations_output ); - $expected .= "\n"; - $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -3506,8 +3502,8 @@ public function test_wp_localize_script_data_formats( $l10n_data, $expected ) { wp_enqueue_script( 'test-example', 'example.com', array(), null ); wp_localize_script( 'test-example', 'testExample', $l10n_data ); - $expected = "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -3570,9 +3566,9 @@ static function () { ); // The non-default script should end concatenation and maintain order. - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, $print_scripts ); } @@ -3698,8 +3694,8 @@ public function data_provider_script_move_to_footer() { }, 'expected_header' => '', 'expected_footer' => ' - - + + ', 'expected_in_footer' => array( 'script-a', @@ -3719,8 +3715,8 @@ public function data_provider_script_move_to_footer() { }, 'expected_header' => '', 'expected_footer' => ' - - + + ', 'expected_in_footer' => array( 'script-a', @@ -3739,8 +3735,8 @@ public function data_provider_script_move_to_footer() { wp_enqueue_script( 'script-b', 'https://example.com/script-b.js', array( 'script-a' ), null, array( 'in_footer' => false ) ); }, 'expected_header' => ' - - + + ', 'expected_footer' => '', 'expected_in_footer' => array(), @@ -3766,10 +3762,10 @@ public function data_provider_script_move_to_footer() { ); }, 'expected_header' => ' - + ', 'expected_footer' => ' - + ', 'expected_in_footer' => array( 'script-b', @@ -3816,12 +3812,12 @@ public function data_provider_script_move_to_footer() { ); }, 'expected_header' => ' - - + + ', 'expected_footer' => ' - - + + ', 'expected_in_footer' => array( 'script-c', @@ -3863,10 +3859,10 @@ public function data_provider_script_move_to_footer() { }, 'expected_header' => '', 'expected_footer' => ' - - - - + + + + ', 'expected_in_footer' => array( 'script-a', @@ -3910,12 +3906,12 @@ public function data_provider_script_move_to_footer() { ); }, 'expected_header' => ' - - + + ', 'expected_footer' => ' - - + + ', 'expected_in_footer' => array( 'script-c', @@ -4206,7 +4202,7 @@ public function test_varying_versions_added_to_handle_args_enqueued_scripts( $ve wp_enqueue_script( 'test-script?qs1=q1&qs2=q2', '/test-script.js', array(), $version ); $markup = get_echo( 'wp_print_scripts' ); - $expected = ""; + $expected = ""; $this->assertEqualHTML( $expected, $markup, '', 'Expected equal snapshot for wp_print_scripts() with version ' . var_export( $version, true ) . ":\n$markup" ); } @@ -4227,7 +4223,7 @@ public function test_varying_versions_added_to_handle_args_registered_then_enque wp_enqueue_script( 'test-script?qs1=q1&qs2=q2' ); $markup = get_echo( 'wp_print_scripts' ); - $expected = ""; + $expected = ""; $this->assertEqualHTML( $expected, $markup, '', 'Expected equal snapshot for wp_print_scripts() with version ' . var_export( $version, true ) . ":\n$markup" ); } diff --git a/tests/phpunit/tests/dependencies/styles.php b/tests/phpunit/tests/dependencies/styles.php index 3828c8246e528..c1c11985190cf 100644 --- a/tests/phpunit/tests/dependencies/styles.php +++ b/tests/phpunit/tests/dependencies/styles.php @@ -68,13 +68,13 @@ public function test_wp_enqueue_style() { wp_enqueue_style( 'registered-no-qs-handle-null-version-enqueued-with-qs?arg1=foo&arg2=bar' ); $ver = get_bloginfo( 'version' ); - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_styles' ) ); @@ -109,7 +109,7 @@ public function test_wp_enqueue_style_with_html5_support_does_not_contain_type_a public function test_awkward_handles_are_supported_consistently( $handle ) { wp_enqueue_style( $handle, 'example.com', array(), null ); - $expected = "\n"; + $expected = "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_styles' ) ); } @@ -145,24 +145,24 @@ public function test_protocols() { // Try with an HTTP reference. wp_enqueue_style( 'reset-css-http', 'http://yui.yahooapis.com/2.8.1/build/reset/reset-min.css' ); - $expected .= "\n"; + $expected .= "\n"; // Try with an HTTPS reference. wp_enqueue_style( 'reset-css-https', 'http://yui.yahooapis.com/2.8.1/build/reset/reset-min.css' ); - $expected .= "\n"; + $expected .= "\n"; // Try with an automatic protocol reference (//). wp_enqueue_style( 'reset-css-doubleslash', '//yui.yahooapis.com/2.8.1/build/reset/reset-min.css' ); - $expected .= "\n"; + $expected .= "\n"; // Try with a local resource and an automatic protocol reference (//). $url = '//my_plugin/style.css'; wp_enqueue_style( 'plugin-style', $url ); - $expected .= "\n"; + $expected .= "\n"; // Try with a bad protocol. wp_enqueue_style( 'reset-css-ftp', 'ftp://yui.yahooapis.com/2.8.1/build/reset/reset-min.css' ); - $expected .= "\n"; + $expected .= "\n"; // Go! $this->assertEqualHTML( $expected, get_echo( 'wp_print_styles' ) ); @@ -185,8 +185,8 @@ public function test_inline_styles() { $style .= "\tbackground: red;\n"; $style .= '}'; - $expected = "\n"; - $expected .= "\n"; @@ -213,8 +213,8 @@ public function test_inline_styles_concat() { $style .= "\tbackground: red;\n"; $style .= '}'; - $expected = "\n"; - $expected .= "\n"; @@ -307,8 +307,8 @@ public function test_multiple_inline_styles() { $style2 .= "\tbackground: blue;\n"; $style2 .= '}'; - $expected = "\n"; - $expected .= "\n"; @@ -353,7 +353,7 @@ public function test_plugin_doing_inline_styles_wrong() { */ public function test_unnecessary_style_tags() { - $expected = "\n"; + $expected = "\n"; wp_enqueue_style( 'handle', 'http://example.com', array(), 1 ); @@ -391,9 +391,9 @@ public function test_wp_register_style() { public function test_wp_add_inline_style_for_handle_without_source() { $style = 'a { color: blue; }'; - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; @@ -628,7 +628,7 @@ static function () use ( $styles_inline_size_limit ): int { $this->assertTrue( $processor->next_tag() ); $this->assertSame( 'STYLE', $processor->get_tag() ); $this->assertSame( $handle . '-inline-css', $processor->get_attribute( 'id' ) ); - $this->assertSame( 'text/css', $processor->get_attribute( 'type' ) ); + $this->assertNull( $processor->get_attribute( 'type' ) ); $expected_inline_styles = $expected_after; if ( isset( $additional_inline_style ) ) { @@ -777,8 +777,8 @@ public function test_source_url_encoding() { wp_add_inline_style( $handle, 'custom-el { content: "ok"; }' ); $expected = << - #-css" media="all"> + @@ -869,7 +869,7 @@ public function test_varying_versions_added_to_handle_args_enqueued_styles( $ver wp_enqueue_style( 'test-style?qs1=q1&qs2=q2', '/test-style.css', array(), $version ); $markup = get_echo( 'wp_print_styles' ); - $expected = ""; + $expected = ""; $this->assertEqualHTML( $expected, $markup, '', 'Expected equal snapshot for wp_print_styles() with version ' . var_export( $version, true ) . ":\n$markup" ); } @@ -890,7 +890,7 @@ public function test_varying_versions_added_to_handle_args_registered_then_enque wp_enqueue_style( 'test-style?qs1=q1&qs2=q2' ); $markup = get_echo( 'wp_print_styles' ); - $expected = ""; + $expected = ""; $this->assertEqualHTML( $expected, $markup, '', 'Expected equal snapshot for wp_print_styles() with version ' . var_export( $version, true ) . ":\n$markup" ); } diff --git a/tests/phpunit/tests/dependencies/wpInlineScriptTag.php b/tests/phpunit/tests/dependencies/wpInlineScriptTag.php index 9f3eb3c8cfb90..b67055213e710 100644 --- a/tests/phpunit/tests/dependencies/wpInlineScriptTag.php +++ b/tests/phpunit/tests/dependencies/wpInlineScriptTag.php @@ -143,7 +143,7 @@ public function test_get_inline_script_tag_with_duplicated_cdata_wrappers() { remove_theme_support( 'html5' ); $this->assertSame( - "\n", + "\n", wp_get_inline_script_tag( "/* */" ) ); } diff --git a/tests/phpunit/tests/fonts/font-face/wpFontFace/generateAndPrint.php b/tests/phpunit/tests/fonts/font-face/wpFontFace/generateAndPrint.php index a6454c11d1883..c0d314d0ab4d8 100644 --- a/tests/phpunit/tests/fonts/font-face/wpFontFace/generateAndPrint.php +++ b/tests/phpunit/tests/fonts/font-face/wpFontFace/generateAndPrint.php @@ -31,7 +31,7 @@ public function test_should_not_generate_and_print_when_no_fonts() { */ public function test_should_generate_and_print_given_fonts( array $fonts, $expected ) { $font_face = new WP_Font_Face(); - $style_element = "\n"; + $style_element = "\n"; $expected_output = sprintf( $style_element, $expected ); $output = get_echo( array( $font_face, 'generate_and_print' ), array( $fonts ) ); diff --git a/tests/phpunit/tests/fonts/font-face/wpPrintFontFaces.php b/tests/phpunit/tests/fonts/font-face/wpPrintFontFaces.php index 71cd964ca1bd8..a1fea3ac948e2 100644 --- a/tests/phpunit/tests/fonts/font-face/wpPrintFontFaces.php +++ b/tests/phpunit/tests/fonts/font-face/wpPrintFontFaces.php @@ -55,7 +55,7 @@ public function test_should_escape_tags() { ); $expected_output = << + @@ -76,7 +76,7 @@ public function test_should_print_fonts_in_merged_data() { } private function get_expected_styles_output( $styles ) { - $style_element = "\n"; + $style_element = "\n"; return sprintf( $style_element, $styles ); } } diff --git a/tests/phpunit/tests/fonts/font-face/wpPrintFontFacesFromStyleVariations.php b/tests/phpunit/tests/fonts/font-face/wpPrintFontFacesFromStyleVariations.php index 5dd6304fd2f7b..664404d552b45 100644 --- a/tests/phpunit/tests/fonts/font-face/wpPrintFontFacesFromStyleVariations.php +++ b/tests/phpunit/tests/fonts/font-face/wpPrintFontFacesFromStyleVariations.php @@ -48,7 +48,7 @@ public function test_should_print_fonts_in_style_variations() { } private function get_expected_styles_output( $styles ) { - $style_element = "\n"; + $style_element = "\n"; return sprintf( $style_element, $styles ); } } diff --git a/tests/phpunit/tests/privacy/wpPrivacyGeneratePersonalDataExportFile.php b/tests/phpunit/tests/privacy/wpPrivacyGeneratePersonalDataExportFile.php index 5e69efac966f0..2c5ad1f513744 100644 --- a/tests/phpunit/tests/privacy/wpPrivacyGeneratePersonalDataExportFile.php +++ b/tests/phpunit/tests/privacy/wpPrivacyGeneratePersonalDataExportFile.php @@ -331,7 +331,7 @@ public function test_html_contents( $groups, array $expected_content = array() ) $expected .= "\n"; $expected .= "\n"; $expected .= "\n"; - $expected .= "Personal Data Export for {$request->email}\n"; + $expected .= "Personal Data Export for {$request->email}\n"; $expected .= "\n"; $expected .= '

Personal Data Export

'; From 87eac6daec8ec2740c07aa8ad83d31e49f23685f Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Sat, 27 Dec 2025 23:55:29 +0000 Subject: [PATCH 061/126] Docs: Improve description for `add_settings_section()`. Follow-up to [13177], [15180]. See #64224. git-svn-id: https://develop.svn.wordpress.org/trunk@61412 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/includes/template.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/wp-admin/includes/template.php b/src/wp-admin/includes/template.php index b607e71d75c2c..adb12bc24bf62 100644 --- a/src/wp-admin/includes/template.php +++ b/src/wp-admin/includes/template.php @@ -1616,7 +1616,7 @@ function do_accordion_sections( $screen, $context, $data_object ) { * * @param string $id Slug-name to identify the section. Used in the 'id' attribute of tags. * @param string $title Formatted title of the section. Shown as the heading for the section. - * @param callable $callback Function that echos out any content at the top of the section (between heading and fields). + * @param callable $callback Function that displays any content at the top of the section (between heading and fields). * @param string $page The slug-name of the settings page on which to show the section. Built-in pages include * 'general', 'reading', 'writing', 'discussion', 'media', etc. Create your own using * add_options_page(); From 6e503285699ca106594a92afa13e26d110b06be7 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Sun, 28 Dec 2025 22:57:37 +0000 Subject: [PATCH 062/126] Tests: Use `assertSame()` in some newly introduced tests. This ensures that not only the return values match the expected results, but also that their type is the same. Going forward, stricter type checking by using `assertSame()` should generally be preferred to `assertEquals()` where appropriate, to make the tests more reliable. Follow-up to [60490], [60524]. See #64324. git-svn-id: https://develop.svn.wordpress.org/trunk@61413 602fd350-edb4-49c9-b593-d223f7449a82 --- tests/phpunit/tests/feed/fetchFeed.php | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/phpunit/tests/feed/fetchFeed.php b/tests/phpunit/tests/feed/fetchFeed.php index 71ed1650e717a..98224ff96c15d 100644 --- a/tests/phpunit/tests/feed/fetchFeed.php +++ b/tests/phpunit/tests/feed/fetchFeed.php @@ -51,10 +51,10 @@ public function test_fetch_feed_cached() { add_filter( 'pre_http_request', array( $filter, 'filter' ) ); fetch_feed( 'https://wordpress.org/news/feed/' ); - $this->assertEquals( 1, $filter->get_call_count(), 'The feed should be fetched on the first call.' ); + $this->assertSame( 1, $filter->get_call_count(), 'The feed should be fetched on the first call.' ); fetch_feed( 'https://wordpress.org/news/feed/' ); - $this->assertEquals( 1, $filter->get_call_count(), 'The feed should be cached on the second call. For SP 1.8.x upgrades, backport simplepie/simplepie#830 to resolve.' ); + $this->assertSame( 1, $filter->get_call_count(), 'The feed should be cached on the second call. For SP 1.8.x upgrades, backport simplepie/simplepie#830 to resolve.' ); } /** @@ -79,7 +79,7 @@ public function test_fetch_feed_uses_global_cache() { switch_to_blog( $second_blog_id ); fetch_feed( 'https://wordpress.org/news/feed/' ); - $this->assertEquals( 1, $filter->get_call_count(), 'The feed cache should be global.' ); + $this->assertSame( 1, $filter->get_call_count(), 'The feed cache should be global.' ); } /** From bd9efed8d97790b50886a2dcfa839e6917bab8e0 Mon Sep 17 00:00:00 2001 From: Jon Surrell Date: Mon, 29 Dec 2025 10:47:40 +0000 Subject: [PATCH 063/126] Scripts: Remove CDATA script wrappers in WP Admin. Fix a regression from [61411] where CDATA wrappers were added to `SCRIPT` tags in WP Admin. Developed in https://github.com/WordPress/wordpress-develop/pull/10666. Follow-up to [61411]. Props sabernhardt. See #64428, #59883. git-svn-id: https://develop.svn.wordpress.org/trunk@61414 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/script-loader.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/wp-includes/script-loader.php b/src/wp-includes/script-loader.php index 60d94a3a0648f..4ac143a918615 100644 --- a/src/wp-includes/script-loader.php +++ b/src/wp-includes/script-loader.php @@ -2969,8 +2969,8 @@ function wp_get_inline_script_tag( $data, $attributes = array() ) { * @see https://www.w3.org/TR/xhtml1/#h-4.8 */ if ( - ! current_theme_supports( 'html5', 'script' ) && - ( + ( ! current_theme_supports( 'html5', 'script' ) && ! is_admin() ) + && ( ! isset( $attributes['type'] ) || 'module' === $attributes['type'] || str_contains( $attributes['type'], 'javascript' ) || From 59c8dcf5d21a17c7b4c45fb94875a2c504b52d34 Mon Sep 17 00:00:00 2001 From: Jon Surrell Date: Mon, 29 Dec 2025 11:32:17 +0000 Subject: [PATCH 064/126] Scripts: Remove non-HTML5 script support. Remove the following behaviors that are obsolete in HTML5: - CDATA wrappers around `SCRIPT` tag contents. - Conversion of boolean attributes to strings (attribute `async="async"` becomes `async`). HTML5 was released in 2008 and data suggests virtually all WordPress sites are served as HTML5. See #59883 for more details. Developed in https://github.com/WordPress/wordpress-develop/pull/10660. Props jonsurrell, westonruter, azaozz, soyebsalar01, dmsnell. Fixes #64442. See #59883. git-svn-id: https://develop.svn.wordpress.org/trunk@61415 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/script-loader.php | 57 +--- tests/phpunit/tests/dependencies/scripts.php | 253 +++++------------- .../tests/dependencies/wpInlineScriptTag.php | 123 --------- .../wpSanitizeScriptAttributes.php | 47 ---- 4 files changed, 62 insertions(+), 418 deletions(-) diff --git a/src/wp-includes/script-loader.php b/src/wp-includes/script-loader.php index 4ac143a918615..a60fce6262744 100644 --- a/src/wp-includes/script-loader.php +++ b/src/wp-includes/script-loader.php @@ -2210,10 +2210,8 @@ function _print_scripts() { if ( $concat ) { if ( ! empty( $wp_scripts->print_code ) ) { echo "\n\n"; } @@ -2871,8 +2869,7 @@ function wp_enqueue_editor_format_library_assets() { * @return string String made of sanitized ` - * - * In an HTML document this would print "…" to the console, - * but in an XHTML document it would print "…" to the console. - * - * - * - * In an HTML document this would print "An image is in HTML", - * but it's an invalid XHTML document because it interprets the `` - * as an empty tag missing its closing `/`. - * - * @see https://www.w3.org/TR/xhtml1/#h-4.8 - */ - if ( - ( ! current_theme_supports( 'html5', 'script' ) && ! is_admin() ) - && ( - ! isset( $attributes['type'] ) || - 'module' === $attributes['type'] || - str_contains( $attributes['type'], 'javascript' ) || - str_contains( $attributes['type'], 'ecmascript' ) || - str_contains( $attributes['type'], 'jscript' ) || - str_contains( $attributes['type'], 'livescript' ) - ) - ) { - /* - * If the string `]]>` exists within the JavaScript it would break - * out of any wrapping CDATA section added here, so to start, it's - * necessary to escape that sequence which requires splitting the - * content into two CDATA sections wherever it's found. - * - * Note: it's only necessary to escape the closing `]]>` because - * an additional `', ']]]]>', $data ); - - // Wrap the entire escaped script inside a CDATA section. - $data = sprintf( "/* */", $data ); - } - $data = "\n" . trim( $data, "\n\r " ) . "\n"; /** diff --git a/tests/phpunit/tests/dependencies/scripts.php b/tests/phpunit/tests/dependencies/scripts.php index f05c4cfab5601..934d7c039f1e7 100644 --- a/tests/phpunit/tests/dependencies/scripts.php +++ b/tests/phpunit/tests/dependencies/scripts.php @@ -48,14 +48,12 @@ public function set_up() { $this->wp_scripts_print_translations_output = << -/* */ JS; $this->wp_scripts_print_translations_output .= "\n"; @@ -238,16 +236,16 @@ public function test_before_inline_scripts_with_delayed_main_script( $strategy ) 'id' => 'ds-i1-1-js-before', ) ); - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $expected .= wp_get_inline_script_tag( "console.log('before last');\n//# sourceURL=ms-i1-1-js-before", array( 'id' => 'ms-i1-1-js-before', ) ); - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, $output, '', 'Inline scripts in the "before" position, that are attached to a deferred main script, are failing to print/execute.' ); } @@ -266,7 +264,7 @@ public function test_loading_strategy_with_valid_async_registration() { // No dependents, No dependencies then async. wp_enqueue_script( 'main-script-a1', '/main-script-a1.js', array(), null, array( 'strategy' => 'async' ) ); $output = get_echo( 'wp_print_scripts' ); - $expected = "\n"; + $expected = "\n"; $this->assertEqualHTML( $expected, $output, '', 'Scripts enqueued with an async loading strategy are failing to have the async attribute applied to the script handle when being printed.' ); } @@ -289,7 +287,7 @@ public function test_delayed_dependent_with_blocking_dependency( $strategy ) { wp_enqueue_script( 'main-script-a2', '/main-script-a2.js', array( 'dependency-script-a2' ), null, compact( 'strategy' ) ); $output = get_echo( 'wp_print_scripts' ); $expected = "\n"; - $expected .= ""; + $expected .= ""; $this->assertEqualHTML( $expected, $output, '', 'Dependents of a blocking dependency are free to have any strategy.' ); } @@ -331,7 +329,6 @@ public function test_blocking_dependent_with_delayed_dependency( $strategy ) { * @param string $strategy Strategy. */ public function test_delayed_dependent_with_blocking_dependency_not_enqueued( $strategy ) { - $this->add_html5_script_theme_support(); wp_enqueue_script( 'main-script-a4', '/main-script-a4.js', array(), null, compact( 'strategy' ) ); // This dependent is registered but not enqueued, so it should not factor into the eligible loading strategy. wp_register_script( 'dependent-script-a4', '/dependent-script-a4.js', array( 'main-script-a4' ), null ); @@ -563,30 +560,22 @@ public function data_provider_to_test_various_strategy_dependency_chains() { }, 'expected_markup' => << -/* */ HTML , @@ -612,43 +601,31 @@ public function data_provider_to_test_various_strategy_dependency_chains() { }, 'expected_markup' => << -/* */ HTML , @@ -666,30 +643,22 @@ public function data_provider_to_test_various_strategy_dependency_chains() { }, 'expected_markup' => << -/* */ HTML , @@ -707,30 +676,22 @@ public function data_provider_to_test_various_strategy_dependency_chains() { }, 'expected_markup' => << -/* */ HTML , @@ -751,29 +712,21 @@ public function data_provider_to_test_various_strategy_dependency_chains() { }, 'expected_markup' => << -/* */ HTML , @@ -797,43 +750,31 @@ public function data_provider_to_test_various_strategy_dependency_chains() { }, 'expected_markup' => << -/* */ HTML , @@ -856,29 +797,21 @@ public function data_provider_to_test_various_strategy_dependency_chains() { }, 'expected_markup' => << -/* */ HTML , @@ -899,43 +832,31 @@ public function data_provider_to_test_various_strategy_dependency_chains() { }, 'expected_markup' => << -/* */ HTML , @@ -956,43 +877,31 @@ public function data_provider_to_test_various_strategy_dependency_chains() { }, 'expected_markup' => << -/* */ HTML , @@ -1010,30 +919,22 @@ public function data_provider_to_test_various_strategy_dependency_chains() { }, 'expected_markup' => << -/* */ HTML , @@ -1047,12 +948,10 @@ public function data_provider_to_test_various_strategy_dependency_chains() { }, 'expected_markup' => << -/* */ - + HTML , ), @@ -1066,10 +965,8 @@ public function data_provider_to_test_various_strategy_dependency_chains() { 'expected_markup' => << HTML , @@ -1085,9 +982,9 @@ public function data_provider_to_test_various_strategy_dependency_chains() { wp_enqueue_script( 'theme-functions', 'https://example.com/theme-functions.js', array( 'jquery' ), null, array( 'strategy' => 'defer' ) ); }, 'expected_markup' => << - - + + + HTML , ), @@ -1114,17 +1011,13 @@ public function data_provider_to_test_various_strategy_dependency_chains() { HTML , @@ -1143,9 +1036,9 @@ public function data_provider_to_test_various_strategy_dependency_chains() { $this->enqueue_test_script( 'defer-dependent-of-async-aliases', 'defer', array( $alias_handle ) ); }, 'expected_markup' => << - - + + + HTML , ), @@ -1181,7 +1074,6 @@ public function test_various_strategy_dependency_chains( $set_up, $expected_mark * @covers ::wp_enqueue_script */ public function test_loading_strategy_with_defer_having_no_dependents_nor_dependencies() { - $this->add_html5_script_theme_support(); wp_enqueue_script( 'main-script-d1', 'http://example.com/main-script-d1.js', array(), null, array( 'strategy' => 'defer' ) ); $output = get_echo( 'wp_print_scripts' ); $expected = str_replace( "'", '"', "\n" ); @@ -1198,7 +1090,6 @@ public function test_loading_strategy_with_defer_having_no_dependents_nor_depend * @covers ::wp_enqueue_script */ public function test_loading_strategy_with_defer_dependent_and_varied_dependencies() { - $this->add_html5_script_theme_support(); wp_enqueue_script( 'dependency-script-d2-1', 'http://example.com/dependency-script-d2-1.js', array(), null, array( 'strategy' => 'defer' ) ); wp_enqueue_script( 'dependency-script-d2-2', 'http://example.com/dependency-script-d2-2.js', array(), null ); wp_enqueue_script( 'dependency-script-d2-3', 'http://example.com/dependency-script-d2-3.js', array( 'dependency-script-d2-2' ), null, array( 'strategy' => 'defer' ) ); @@ -1218,7 +1109,6 @@ public function test_loading_strategy_with_defer_dependent_and_varied_dependenci * @covers ::wp_enqueue_script */ public function test_loading_strategy_with_all_defer_dependencies() { - $this->add_html5_script_theme_support(); wp_enqueue_script( 'main-script-d3', 'http://example.com/main-script-d3.js', array(), null, array( 'strategy' => 'defer' ) ); wp_enqueue_script( 'dependent-script-d3-1', 'http://example.com/dependent-script-d3-1.js', array( 'main-script-d3' ), null, array( 'strategy' => 'defer' ) ); wp_enqueue_script( 'dependent-script-d3-2', 'http://example.com/dependent-script-d3-2.js', array( 'dependent-script-d3-1' ), null, array( 'strategy' => 'defer' ) ); @@ -1276,10 +1166,10 @@ public function test_defer_with_async_dependent() { ); // Note: All of these scripts have fetchpriority=high because the leaf dependent script has that fetch priority. $output = get_echo( 'wp_print_scripts' ); - $expected = "\n"; - $expected .= "\n"; - $expected .= "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; + $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, $output, '', 'Scripts registered as defer but that have dependents that are async are expected to have said dependents deferred.' ); } @@ -1529,7 +1419,7 @@ public function test_priority_of_dependency_for_non_enqueued_dependent() { $actual = $this->normalize_markup_for_snapshot( get_echo( array( $wp_scripts, 'print_scripts' ) ) ); $this->assertEqualHTML( - '', + '', $actual, '', "Snapshot:\n$actual" @@ -1566,7 +1456,7 @@ public function test_printing_default_script_comment_reply_enqueued_or_not_enque $this->assertEqualHTML( sprintf( - '', + '', includes_url( 'js/comment-reply.js' ) ), $markup @@ -1916,7 +1806,7 @@ public function test_concatenate_with_defer_strategy() { $print_scripts = get_echo( '_print_scripts' ); $expected = "\n"; - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, $print_scripts, '', 'Scripts are being incorrectly concatenated when a main script is registered with a "defer" loading strategy. Deferred scripts should not be part of the script concat loading query.' ); } @@ -1947,7 +1837,7 @@ public function test_concatenate_with_async_strategy() { $print_scripts = get_echo( '_print_scripts' ); $expected = "\n"; - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, $print_scripts, '', 'Scripts are being incorrectly concatenated when a main script is registered with an "async" loading strategy. Async scripts should not be part of the script concat loading query.' ); } @@ -1982,7 +1872,7 @@ public function test_concatenate_with_blocking_script_before_and_after_script_wi $print_scripts = get_echo( '_print_scripts' ); $expected = "\n"; - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, $print_scripts, '', 'Scripts are being incorrectly concatenated when a main script is registered as deferred after other blocking scripts are registered. Deferred scripts should not be part of the script concat loader query string. ' ); } @@ -1993,8 +1883,6 @@ public function test_concatenate_with_blocking_script_before_and_after_script_wi public function test_wp_enqueue_script_with_html5_support_does_not_contain_type_attribute() { global $wp_version; - $this->add_html5_script_theme_support(); - $GLOBALS['wp_scripts'] = new WP_Scripts(); $GLOBALS['wp_scripts']->default_version = get_bloginfo( 'version' ); @@ -2080,7 +1968,7 @@ public function test_wp_script_add_data_with_data_key() { // Enqueue and add data. wp_enqueue_script( 'test-only-data', 'example.com', array(), null ); wp_script_add_data( 'test-only-data', 'data', 'testing' ); - $expected = "\n"; + $expected = "\n"; $expected .= "\n"; // Go! @@ -2318,10 +2206,8 @@ public function test_wp_add_inline_script_before() { $expected = << -/* */ HTML; $expected .= "\n"; @@ -2339,10 +2225,8 @@ public function test_wp_add_inline_script_after() { $expected = "\n"; $expected .= << -/* */ HTML; @@ -2357,9 +2241,9 @@ public function test_wp_add_inline_script_before_and_after() { wp_add_inline_script( 'test-example', 'console.log("before");', 'before' ); wp_add_inline_script( 'test-example', 'console.log("after");' ); - $expected = "\n"; + $expected = "\n"; $expected .= "\n"; - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2372,7 +2256,7 @@ public function test_wp_add_inline_script_before_for_handle_without_source() { wp_enqueue_script( 'test-example' ); wp_add_inline_script( 'test-example', 'console.log("before");', 'before' ); - $expected = "\n"; + $expected = "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2385,7 +2269,7 @@ public function test_wp_add_inline_script_after_for_handle_without_source() { wp_enqueue_script( 'test-example' ); wp_add_inline_script( 'test-example', 'console.log("after");' ); - $expected = "\n"; + $expected = "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2399,8 +2283,8 @@ public function test_wp_add_inline_script_before_and_after_for_handle_without_so wp_add_inline_script( 'test-example', 'console.log("before");', 'before' ); wp_add_inline_script( 'test-example', 'console.log("after");' ); - $expected = "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2415,9 +2299,9 @@ public function test_wp_add_inline_script_multiple() { wp_add_inline_script( 'test-example', 'console.log("after");' ); wp_add_inline_script( 'test-example', 'console.log("after");' ); - $expected = "\n"; + $expected = "\n"; $expected .= "\n"; - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2431,10 +2315,10 @@ public function test_wp_add_inline_script_localized_data_is_added_first() { wp_add_inline_script( 'test-example', 'console.log("before");', 'before' ); wp_add_inline_script( 'test-example', 'console.log("after");' ); - $expected = "\n"; - $expected .= "\n"; + $expected = "\n"; + $expected .= "\n"; $expected .= "\n"; - $expected .= "\n"; + $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); } @@ -2455,9 +2339,9 @@ public function test_wp_add_inline_script_before_with_concat() { wp_add_inline_script( 'one', 'console.log("before one");', 'before' ); wp_add_inline_script( 'two', 'console.log("before two");', 'before' ); - $expected = "\n"; + $expected = "\n"; $expected .= "\n"; - $expected .= "\n"; + $expected .= "\n"; $expected .= "\n"; $expected .= "\n"; @@ -2479,7 +2363,7 @@ public function test_wp_add_inline_script_before_with_concat2() { wp_add_inline_script( 'one', 'console.log("before one");', 'before' ); - $expected = "\n"; + $expected = "\n"; $expected .= "\n"; $expected .= "\n"; $expected .= "\n"; @@ -2506,9 +2390,9 @@ public function test_wp_add_inline_script_after_with_concat() { $expected = "\n"; $expected .= "\n"; - $expected .= "\n"; + $expected .= "\n"; $expected .= "\n"; - $expected .= "\n"; + $expected .= "\n"; $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); @@ -2554,7 +2438,7 @@ public function test_wp_add_inline_script_after_with_concat_and_core_dependency( $expected = "\n"; $expected .= "\n"; - $expected .= "\n"; + $expected .= "\n"; wp_enqueue_script( 'test-example', 'http://example.com', array( 'jquery' ), null ); wp_add_inline_script( 'test-example', 'console.log("after");' ); @@ -2602,7 +2486,7 @@ public function test_wp_add_inline_script_before_with_concat_and_core_dependency $wp_scripts->do_concat = true; $expected = "\n"; - $expected .= "\n"; + $expected .= "\n"; $expected .= "\n"; wp_enqueue_script( 'test-example', 'http://example.com', array( 'jquery' ), null ); @@ -2628,19 +2512,17 @@ public function test_wp_add_inline_script_before_after_concat_with_core_dependen $expected = "\n"; $expected .= "\n"; $expected .= "\n"; $expected .= "\n"; $expected .= "\n"; $expected .= "\n"; $expected .= "\n"; - $expected .= "\n"; + $expected .= "\n"; wp_enqueue_script( 'test-example', 'http://example.com', array( 'jquery' ), null ); wp_add_inline_script( 'test-example', 'console.log("before");', 'before' ); wp_enqueue_script( 'test-example2', 'http://example2.com', array( 'wp-a11y' ), null ); @@ -2695,10 +2577,8 @@ public function test_wp_add_inline_script_customize_dependency() { $this->assertEqualHTMLScriptTagById( $expected, $print_scripts ); $expected = "\n"; $this->assertEqualHTMLScriptTagById( $expected, $print_scripts ); } @@ -2719,7 +2599,7 @@ public function test_wp_add_inline_script_after_for_core_scripts_with_concat_is_ wp_enqueue_script( 'four', '/wp-includes/js/script4.js' ); $expected = "\n"; - $expected .= "\n"; + $expected .= "\n"; $expected .= "\n"; $expected .= "\n"; $expected .= "\n"; @@ -2743,7 +2623,7 @@ public function test_wp_add_inline_script_before_third_core_script_prints_two_co wp_enqueue_script( 'four', '/wp-includes/js/script4.js' ); $expected = "\n"; - $expected .= "\n"; + $expected .= "\n"; $expected .= "\n"; $expected .= "\n"; @@ -2764,7 +2644,7 @@ public function data_provider_to_test_get_inline_script() { ), 'delayed' => false, 'expected_data' => "/*before foo 1*/\n//# sourceURL=foo-js-before", - 'expected_tag' => "\n", + 'expected_tag' => "\n", ), 'after-blocking' => array( 'position' => 'after', @@ -2774,7 +2654,7 @@ public function data_provider_to_test_get_inline_script() { ), 'delayed' => false, 'expected_data' => "/*after foo 1*/\n/*after foo 2*/\n//# sourceURL=foo-js-after", - 'expected_tag' => "\n", + 'expected_tag' => "\n", ), 'before-delayed' => array( 'position' => 'before', @@ -2783,7 +2663,7 @@ public function data_provider_to_test_get_inline_script() { ), 'delayed' => true, 'expected_data' => "/*before foo 1*/\n//# sourceURL=foo-js-before", - 'expected_tag' => "\n", + 'expected_tag' => "\n", ), 'after-delayed' => array( 'position' => 'after', @@ -2793,7 +2673,7 @@ public function data_provider_to_test_get_inline_script() { ), 'delayed' => true, 'expected_data' => "/*after foo 1*/\n/*after foo 2*/\n//# sourceURL=foo-js-after", - 'expected_tag' => "\n", + 'expected_tag' => "\n", ), ); } @@ -3502,7 +3382,7 @@ public function test_wp_localize_script_data_formats( $l10n_data, $expected ) { wp_enqueue_script( 'test-example', 'example.com', array(), null ); wp_localize_script( 'test-example', 'testExample', $l10n_data ); - $expected = "\n"; + $expected = "\n"; $expected .= "\n"; $this->assertEqualHTML( $expected, get_echo( 'wp_print_scripts' ) ); @@ -3605,13 +3485,6 @@ public function test_printing_non_enqueued_scripts( $strategy ) { $this->assertStringContainsString( $strategy, $actual ); } - /** - * Adds html5 script theme support. - */ - protected function add_html5_script_theme_support() { - add_theme_support( 'html5', array( 'script' ) ); - } - /** * Test that a script is moved to the footer if it is made non-deferrable, was in the header and * all scripts that depend on it are in the footer. @@ -3762,10 +3635,10 @@ public function data_provider_script_move_to_footer() { ); }, 'expected_header' => ' - + ', 'expected_footer' => ' - + ', 'expected_in_footer' => array( 'script-b', @@ -3812,12 +3685,12 @@ public function data_provider_script_move_to_footer() { ); }, 'expected_header' => ' - - + + ', 'expected_footer' => ' - - + + ', 'expected_in_footer' => array( 'script-c', @@ -3860,9 +3733,9 @@ public function data_provider_script_move_to_footer() { 'expected_header' => '', 'expected_footer' => ' - + - + ', 'expected_in_footer' => array( 'script-a', @@ -3907,11 +3780,11 @@ public function data_provider_script_move_to_footer() { }, 'expected_header' => ' - + ', 'expected_footer' => ' - + ', 'expected_in_footer' => array( 'script-c', @@ -4076,8 +3949,6 @@ private function _scripts_from_package_json() { * @ticket 63887 */ public function test_source_url_encoding() { - $this->add_html5_script_theme_support(); - $handle = '# test/ #'; wp_enqueue_script( $handle, '/example.js', array(), '0.0' ); @@ -4110,7 +3981,6 @@ public function test_source_url_encoding() { */ public function test_source_url_with_concat() { global $wp_scripts, $concatenate_scripts, $wp_version; - $this->add_html5_script_theme_support(); $concatenate_scripts = true; @@ -4127,10 +3997,8 @@ public function test_source_url_with_concat() { $expected = << -/* */ @@ -4147,7 +4015,6 @@ public function test_source_url_with_concat() { */ public function test_print_translations_no_display_no_sourceurl() { global $wp_scripts; - $this->add_html5_script_theme_support(); wp_register_script( 'wp-i18n', '/wp-includes/js/dist/wp-i18n.js', array(), null ); wp_enqueue_script( 'test-example', '/wp-includes/js/script.js', array(), null ); diff --git a/tests/phpunit/tests/dependencies/wpInlineScriptTag.php b/tests/phpunit/tests/dependencies/wpInlineScriptTag.php index b67055213e710..76e53db9c235e 100644 --- a/tests/phpunit/tests/dependencies/wpInlineScriptTag.php +++ b/tests/phpunit/tests/dependencies/wpInlineScriptTag.php @@ -34,22 +34,6 @@ public function tear_down() { JS; public function get_inline_script_tag_type_set() { - add_theme_support( 'html5', array( 'script' ) ); - - $this->assertSame( - '\n", - wp_get_inline_script_tag( - $this->event_handler, - array( - 'type' => 'application/javascript', - 'async' => false, - 'nomodule' => true, - ) - ) - ); - - remove_theme_support( 'html5' ); - $this->assertSame( '\n", wp_get_inline_script_tag( @@ -64,8 +48,6 @@ public function get_inline_script_tag_type_set() { } public function test_get_inline_script_tag_type_not_set() { - add_theme_support( 'html5', array( 'script' ) ); - $this->assertSame( "\n", wp_get_inline_script_tag( @@ -76,19 +58,13 @@ public function test_get_inline_script_tag_type_not_set() { ) ) ); - - remove_theme_support( 'html5' ); } public function test_get_inline_script_tag_unescaped_src() { - add_theme_support( 'html5', array( 'script' ) ); - $this->assertSame( "\n", wp_get_inline_script_tag( $this->event_handler ) ); - - remove_theme_support( 'html5' ); } public function test_print_script_tag_prints_get_inline_script_tag() { @@ -102,8 +78,6 @@ static function ( $attributes ) { } ); - add_theme_support( 'html5', array( 'script' ) ); - $attributes = array( 'id' => 'utils-js-before', 'nomodule' => true, @@ -119,102 +93,5 @@ static function ( $attributes ) { ) ) ); - - remove_theme_support( 'html5' ); - - $this->assertSame( - wp_get_inline_script_tag( $this->event_handler, $attributes ), - get_echo( - 'wp_print_inline_script_tag', - array( - $this->event_handler, - $attributes, - ) - ) - ); - } - - /** - * Tests that CDATA wrapper duplication is handled. - * - * @ticket 58664 - */ - public function test_get_inline_script_tag_with_duplicated_cdata_wrappers() { - remove_theme_support( 'html5' ); - - $this->assertSame( - "\n", - wp_get_inline_script_tag( "/* */" ) - ); - } - - public function data_provider_to_test_cdata_wrapper_omitted_for_non_javascript_scripts() { - return array( - 'no-type' => array( - 'type' => null, - 'data' => 'alert("hello")', - 'expected_cdata' => true, - ), - 'js-type' => array( - 'type' => 'text/javascript', - 'data' => 'alert("hello")', - 'expected_cdata' => true, - ), - 'js-alt-type' => array( - 'type' => 'application/javascript', - 'data' => 'alert("hello")', - 'expected_cdata' => true, - ), - 'module' => array( - 'type' => 'module', - 'data' => 'alert("hello")', - 'expected_cdata' => true, - ), - 'importmap' => array( - 'type' => 'importmap', - 'data' => '{"imports":{"bar":"http:\/\/localhost:10023\/bar.js?ver=6.5-alpha-57321"}}', - 'expected_cdata' => false, - ), - 'html' => array( - 'type' => 'text/html', - 'data' => '
template code
', - 'expected_cdata' => false, - ), - 'json' => array( - 'type' => 'application/json', - 'data' => '{}', - 'expected_cdata' => false, - ), - 'ld' => array( - 'type' => 'application/ld+json', - 'data' => '{}', - 'expected_cdata' => false, - ), - 'specrules' => array( - 'type' => 'speculationrules', - 'data' => '{}', - 'expected_cdata' => false, - ), - ); - } - - /** - * Tests that CDATA wrapper is not added for non-JavaScript scripts. - * - * @ticket 60320 - * - * @dataProvider data_provider_to_test_cdata_wrapper_omitted_for_non_javascript_scripts - */ - public function test_cdata_wrapper_omitted_for_non_javascript_scripts( $type, $data, $expected_cdata ) { - remove_theme_support( 'html5' ); - - $attrs = array(); - if ( $type ) { - $attrs['type'] = $type; - } - $script = wp_get_inline_script_tag( $data, $attrs ); - $this->assertSame( $expected_cdata, str_contains( $script, '/* assertSame( $expected_cdata, str_contains( $script, '/* ]]> */' ) ); - $this->assertStringContainsString( $data, $script ); } } diff --git a/tests/phpunit/tests/dependencies/wpSanitizeScriptAttributes.php b/tests/phpunit/tests/dependencies/wpSanitizeScriptAttributes.php index 0c96d9ee47654..69ab85b8e3cd0 100644 --- a/tests/phpunit/tests/dependencies/wpSanitizeScriptAttributes.php +++ b/tests/phpunit/tests/dependencies/wpSanitizeScriptAttributes.php @@ -10,8 +10,6 @@ class Tests_Dependencies_wpSanitizeScriptAttributes extends WP_UnitTestCase { public function test_sanitize_script_attributes_type_set() { - add_theme_support( 'html5', array( 'script' ) ); - $this->assertSame( ' type="application/javascript" src="https://DOMAIN.TLD/PATH/FILE.js" nomodule', wp_sanitize_script_attributes( @@ -23,25 +21,9 @@ public function test_sanitize_script_attributes_type_set() { ) ) ); - - remove_theme_support( 'html5' ); - - $this->assertSame( - ' src="https://DOMAIN.TLD/PATH/FILE.js" type="application/javascript" nomodule="nomodule"', - wp_sanitize_script_attributes( - array( - 'src' => 'https://DOMAIN.TLD/PATH/FILE.js', - 'type' => 'application/javascript', - 'async' => false, - 'nomodule' => true, - ) - ) - ); } public function test_sanitize_script_attributes_type_not_set() { - add_theme_support( 'html5', array( 'script' ) ); - $this->assertSame( ' src="https://DOMAIN.TLD/PATH/FILE.js" nomodule', wp_sanitize_script_attributes( @@ -52,36 +34,17 @@ public function test_sanitize_script_attributes_type_not_set() { ) ) ); - - remove_theme_support( 'html5' ); - - $this->assertSame( - ' src="https://DOMAIN.TLD/PATH/FILE.js" nomodule="nomodule"', - wp_sanitize_script_attributes( - array( - 'src' => 'https://DOMAIN.TLD/PATH/FILE.js', - 'async' => false, - 'nomodule' => true, - ) - ) - ); } public function test_sanitize_script_attributes_no_attributes() { - add_theme_support( 'html5', array( 'script' ) ); - $this->assertSame( '', wp_sanitize_script_attributes( array() ) ); - - remove_theme_support( 'html5' ); } public function test_sanitize_script_attributes_relative_src() { - add_theme_support( 'html5', array( 'script' ) ); - $this->assertSame( ' src="PATH/FILE.js" nomodule', wp_sanitize_script_attributes( @@ -92,14 +55,10 @@ public function test_sanitize_script_attributes_relative_src() { ) ) ); - - remove_theme_support( 'html5' ); } public function test_sanitize_script_attributes_only_false_boolean_attributes() { - add_theme_support( 'html5', array( 'script' ) ); - $this->assertSame( '', wp_sanitize_script_attributes( @@ -109,13 +68,9 @@ public function test_sanitize_script_attributes_only_false_boolean_attributes() ) ) ); - - remove_theme_support( 'html5' ); } public function test_sanitize_script_attributes_only_true_boolean_attributes() { - add_theme_support( 'html5', array( 'script' ) ); - $this->assertSame( ' async nomodule', wp_sanitize_script_attributes( @@ -125,7 +80,5 @@ public function test_sanitize_script_attributes_only_true_boolean_attributes() { ) ) ); - - remove_theme_support( 'html5' ); } } From 31745d4b7149a67e09e1744319dcb6fd3104f9ec Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Mon, 29 Dec 2025 18:59:20 +0000 Subject: [PATCH 065/126] Script Loader: Warn when a registered style has invalid `path` data and allow inlining empty stylesheets. When a stylesheet is registered with a `path` that does not exist or which is not readable, then a `_doing_it_wrong()` is now issued. Previously, paths that did not exist were silently skipped; paths for empty styles were also needlessly skipped, since `wp_filesize()` also returns `0` for the failure case. Developed in https://github.com/WordPress/wordpress-develop/pull/10653 Follow-up to [50836]. Props westonruter, jonsurrell, soyebsalar01. See #52620. Fixes #64447. git-svn-id: https://develop.svn.wordpress.org/trunk@61416 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/script-loader.php | 27 +++++++- tests/phpunit/tests/dependencies/styles.php | 68 ++++++++++++++++++++- tests/phpunit/tests/media.php | 4 ++ tests/phpunit/tests/template.php | 12 ++-- 4 files changed, 104 insertions(+), 7 deletions(-) diff --git a/src/wp-includes/script-loader.php b/src/wp-includes/script-loader.php index a60fce6262744..ffb2fffa5c9d1 100644 --- a/src/wp-includes/script-loader.php +++ b/src/wp-includes/script-loader.php @@ -3010,7 +3010,18 @@ function wp_maybe_inline_styles() { $path = $wp_styles->get_data( $handle, 'path' ); if ( $path && $src ) { $size = wp_filesize( $path ); - if ( ! $size ) { + if ( 0 === $size && ! file_exists( $path ) ) { + _doing_it_wrong( + __FUNCTION__, + sprintf( + /* translators: 1: 'path', 2: filesystem path, 3: style handle */ + __( 'Unable to read the "%1$s" key with value "%2$s" for stylesheet "%3$s".' ), + 'path', + esc_html( $path ), + esc_html( $handle ) + ), + '7.0.0' + ); continue; } $styles[] = array( @@ -3048,6 +3059,20 @@ static function ( $a, $b ) { } // Get the styles if we don't already have them. + if ( ! is_readable( $style['path'] ) ) { + _doing_it_wrong( + __FUNCTION__, + sprintf( + /* translators: 1: 'path', 2: filesystem path, 3: style handle */ + __( 'Unable to read the "%1$s" key with value "%2$s" for stylesheet "%3$s".' ), + 'path', + esc_html( $style['path'] ), + esc_html( $style['handle'] ) + ), + '7.0.0' + ); + continue; + } $style['css'] = file_get_contents( $style['path'] ); /* diff --git a/tests/phpunit/tests/dependencies/styles.php b/tests/phpunit/tests/dependencies/styles.php index c1c11985190cf..57687752f6a08 100644 --- a/tests/phpunit/tests/dependencies/styles.php +++ b/tests/phpunit/tests/dependencies/styles.php @@ -716,10 +716,12 @@ public function test_wp_maybe_inline_styles_multiple_runs() { /** * @ticket 58394 + * @ticket 64447 * * @covers ::wp_maybe_inline_styles + * @expectedIncorrectUsage wp_maybe_inline_styles */ - public function test_test_wp_maybe_inline_styles_missing_file() { + public function test_wp_maybe_inline_styles_missing_file() { $filter = new MockAction(); add_filter( 'pre_wp_filesize', array( $filter, 'filter' ) ); $url = '/' . WPINC . '/css/invalid.css'; @@ -768,6 +770,70 @@ public function test_wp_maybe_inline_styles_no_path() { $this->assertSame( $GLOBALS['wp_styles']->registered['test-handle']->src, $url ); } + /** + * @ticket 64447 + * + * @covers ::wp_maybe_inline_styles + * @expectedIncorrectUsage wp_maybe_inline_styles + */ + public function test_wp_maybe_inline_styles_bad_path_with_file_size_provided() { + $style_path = '/css/invalid.css'; // Does not exist. + + // This ensures the initial file size check is bypassed. + add_filter( + 'pre_wp_filesize', + static function ( $size, $path ) use ( $style_path ) { + if ( str_contains( $path, $style_path ) ) { + $size = 1000; + } + return $size; + }, + 10, + 2 + ); + + $handle = 'test-handle'; + $url = '/' . WPINC . $style_path; + wp_register_style( $handle, $url ); + wp_style_add_data( $handle, 'path', ABSPATH . WPINC . $style_path ); + wp_enqueue_style( $handle ); + + wp_maybe_inline_styles(); + + $this->assertSame( $GLOBALS['wp_styles']->registered[ $handle ]->src, $url ); + } + + /** + * @ticket 64447 + * + * @covers ::wp_maybe_inline_styles + */ + public function test_wp_maybe_inline_styles_good_path_with_zero_file_size_provided() { + $style_path = '/css/classic-themes.css'; + + // This simulates the file having a zero size. + add_filter( + 'pre_wp_filesize', + static function ( $size, $path ) use ( $style_path ) { + if ( str_contains( $path, $style_path ) ) { + $size = 0; + } + return $size; + }, + 10, + 2 + ); + + $handle = 'test-handle'; + wp_register_style( $handle, '/' . WPINC . $style_path ); + wp_style_add_data( $handle, 'path', ABSPATH . WPINC . $style_path ); + wp_enqueue_style( $handle ); + + wp_maybe_inline_styles(); + + $this->assertFalse( $GLOBALS['wp_styles']->registered[ $handle ]->src ); + } + /** * @ticket 63887 */ diff --git a/tests/phpunit/tests/media.php b/tests/phpunit/tests/media.php index 1ab836fe856d8..f6b1e5b2d982b 100644 --- a/tests/phpunit/tests/media.php +++ b/tests/phpunit/tests/media.php @@ -6677,6 +6677,10 @@ static function () { * @dataProvider data_provider_data_provider_to_test_wp_enqueue_img_auto_sizes_contain_css_fix */ public function test_wp_enqueue_img_auto_sizes_contain_css_fix( ?Closure $set_up, bool $expected, ?string $expected_deprecated = null ): void { + // These files are created as part of the build process, but the unit tests don't run the build prior to running unit tests on GHA. + self::touch( ABSPATH . WPINC . '/css/dist/block-library/style.css' ); + self::touch( ABSPATH . WPINC . '/css/dist/block-library/common.css' ); + if ( $set_up ) { $set_up(); } diff --git a/tests/phpunit/tests/template.php b/tests/phpunit/tests/template.php index a304fff95f865..a965665360b05 100644 --- a/tests/phpunit/tests/template.php +++ b/tests/phpunit/tests/template.php @@ -1677,6 +1677,9 @@ function (): void { * @dataProvider data_wp_hoist_late_printed_styles */ public function test_wp_hoist_late_printed_styles( ?Closure $set_up, int $inline_size_limit, array $expected_styles ): void { + // `_print_emoji_detection_script()` assumes `wp-includes/js/wp-emoji-loader.js` is present: + self::touch( ABSPATH . WPINC . '/js/wp-emoji-loader.js' ); + switch_theme( 'default' ); global $wp_styles; $wp_styles = null; @@ -1711,6 +1714,8 @@ static function () { 'wp-block-library', wp_should_load_separate_core_block_assets() ? 'css/dist/block-library/common.css' : 'css/dist/block-library/style.css' ); + $this->ensure_style_asset_file_created( 'wp-block-library-theme', 'css/dist/block-library/theme.css' ); + if ( wp_should_load_separate_core_block_assets() ) { $this->ensure_style_asset_file_created( 'wp-block-separator', 'blocks/separator/style.css' ); } @@ -1827,11 +1832,8 @@ private function ensure_style_asset_file_created( string $handle, string $relati } $dependency->src = includes_url( $relative_path ); $path = ABSPATH . WPINC . '/' . $relative_path; - if ( ! file_exists( $path ) ) { - $dir = dirname( $path ); - if ( ! file_exists( $dir ) ) { - mkdir( $dir, 0777, true ); - } + self::touch( $path ); + if ( 0 === filesize( $path ) ) { file_put_contents( $path, "/* CSS for $handle */" ); } wp_style_add_data( $handle, 'path', $path ); From b167a0351424f229bfd67835989c2fda40729bb5 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Mon, 29 Dec 2025 23:13:54 +0000 Subject: [PATCH 066/126] Tests: Use `assertSame()` in `wp_count_posts()` tests. This ensures that not only the return values match the expected results, but also that their type is the same. Going forward, stricter type checking by using `assertSame()` should generally be preferred to `assertEquals()` where appropriate, to make the tests more reliable. Follow-up to [1323/tests], [25554], [27081], [60788]. Props costdev, SergeyBiryukov. See #64324. git-svn-id: https://develop.svn.wordpress.org/trunk@61417 602fd350-edb4-49c9-b593-d223f7449a82 --- tests/phpunit/tests/post.php | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/tests/phpunit/tests/post.php b/tests/phpunit/tests/post.php index e5779946da066..e609fa0d3003d 100644 --- a/tests/phpunit/tests/post.php +++ b/tests/phpunit/tests/post.php @@ -183,7 +183,7 @@ public function test_wp_count_posts() { ); $count = wp_count_posts( $post_type, 'readable' ); - $this->assertEquals( 1, $count->publish ); + $this->assertSame( '1', $count->publish ); _unregister_post_type( $post_type ); $count = wp_count_posts( $post_type, 'readable' ); @@ -226,7 +226,7 @@ public function test_wp_count_posts_readable_excludes_unreadable_private_posts() wp_set_current_user( self::$user_ids['author'] ); $count = wp_count_posts( $post_type, 'readable' ); - $this->assertEquals( 5, $count->publish ); + $this->assertSame( '5', $count->publish ); _unregister_post_type( $post_type ); } @@ -245,16 +245,16 @@ public function test_wp_count_posts_filtered() { ); $count1 = wp_count_posts( $post_type, 'readable' ); - $this->assertEquals( 3, $count1->publish ); + $this->assertSame( '3', $count1->publish ); add_filter( 'wp_count_posts', array( $this, 'filter_wp_count_posts' ) ); $count2 = wp_count_posts( $post_type, 'readable' ); remove_filter( 'wp_count_posts', array( $this, 'filter_wp_count_posts' ) ); - $this->assertEquals( 2, $count2->publish ); + $this->assertSame( '2', $count2->publish ); } public function filter_wp_count_posts( $counts ) { - $counts->publish = 2; + $counts->publish = '2'; return $counts; } @@ -276,8 +276,8 @@ public function test_wp_count_posts_insert_invalidation() { $this->assertNotEquals( 'publish', $post->post_status ); $after_draft_counts = wp_count_posts(); - $this->assertEquals( 1, $after_draft_counts->draft ); - $this->assertEquals( 2, $after_draft_counts->publish ); + $this->assertSame( '1', $after_draft_counts->draft ); + $this->assertSame( '2', $after_draft_counts->publish ); $this->assertNotEquals( $initial_counts->publish, $after_draft_counts->publish ); } @@ -297,8 +297,8 @@ public function test_wp_count_posts_trash_invalidation() { $this->assertNotEquals( 'publish', $post->post_status ); $after_trash_counts = wp_count_posts(); - $this->assertEquals( 1, $after_trash_counts->trash ); - $this->assertEquals( 2, $after_trash_counts->publish ); + $this->assertSame( '1', $after_trash_counts->trash ); + $this->assertSame( '2', $after_trash_counts->publish ); $this->assertNotEquals( $initial_counts->publish, $after_trash_counts->publish ); } From 1231ef9ff7382a403e901bce13a7f7f1a0a75695 Mon Sep 17 00:00:00 2001 From: Jon Surrell Date: Tue, 30 Dec 2025 13:01:11 +0000 Subject: [PATCH 067/126] Use the HTML API to generate style tags. The HTML API escapes `\n", - esc_attr( $handle ), - $inline_style - ); + $processor = new WP_HTML_Tag_Processor( '' ); + $processor->next_tag(); + $processor->set_attribute( 'id', "{$handle}-inline-css" ); + $processor->set_modifiable_text( "\n{$inline_style}\n" ); + $inline_style_tag = "{$processor->get_updated_html()}\n"; } else { $inline_style_tag = ''; } @@ -336,11 +336,11 @@ public function print_inline_style( $handle, $display = true ) { return $output; } - printf( - "\n", - esc_attr( $handle ), - $output - ); + $processor = new WP_HTML_Tag_Processor( '' ); + $processor->next_tag(); + $processor->set_attribute( 'id', "{$handle}-inline-css" ); + $processor->set_modifiable_text( "\n{$output}\n" ); + echo "{$processor->get_updated_html()}\n"; return true; } diff --git a/src/wp-includes/fonts/class-wp-font-face.php b/src/wp-includes/fonts/class-wp-font-face.php index 96d51b19ff401..193a5d0951ddb 100644 --- a/src/wp-includes/fonts/class-wp-font-face.php +++ b/src/wp-includes/fonts/class-wp-font-face.php @@ -92,7 +92,10 @@ public function generate_and_print( array $fonts ) { return; } - printf( $this->get_style_element(), $css ); + $processor = new WP_HTML_Tag_Processor( '' ); + $processor->next_tag(); + $processor->set_modifiable_text( "\n{$css}\n" ); + echo "{$processor->get_updated_html()}\n"; } /** @@ -193,17 +196,6 @@ private function validate_font_face_declarations( array $font_face ) { return $font_face; } - /** - * Gets the style element for wrapping the `@font-face` CSS. - * - * @since 6.4.0 - * - * @return string The style element. - */ - private function get_style_element() { - return "\n"; - } - /** * Gets the `@font-face` CSS styles for locally-hosted font files. * diff --git a/src/wp-includes/script-loader.php b/src/wp-includes/script-loader.php index ffb2fffa5c9d1..c0108dc848276 100644 --- a/src/wp-includes/script-loader.php +++ b/src/wp-includes/script-loader.php @@ -2413,10 +2413,12 @@ function _print_styles() { echo "\n"; if ( ! empty( $wp_styles->print_code ) ) { - echo "\n"; + $processor = new WP_HTML_Tag_Processor( '' ); + $processor->next_tag(); + $style_tag_contents = "\n{$wp_styles->print_code}\n" + . sprintf( "/*# sourceURL=%s */\n", rawurlencode( $concat_source_url ) ); + $processor->set_modifiable_text( $style_tag_contents ); + echo "{$processor->get_updated_html()}\n"; } } @@ -3171,7 +3173,10 @@ function wp_enqueue_block_support_styles( $style, $priority = 10 ) { add_action( $action_hook_name, static function () use ( $style ) { - echo "\n"; + $processor = new WP_HTML_Tag_Processor( '' ); + $processor->next_tag(); + $processor->set_modifiable_text( $style ); + echo "{$processor->get_updated_html()}\n"; }, $priority ); diff --git a/src/wp-includes/theme.php b/src/wp-includes/theme.php index 89d56d4e44bce..0ff915cbe4263 100644 --- a/src/wp-includes/theme.php +++ b/src/wp-includes/theme.php @@ -1950,11 +1950,13 @@ function _custom_background_cb() { $style .= $image . $position . $size . $repeat . $attachment; } - ?> - id="custom-background-css"> -body.custom-background { } - - " ); + $processor->next_tag(); + + $style_tag_content = 'body.custom-background { ' . trim( $style ) . ' }'; + $processor->set_modifiable_text( "\n{$style_tag_content}\n" ); + echo "{$processor->get_updated_html()}\n"; } /** @@ -1964,17 +1966,18 @@ function _custom_background_cb() { */ function wp_custom_css_cb() { $styles = wp_get_custom_css(); - if ( $styles || is_customize_preview() ) : - $type_attr = current_theme_supports( 'html5', 'style' ) ? '' : ' type="text/css"'; - ?> - id="wp-custom-css"> - - - ' ); + $processor->next_tag(); + if ( ! current_theme_supports( 'html5', 'style' ) ) { + $processor->set_attribute( 'type', 'text/css' ); + } + $processor->set_attribute( 'id', 'wp-custom-css' ); + $processor->set_modifiable_text( "\n{$styles}\n" ); + echo "{$processor->get_updated_html()}\n"; } /** From af28bcc61300fcc40fc376331df496e4372179b3 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Tue, 30 Dec 2025 22:53:23 +0000 Subject: [PATCH 068/126] Upgrade/Install: Update sodium_compat to v1.24.0. The latest version includes a security fix to ensure that the public key is on the prime order subgroup. References: * [https://github.com/paragonie/sodium_compat/releases/tag/v1.24.0 sodium_compat 1.24.0 release notes] * [https://github.com/paragonie/sodium_compat/compare/v1.23.0...v1.24.0 Full list of changes in sodium_compat 1.24.0] Follow-up to [55699], [58752], [58753], [60787], [60905]. Props paragoninitiativeenterprises, johnbillion, SergeyBiryukov. Fixes #64462. git-svn-id: https://develop.svn.wordpress.org/trunk@61419 602fd350-edb4-49c9-b593-d223f7449a82 --- .../sodium_compat/src/Core/Ed25519.php | 26 ++++++++++++++++--- src/wp-includes/sodium_compat/src/File.php | 6 +++++ 2 files changed, 28 insertions(+), 4 deletions(-) diff --git a/src/wp-includes/sodium_compat/src/Core/Ed25519.php b/src/wp-includes/sodium_compat/src/Core/Ed25519.php index 01457bad46c0d..bf6b5cfbd77f4 100644 --- a/src/wp-includes/sodium_compat/src/Core/Ed25519.php +++ b/src/wp-includes/sodium_compat/src/Core/Ed25519.php @@ -106,6 +106,22 @@ public static function publickey_from_secretkey($sk) return self::sk_to_pk($sk); } + /** + * Returns TRUE if $A represents a point on the order of the Edwards25519 prime order subgroup. + * Returns FALSE if $A is on a different subgroup. + * + * @param ParagonIE_Sodium_Core_Curve25519_Ge_P3 $A + * @return bool + * + * @throws SodiumException + */ + public static function is_on_main_subgroup(ParagonIE_Sodium_Core_Curve25519_Ge_P3 $A) + { + $p1 = self::ge_mul_l($A); + $t = self::fe_sub($p1->Y, $p1->Z); + return self::fe_isnonzero($p1->X) && self::fe_isnonzero($t); + } + /** * @param string $pk * @return string @@ -118,9 +134,8 @@ public static function pk_to_curve25519($pk) throw new SodiumException('Public key is on a small order'); } $A = self::ge_frombytes_negate_vartime(self::substr($pk, 0, 32)); - $p1 = self::ge_mul_l($A); - if (!self::fe_isnonzero($p1->X)) { - throw new SodiumException('Unexpected zero result'); + if (!self::is_on_main_subgroup($A)) { + throw new SodiumException('Public key is not on a member of the main subgroup'); } # fe_1(one_minus_y); @@ -287,7 +302,7 @@ public static function verify_detached($sig, $message, $pk) throw new SodiumException('Argument 3 must be CRYPTO_SIGN_PUBLICKEYBYTES long'); } if ((self::chrToInt($sig[63]) & 240) && self::check_S_lt_L(self::substr($sig, 32, 32))) { - throw new SodiumException('S < L - Invalid signature'); + throw new SodiumException('S >= L - Invalid signature'); } if (self::small_order($sig)) { throw new SodiumException('Signature is on too small of an order'); @@ -311,6 +326,9 @@ public static function verify_detached($sig, $message, $pk) /** @var ParagonIE_Sodium_Core_Curve25519_Ge_P3 $A */ $A = self::ge_frombytes_negate_vartime($pk); + if (!self::is_on_main_subgroup($A)) { + throw new SodiumException('Public key is not on a member of the main subgroup'); + } /** @var string $hDigest */ $hDigest = hash( diff --git a/src/wp-includes/sodium_compat/src/File.php b/src/wp-includes/sodium_compat/src/File.php index 80d625fa294ad..c132a92e25fff 100644 --- a/src/wp-includes/sodium_compat/src/File.php +++ b/src/wp-includes/sodium_compat/src/File.php @@ -786,8 +786,14 @@ public static function verify( // Set ParagonIE_Sodium_Compat::$fastMult to true to speed up verification. ParagonIE_Sodium_Compat::$fastMult = true; + if (ParagonIE_Sodium_Core_Ed25519::small_order($publicKey)) { + throw new SodiumException('Public key has small order'); + } /** @var ParagonIE_Sodium_Core_Curve25519_Ge_P3 $A */ $A = ParagonIE_Sodium_Core_Ed25519::ge_frombytes_negate_vartime($publicKey); + if (!ParagonIE_Sodium_Core_Ed25519::is_on_main_subgroup($A)) { + throw new SodiumException('Public key is not on a member of the main subgroup'); + } $hs = hash_init('sha512'); self::hash_update($hs, self::substr($sig, 0, 32)); From 8d3a5e1526bd16425d382e43abeeb25c4c60080a Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Wed, 31 Dec 2025 19:00:23 +0000 Subject: [PATCH 069/126] Tests: Use `assertSame()` in `populate_network()` tests. This ensures that not only the return values match the expected results, but also that their type is the same. Going forward, stricter type checking by using `assertSame()` should generally be preferred to `assertEquals()` where appropriate, to make the tests more reliable. Follow-up to [60954]. See #64324. git-svn-id: https://develop.svn.wordpress.org/trunk@61420 602fd350-edb4-49c9-b593-d223f7449a82 --- tests/phpunit/tests/multisite/populateNetworkHooks.php | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/tests/phpunit/tests/multisite/populateNetworkHooks.php b/tests/phpunit/tests/multisite/populateNetworkHooks.php index 8611a7eb95a7c..d315d98bae120 100644 --- a/tests/phpunit/tests/multisite/populateNetworkHooks.php +++ b/tests/phpunit/tests/multisite/populateNetworkHooks.php @@ -59,10 +59,10 @@ public function test_before_populate_network_hook() { $this->assertSame( 1, $this->action_counts['before_populate_network'], 'before_populate_network action should fire once' ); $this->assertSame( 1, $this->action_counts['after_populate_network'], 'after_populate_network action should fire once' ); - $this->assertEquals( $network_id, $this->action_args['before_populate_network']['network_id'], 'Network ID should match in before_populate_network hook' ); - $this->assertEquals( $domain, $this->action_args['before_populate_network']['domain'], 'Domain should match in before_populate_network hook' ); - $this->assertEquals( $network_id, $this->action_args['after_populate_network']['network_id'], 'Network ID should match in after_populate_network hook' ); - $this->assertEquals( $domain, $this->action_args['after_populate_network']['domain'], 'Domain should match in after_populate_network hook' ); + $this->assertSame( $network_id, $this->action_args['before_populate_network']['network_id'], 'Network ID should match in before_populate_network hook' ); + $this->assertSame( $domain, $this->action_args['before_populate_network']['domain'], 'Domain should match in before_populate_network hook' ); + $this->assertSame( $network_id, $this->action_args['after_populate_network']['network_id'], 'Network ID should match in after_populate_network hook' ); + $this->assertSame( $domain, $this->action_args['after_populate_network']['domain'], 'Domain should match in after_populate_network hook' ); remove_action( 'before_populate_network', array( $this, 'hook_action_counter' ), 10 ); remove_action( 'after_populate_network', array( $this, 'hook_action_counter' ), 10 ); From c539f438bd7717e48a88c3245a8ba99a61754623 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Thu, 1 Jan 2026 00:05:54 +0000 Subject: [PATCH 070/126] =?UTF-8?q?Happy=20New=20Year!=20=F0=9F=8E=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Update copyright year to 2026 in `license.txt` and bundled themes. Follow-up to [18201], [23306], [28064], [36855], [36856], [39659], [40241], [42424], [46719], [46720], [47025], [47026], [49915], [52427], [55024], [57235], [59568], [59569]. Props mukesh27. git-svn-id: https://develop.svn.wordpress.org/trunk@61421 602fd350-edb4-49c9-b593-d223f7449a82 --- src/license.txt | 2 +- src/wp-content/themes/twentyeleven/readme.txt | 2 +- src/wp-content/themes/twentyfifteen/readme.txt | 2 +- src/wp-content/themes/twentyfourteen/readme.txt | 2 +- src/wp-content/themes/twentynineteen/readme.txt | 4 ++-- src/wp-content/themes/twentyseventeen/readme.txt | 2 +- src/wp-content/themes/twentysixteen/readme.txt | 2 +- src/wp-content/themes/twentyten/readme.txt | 2 +- src/wp-content/themes/twentythirteen/readme.txt | 2 +- src/wp-content/themes/twentytwelve/readme.txt | 2 +- src/wp-content/themes/twentytwenty/readme.txt | 8 ++++---- src/wp-content/themes/twentytwentyfive/readme.txt | 2 +- src/wp-content/themes/twentytwentyfour/readme.txt | 2 +- src/wp-content/themes/twentytwentyone/readme.txt | 12 ++++++------ src/wp-content/themes/twentytwentythree/readme.txt | 2 +- src/wp-content/themes/twentytwentytwo/readme.txt | 2 +- 16 files changed, 25 insertions(+), 25 deletions(-) diff --git a/src/license.txt b/src/license.txt index 04711e166b5e5..2d9ed1ab7973b 100644 --- a/src/license.txt +++ b/src/license.txt @@ -1,6 +1,6 @@ WordPress - Web publishing software -Copyright 2011-2025 by the contributors +Copyright 2011-2026 by the contributors This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by diff --git a/src/wp-content/themes/twentyeleven/readme.txt b/src/wp-content/themes/twentyeleven/readme.txt index 494e9f6c3eb73..3fccba98d2af8 100644 --- a/src/wp-content/themes/twentyeleven/readme.txt +++ b/src/wp-content/themes/twentyeleven/readme.txt @@ -23,7 +23,7 @@ For more information about Twenty Eleven please go to https://codex.wordpress.or == Copyright == -Twenty Eleven WordPress Theme, Copyright 2011-2025 WordPress.org, Automattic Inc., and contributors. +Twenty Eleven WordPress Theme, Copyright 2011-2026 WordPress.org, Automattic Inc., and contributors. Twenty Eleven is Distributed under the terms of the GNU GPL This program is free software: you can redistribute it and/or modify diff --git a/src/wp-content/themes/twentyfifteen/readme.txt b/src/wp-content/themes/twentyfifteen/readme.txt index c42042c4461de..046bb8f1ea83c 100644 --- a/src/wp-content/themes/twentyfifteen/readme.txt +++ b/src/wp-content/themes/twentyfifteen/readme.txt @@ -31,7 +31,7 @@ For more information about Twenty Fifteen please go to https://wordpress.org/doc == Copyright == -Twenty Fifteen WordPress Theme, Copyright 2014-2025 WordPress.org, Automattic Inc., and contributors. +Twenty Fifteen WordPress Theme, Copyright 2014-2026 WordPress.org, Automattic Inc., and contributors. Twenty Fifteen is distributed under the terms of the GNU GPL This program is free software: you can redistribute it and/or modify diff --git a/src/wp-content/themes/twentyfourteen/readme.txt b/src/wp-content/themes/twentyfourteen/readme.txt index 58e5fe4f4a908..a4402691516b7 100644 --- a/src/wp-content/themes/twentyfourteen/readme.txt +++ b/src/wp-content/themes/twentyfourteen/readme.txt @@ -23,7 +23,7 @@ For more information about Twenty Fourteen please go to https://codex.wordpress. == Copyright == -Twenty Fourteen WordPress Theme, Copyright 2013-2025 WordPress.org, Automattic Inc., and contributors. +Twenty Fourteen WordPress Theme, Copyright 2013-2026 WordPress.org, Automattic Inc., and contributors. Twenty Fourteen is Distributed under the terms of the GNU GPL This program is free software: you can redistribute it and/or modify diff --git a/src/wp-content/themes/twentynineteen/readme.txt b/src/wp-content/themes/twentynineteen/readme.txt index 7f665c0c7793f..1f2ffbc7b828c 100644 --- a/src/wp-content/themes/twentynineteen/readme.txt +++ b/src/wp-content/themes/twentynineteen/readme.txt @@ -25,7 +25,7 @@ For more information about Twenty Nineteen please go to https://wordpress.org/do == Copyright == -Twenty Nineteen WordPress Theme, Copyright 2018-2025 WordPress.org, and contributors. +Twenty Nineteen WordPress Theme, Copyright 2018-2026 WordPress.org, and contributors. Twenty Nineteen is distributed under the terms of the GNU GPL This program is free software: you can redistribute it and/or modify @@ -157,7 +157,7 @@ Initial release == Resources == * normalize.css, © 2012-2018 Nicolas Gallagher and Jonathan Neal, MIT -* Underscores, © 2012-2025 Automattic, Inc., GNU GPL v2 or later +* Underscores, © 2012-2026 Automattic, Inc., GNU GPL v2 or later * Bundled block pattern images: * Abstract Background by HD Wallpapers, CC0. https://stocksnap.io/photo/abstract-background-0SRRVNMKBX * Abstract Waves by HD Wallpapers, CC0. https://stocksnap.io/photo/abstract-waves-0KREGLTZQ3 diff --git a/src/wp-content/themes/twentyseventeen/readme.txt b/src/wp-content/themes/twentyseventeen/readme.txt index 2002dadf8fbd7..93d3765e2c3bd 100644 --- a/src/wp-content/themes/twentyseventeen/readme.txt +++ b/src/wp-content/themes/twentyseventeen/readme.txt @@ -24,7 +24,7 @@ For more information about Twenty Seventeen please go to https://wordpress.org/d == Copyright == -Twenty Seventeen WordPress Theme, Copyright 2016-2025 WordPress.org, and contributors. +Twenty Seventeen WordPress Theme, Copyright 2016-2026 WordPress.org, and contributors. Twenty Seventeen is distributed under the terms of the GNU GPL This program is free software: you can redistribute it and/or modify diff --git a/src/wp-content/themes/twentysixteen/readme.txt b/src/wp-content/themes/twentysixteen/readme.txt index 34ccf8040598e..c93f3510ff198 100644 --- a/src/wp-content/themes/twentysixteen/readme.txt +++ b/src/wp-content/themes/twentysixteen/readme.txt @@ -30,7 +30,7 @@ For more information about Twenty Sixteen please go to https://wordpress.org/doc == Copyright == -Twenty Sixteen WordPress Theme, Copyright 2014-2025 WordPress.org, and contributors. +Twenty Sixteen WordPress Theme, Copyright 2014-2026 WordPress.org, and contributors. Twenty Sixteen is distributed under the terms of the GNU GPL This program is free software: you can redistribute it and/or modify diff --git a/src/wp-content/themes/twentyten/readme.txt b/src/wp-content/themes/twentyten/readme.txt index 64a3d1eee3cac..6f5466d6fdaf6 100644 --- a/src/wp-content/themes/twentyten/readme.txt +++ b/src/wp-content/themes/twentyten/readme.txt @@ -23,7 +23,7 @@ For more information about Twenty Ten theme please go to https://codex.wordpress == Copyright == -Twenty Ten WordPress Theme, Copyright 2010-2025 WordPress.org, Automattic Inc., and contributors. +Twenty Ten WordPress Theme, Copyright 2010-2026 WordPress.org, Automattic Inc., and contributors. Twenty Ten is Distributed under the terms of the GNU GPL This program is free software: you can redistribute it and/or modify diff --git a/src/wp-content/themes/twentythirteen/readme.txt b/src/wp-content/themes/twentythirteen/readme.txt index d6099971670a8..33e7e881a0e97 100644 --- a/src/wp-content/themes/twentythirteen/readme.txt +++ b/src/wp-content/themes/twentythirteen/readme.txt @@ -23,7 +23,7 @@ For more information about Twenty Thirteen please go to https://codex.wordpress. == Copyright == -Twenty Thirteen WordPress Theme, Copyright 2013-2025 WordPress.org, Automattic Inc., and contributors. +Twenty Thirteen WordPress Theme, Copyright 2013-2026 WordPress.org, Automattic Inc., and contributors. Twenty Thirteen is Distributed under the terms of the GNU GPL This program is free software: you can redistribute it and/or modify diff --git a/src/wp-content/themes/twentytwelve/readme.txt b/src/wp-content/themes/twentytwelve/readme.txt index 6fcf497c54c20..42d80f1a64134 100644 --- a/src/wp-content/themes/twentytwelve/readme.txt +++ b/src/wp-content/themes/twentytwelve/readme.txt @@ -23,7 +23,7 @@ For more information about Twenty Twelve please go to https://codex.wordpress.or == Copyright == -Twenty Twelve WordPress Theme, Copyright 2012-2025 WordPress.org, Automattic Inc., and contributors. +Twenty Twelve WordPress Theme, Copyright 2012-2026 WordPress.org, Automattic Inc., and contributors. Twenty Twelve is Distributed under the terms of the GNU GPL This program is free software: you can redistribute it and/or modify diff --git a/src/wp-content/themes/twentytwenty/readme.txt b/src/wp-content/themes/twentytwenty/readme.txt index 12316e2945e7d..2a977de2099f2 100644 --- a/src/wp-content/themes/twentytwenty/readme.txt +++ b/src/wp-content/themes/twentytwenty/readme.txt @@ -131,7 +131,7 @@ Initial release == Copyright == -Twenty Twenty WordPress Theme, Copyright 2019-2025 WordPress.org and contributors. +Twenty Twenty WordPress Theme, Copyright 2019-2026 WordPress.org and contributors. Twenty Twenty is distributed under the terms of the GNU GPL. This program is free software: you can redistribute it and/or modify @@ -180,7 +180,7 @@ License URI: http://www.gnu.org/licenses/gpl-2.0.html Source: WordPress Social Link Block (See wp-includes\blocks\social-link.php) Code from Twenty Nineteen -Copyright (c) 2018-2025 WordPress.org +Copyright (c) 2018-2026 WordPress.org License: GPLv2 Source: https://wordpress.org/themes/twentynineteen/ Included as part of the following classes and functions: @@ -190,11 +190,11 @@ Included as part of the following classes and functions: - twentytwenty_nav_menu_social_icons() Code from Twenty Seventeen -Copyright (c) 2016-2025 WordPress.org +Copyright (c) 2016-2026 WordPress.org License: GPLv2 Source: https://wordpress.org/themes/twentyseventeen/ Included as part of the following classes and functions: - twentytwenty_unique_id() Underscores -https://underscores.me/, (C) 2012-2025 Automattic, Inc., [GPLv2 or later](https://www.gnu.org/licenses/gpl-2.0.html) +https://underscores.me/, (C) 2012-2026 Automattic, Inc., [GPLv2 or later](https://www.gnu.org/licenses/gpl-2.0.html) diff --git a/src/wp-content/themes/twentytwentyfive/readme.txt b/src/wp-content/themes/twentytwentyfive/readme.txt index cfb1e820a2d93..65b66d706390a 100644 --- a/src/wp-content/themes/twentytwentyfive/readme.txt +++ b/src/wp-content/themes/twentytwentyfive/readme.txt @@ -41,7 +41,7 @@ https://wordpress.org/documentation/article/twenty-twenty-five-changelog/#Versio == Copyright == -Twenty Twenty-Five WordPress Theme, (C) 2024-2025 WordPress.org and contributors. +Twenty Twenty-Five WordPress Theme, (C) 2024-2026 WordPress.org and contributors. Twenty Twenty-Five is distributed under the terms of the GNU GPL. This program is free software: you can redistribute it and/or modify diff --git a/src/wp-content/themes/twentytwentyfour/readme.txt b/src/wp-content/themes/twentytwentyfour/readme.txt index df36951b0f58d..9941169607a6c 100644 --- a/src/wp-content/themes/twentytwentyfour/readme.txt +++ b/src/wp-content/themes/twentytwentyfour/readme.txt @@ -40,7 +40,7 @@ https://wordpress.org/documentation/article/twenty-twenty-four-changelog/#Versio == Copyright == -Twenty Twenty-Four WordPress Theme, (C) 2023-2025 WordPress.org and contributors. +Twenty Twenty-Four WordPress Theme, (C) 2023-2026 WordPress.org and contributors. Twenty Twenty-Four is distributed under the terms of the GNU GPL. This program is free software: you can redistribute it and/or modify diff --git a/src/wp-content/themes/twentytwentyone/readme.txt b/src/wp-content/themes/twentytwentyone/readme.txt index ef430aeeb55c4..704d585b38b87 100644 --- a/src/wp-content/themes/twentytwentyone/readme.txt +++ b/src/wp-content/themes/twentytwentyone/readme.txt @@ -122,7 +122,7 @@ https://wordpress.org/documentation/article/twenty-twenty-one-changelog/#Version == Copyright == -Twenty Twenty-One WordPress Theme, 2020-2025 WordPress.org and contributors. +Twenty Twenty-One WordPress Theme, 2020-2026 WordPress.org and contributors. Twenty Twenty-One is distributed under the terms of the GNU GPL. This program is free software: you can redistribute it and/or modify @@ -140,19 +140,19 @@ Twenty Twenty-One is derived from Seedlet, (C) 2020 Automattic, Inc. Twenty Twenty-One is also based on: -Twenty Nineteen. 2018-2025 WordPress.org +Twenty Nineteen. 2018-2026 WordPress.org Twenty Nineteen is distributed under the terms of the GNU GPL v2 or later. -Twenty Seventeen. Copyright (C) 2016-2025 WordPress.org +Twenty Seventeen. Copyright (C) 2016-2026 WordPress.org Twenty Seventeen is distributed under the terms of the GNU GPL v2 or later. -Twenty Sixteen. Copyright (C) 2015-2025 WordPress.org +Twenty Sixteen. Copyright (C) 2015-2026 WordPress.org Twenty Sixteen is distributed under the terms of the GNU GPL v2 or later. -Twenty Twenty. Copyright (C) 2020-2025 WordPress.org +Twenty Twenty. Copyright (C) 2020-2026 WordPress.org Twenty Twenty is distributed under the terms of the GNU GPL v2 or later. -Underscores https://underscores.me/, Copyright (C) 2012-2025 Automattic, Inc. +Underscores https://underscores.me/, Copyright (C) 2012-2026 Automattic, Inc. Underscores is distributed under the terms of the GNU GPL v2 or later. Normalizing styles have been helped along thanks to the fine work of diff --git a/src/wp-content/themes/twentytwentythree/readme.txt b/src/wp-content/themes/twentytwentythree/readme.txt index 3c242e572fed2..20e133178ae9f 100644 --- a/src/wp-content/themes/twentytwentythree/readme.txt +++ b/src/wp-content/themes/twentytwentythree/readme.txt @@ -52,7 +52,7 @@ https://wordpress.org/documentation/article/twenty-twenty-three-changelog/#Versi == Copyright == -Twenty Twenty-Three WordPress Theme, (C) 2022-2025 WordPress.org and contributors. +Twenty Twenty-Three WordPress Theme, (C) 2022-2026 WordPress.org and contributors. Twenty Twenty-Three is distributed under the terms of the GNU GPL. This program is free software: you can redistribute it and/or modify diff --git a/src/wp-content/themes/twentytwentytwo/readme.txt b/src/wp-content/themes/twentytwentytwo/readme.txt index 838f24432c1ed..d29eff85ab8ee 100644 --- a/src/wp-content/themes/twentytwentytwo/readme.txt +++ b/src/wp-content/themes/twentytwentytwo/readme.txt @@ -101,7 +101,7 @@ https://wordpress.org/documentation/article/twenty-twenty-two-changelog/#Version == Copyright == -Twenty Twenty-Two WordPress Theme, 2021-2025 WordPress.org and contributors. +Twenty Twenty-Two WordPress Theme, 2021-2026 WordPress.org and contributors. Twenty Twenty-Two is distributed under the terms of the GNU GPL. This program is free software: you can redistribute it and/or modify From 3c12b50156ddebf22710d365999040939d6d2f46 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Thu, 1 Jan 2026 08:43:49 +0000 Subject: [PATCH 071/126] Tests: Update regex to match PHP security releases in addition to stable releases. PHP 8.3 changed from "Active support" to "Security fixes only" on January 1, 2026. Follow-up to [61421], [33937]. Props mukesh27, westonruter. See #33758. git-svn-id: https://develop.svn.wordpress.org/trunk@61422 602fd350-edb4-49c9-b593-d223f7449a82 --- tests/phpunit/tests/readme.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/phpunit/tests/readme.php b/tests/phpunit/tests/readme.php index 89281e2be612e..036abf93c25cf 100644 --- a/tests/phpunit/tests/readme.php +++ b/tests/phpunit/tests/readme.php @@ -20,7 +20,7 @@ public function test_readme_php_version() { $response_body = $this->get_response_body( 'https://www.php.net/supported-versions.php' ); - preg_match_all( '#\s*\s*]*>\s*([0-9.]*)#s', $response_body, $php_matches ); + preg_match_all( '#\s*\s*]*>\s*([0-9.]*)#s', $response_body, $php_matches ); $this->assertContains( $matches[1], $php_matches[1], "readme.html's Recommended PHP version is too old. Remember to update the WordPress.org Requirements page, too." ); } From 2c4d5d97357167d18f7995f08bcd5ea06aa17278 Mon Sep 17 00:00:00 2001 From: Sergey Biryukov Date: Fri, 2 Jan 2026 22:10:33 +0000 Subject: [PATCH 072/126] Tests: Reset environment before performing assertions in `populate_network()` tests. This aims to avoid affecting other tests in case of failure. Follow-up to [60954], [61420]. See #64225. git-svn-id: https://develop.svn.wordpress.org/trunk@61423 602fd350-edb4-49c9-b593-d223f7449a82 --- .../tests/multisite/populateNetworkHooks.php | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/tests/phpunit/tests/multisite/populateNetworkHooks.php b/tests/phpunit/tests/multisite/populateNetworkHooks.php index d315d98bae120..c642a0efb3366 100644 --- a/tests/phpunit/tests/multisite/populateNetworkHooks.php +++ b/tests/phpunit/tests/multisite/populateNetworkHooks.php @@ -56,6 +56,13 @@ public function test_before_populate_network_hook() { ) ); + remove_action( 'before_populate_network', array( $this, 'hook_action_counter' ), 10 ); + remove_action( 'after_populate_network', array( $this, 'hook_action_counter' ), 10 ); + + global $wpdb; + $wpdb->query( $wpdb->prepare( "DELETE FROM {$wpdb->sitemeta} WHERE site_id = %d", $network_id ) ); + $wpdb->query( $wpdb->prepare( "DELETE FROM {$wpdb->site} WHERE id = %d", $network_id ) ); + $this->assertSame( 1, $this->action_counts['before_populate_network'], 'before_populate_network action should fire once' ); $this->assertSame( 1, $this->action_counts['after_populate_network'], 'after_populate_network action should fire once' ); @@ -63,13 +70,6 @@ public function test_before_populate_network_hook() { $this->assertSame( $domain, $this->action_args['before_populate_network']['domain'], 'Domain should match in before_populate_network hook' ); $this->assertSame( $network_id, $this->action_args['after_populate_network']['network_id'], 'Network ID should match in after_populate_network hook' ); $this->assertSame( $domain, $this->action_args['after_populate_network']['domain'], 'Domain should match in after_populate_network hook' ); - - remove_action( 'before_populate_network', array( $this, 'hook_action_counter' ), 10 ); - remove_action( 'after_populate_network', array( $this, 'hook_action_counter' ), 10 ); - - global $wpdb; - $wpdb->query( $wpdb->prepare( "DELETE FROM {$wpdb->sitemeta} WHERE site_id = %d", $network_id ) ); - $wpdb->query( $wpdb->prepare( "DELETE FROM {$wpdb->site} WHERE id = %d", $network_id ) ); } /** @@ -90,13 +90,13 @@ public function test_populate_network_hook_filter() { ) ); - $this->assertTrue( $this->hook_called, 'The modify_domain_hook action should have been called' ); - remove_action( 'before_populate_network', array( $this, 'modify_domain_hook' ), 10 ); global $wpdb; $wpdb->query( $wpdb->prepare( "DELETE FROM {$wpdb->sitemeta} WHERE site_id = %d", $network_id ) ); $wpdb->query( $wpdb->prepare( "DELETE FROM {$wpdb->site} WHERE id = %d", $network_id ) ); + + $this->assertTrue( $this->hook_called, 'The modify_domain_hook action should have been called' ); } /** From 5a10b30597b6e76501c94a1852d03a373320e52f Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Sat, 3 Jan 2026 06:15:57 +0000 Subject: [PATCH 073/126] Code Modernization: Update `tests` to use null coalescing operator in place of `isset()` in ternaries. Developed as a subset of https://github.com/WordPress/wordpress-develop/pull/10654 Follow-up to [61404], [61403]. See #58874, #63430. git-svn-id: https://develop.svn.wordpress.org/trunk@61424 602fd350-edb4-49c9-b593-d223f7449a82 --- .../data/WPHTTP-testcase-redirection-script.php | 6 +++--- tests/phpunit/includes/abstract-testcase.php | 2 +- .../factory/class-wp-unittest-factory-for-term.php | 2 +- tests/phpunit/includes/mock-fs.php | 4 ++-- .../phpunit/tests/abilities-api/wpRegisterAbility.php | 10 +++++----- .../tests/abilities-api/wpRegisterAbilityCategory.php | 10 +++++----- tests/phpunit/tests/admin/wpPluginsListTable.php | 2 +- tests/phpunit/tests/block-bindings/postMetaSource.php | 2 +- tests/phpunit/tests/cron.php | 2 +- tests/phpunit/tests/dependencies/scripts.php | 6 +++--- .../tests/filesystem/wpFilesystemDirect/base.php | 2 +- .../font-library/wpRestFontFamiliesController.php | 4 +--- tests/phpunit/tests/general/wpResourceHints.php | 4 ++-- .../wpInteractivityAPI-wp-router-region.php | 2 +- tests/phpunit/tests/l10n/loadScriptTextdomain.php | 2 +- tests/phpunit/tests/link/getAdjacentPost.php | 4 ++-- tests/phpunit/tests/oembed/controller.php | 2 +- tests/phpunit/tests/post/thumbnails.php | 4 ++-- tests/phpunit/tests/rest-api/application-passwords.php | 2 +- .../rest-api/rest-pattern-directory-controller.php | 2 +- tests/phpunit/tests/rest-api/rest-post-meta-fields.php | 2 +- tests/phpunit/tests/rest-api/rest-term-meta-fields.php | 2 +- tests/phpunit/tests/shortcode.php | 2 +- 23 files changed, 39 insertions(+), 41 deletions(-) diff --git a/tests/phpunit/data/WPHTTP-testcase-redirection-script.php b/tests/phpunit/data/WPHTTP-testcase-redirection-script.php index 94643d3de9c43..6b535a45c36bb 100644 --- a/tests/phpunit/data/WPHTTP-testcase-redirection-script.php +++ b/tests/phpunit/data/WPHTTP-testcase-redirection-script.php @@ -54,7 +54,7 @@ function is_ssl() { if ( isset( $_GET['post-redirect-to-method'] ) ) { $method = $_SERVER['REQUEST_METHOD']; - $response_code = isset( $_GET['response_code'] ) ? $_GET['response_code'] : 301; + $response_code = $_GET['response_code'] ?? 301; if ( 'POST' == $method && ! isset( $_GET['redirection-performed'] ) ) { header( "Location: $url?post-redirect-to-method=1&redirection-performed=1", true, $response_code ); @@ -123,8 +123,8 @@ function is_ssl() { } -$rt = isset($_GET['rt']) ? $_GET['rt'] : 5; -$r = isset($_GET['r']) ? $_GET['r'] : 0; +$rt = $_GET['rt'] ?? 5; +$r = $_GET['r'] ?? 0; if ( $r < $rt ) { $code = isset($_GET['code']) ? (int)$_GET['code'] : 302; diff --git a/tests/phpunit/includes/abstract-testcase.php b/tests/phpunit/includes/abstract-testcase.php index 5b080fc7ceb9f..35bf18f688feb 100644 --- a/tests/phpunit/includes/abstract-testcase.php +++ b/tests/phpunit/includes/abstract-testcase.php @@ -1313,7 +1313,7 @@ public function go_to( $url ) { } $parts = parse_url( $url ); if ( isset( $parts['scheme'] ) ) { - $req = isset( $parts['path'] ) ? $parts['path'] : ''; + $req = $parts['path'] ?? ''; if ( isset( $parts['query'] ) ) { $req .= '?' . $parts['query']; // Parse the URL query vars into $_GET. diff --git a/tests/phpunit/includes/factory/class-wp-unittest-factory-for-term.php b/tests/phpunit/includes/factory/class-wp-unittest-factory-for-term.php index ee082b3f97de1..6b2b7340df176 100644 --- a/tests/phpunit/includes/factory/class-wp-unittest-factory-for-term.php +++ b/tests/phpunit/includes/factory/class-wp-unittest-factory-for-term.php @@ -109,7 +109,7 @@ public function create_and_get( $args = array(), $generation_definitions = null return $term_id; } - $taxonomy = isset( $args['taxonomy'] ) ? $args['taxonomy'] : $this->taxonomy; + $taxonomy = $args['taxonomy'] ?? $this->taxonomy; return get_term( $term_id, $taxonomy ); } diff --git a/tests/phpunit/includes/mock-fs.php b/tests/phpunit/includes/mock-fs.php index 40705dc41141d..5a54e49039a21 100644 --- a/tests/phpunit/includes/mock-fs.php +++ b/tests/phpunit/includes/mock-fs.php @@ -46,7 +46,7 @@ public function init( $paths = '', $home_dir = '/' ) { '/' => $this->fs, ); $this->cache = array(); // Used by find_folder() and friends. - $this->cwd = isset( $this->fs_map[ $home_dir ] ) ? $this->fs_map[ $home_dir ] : '/'; + $this->cwd = $this->fs_map[ $home_dir ] ?? '/'; $this->setfs( $paths ); } @@ -79,7 +79,7 @@ public function setfs( $paths ) { * Locates a filesystem "node" */ private function locate_node( $path ) { - return isset( $this->fs_map[ $path ] ) ? $this->fs_map[ $path ] : false; + return $this->fs_map[ $path ] ?? false; } /** diff --git a/tests/phpunit/tests/abilities-api/wpRegisterAbility.php b/tests/phpunit/tests/abilities-api/wpRegisterAbility.php index d07de062e12b2..61bf8f59dba53 100644 --- a/tests/phpunit/tests/abilities-api/wpRegisterAbility.php +++ b/tests/phpunit/tests/abilities-api/wpRegisterAbility.php @@ -154,7 +154,7 @@ public function test_register_ability_no_init_action(): void { global $wp_actions; // Store the original action count. - $original_count = isset( $wp_actions['init'] ) ? $wp_actions['init'] : 0; + $original_count = $wp_actions['init'] ?? 0; // Reset the action count to simulate it not being fired. unset( $wp_actions['init'] ); @@ -450,7 +450,7 @@ public function test_unregister_ability_no_init_action(): void { global $wp_actions; // Store the original action count. - $original_count = isset( $wp_actions['init'] ) ? $wp_actions['init'] : 0; + $original_count = $wp_actions['init'] ?? 0; // Reset the action count to simulate it not being fired. unset( $wp_actions['init'] ); @@ -496,7 +496,7 @@ public function test_get_ability_no_init_action(): void { global $wp_actions; // Store the original action count. - $original_count = isset( $wp_actions['init'] ) ? $wp_actions['init'] : 0; + $original_count = $wp_actions['init'] ?? 0; // Reset the action count to simulate it not being fired. unset( $wp_actions['init'] ); @@ -559,7 +559,7 @@ public function test_has_ability_no_init_action(): void { global $wp_actions; // Store the original action count. - $original_count = isset( $wp_actions['init'] ) ? $wp_actions['init'] : 0; + $original_count = $wp_actions['init'] ?? 0; // Reset the action count to simulate it not being fired. unset( $wp_actions['init'] ); @@ -615,7 +615,7 @@ public function test_get_abilities_no_init_action(): void { global $wp_actions; // Store the original action count. - $original_count = isset( $wp_actions['init'] ) ? $wp_actions['init'] : 0; + $original_count = $wp_actions['init'] ?? 0; // Reset the action count to simulate it not being fired. unset( $wp_actions['init'] ); diff --git a/tests/phpunit/tests/abilities-api/wpRegisterAbilityCategory.php b/tests/phpunit/tests/abilities-api/wpRegisterAbilityCategory.php index 169ea287d5e80..5a59b1050bf25 100644 --- a/tests/phpunit/tests/abilities-api/wpRegisterAbilityCategory.php +++ b/tests/phpunit/tests/abilities-api/wpRegisterAbilityCategory.php @@ -82,7 +82,7 @@ public function test_register_ability_category_no_init_action(): void { global $wp_actions; // Store the original action count. - $original_count = isset( $wp_actions['init'] ) ? $wp_actions['init'] : 0; + $original_count = $wp_actions['init'] ?? 0; // Reset the action count to simulate it not being fired. unset( $wp_actions['init'] ); @@ -132,7 +132,7 @@ public function test_unregister_ability_category_no_init_action(): void { global $wp_actions; // Store the original action count. - $original_count = isset( $wp_actions['init'] ) ? $wp_actions['init'] : 0; + $original_count = $wp_actions['init'] ?? 0; // Reset the action count to simulate it not being fired. unset( $wp_actions['init'] ); @@ -194,7 +194,7 @@ public function test_has_ability_category_no_init_action(): void { global $wp_actions; // Store the original action count. - $original_count = isset( $wp_actions['init'] ) ? $wp_actions['init'] : 0; + $original_count = $wp_actions['init'] ?? 0; // Reset the action count to simulate it not being fired. unset( $wp_actions['init'] ); @@ -255,7 +255,7 @@ public function test_get_ability_category_no_init_action(): void { global $wp_actions; // Store the original action count. - $original_count = isset( $wp_actions['init'] ) ? $wp_actions['init'] : 0; + $original_count = $wp_actions['init'] ?? 0; // Reset the action count to simulate it not being fired. unset( $wp_actions['init'] ); @@ -328,7 +328,7 @@ public function test_get_ability_categories_no_init_action(): void { global $wp_actions; // Store the original action count. - $original_count = isset( $wp_actions['init'] ) ? $wp_actions['init'] : 0; + $original_count = $wp_actions['init'] ?? 0; // Reset the action count to simulate it not being fired. unset( $wp_actions['init'] ); diff --git a/tests/phpunit/tests/admin/wpPluginsListTable.php b/tests/phpunit/tests/admin/wpPluginsListTable.php index e75a473e2ba82..daa54750fdf9e 100644 --- a/tests/phpunit/tests/admin/wpPluginsListTable.php +++ b/tests/phpunit/tests/admin/wpPluginsListTable.php @@ -137,7 +137,7 @@ public function test_get_views_should_return_views_by_default() { * @param string $status The value for $_REQUEST['plugin_status']. */ public function test_construct_should_not_set_show_autoupdates_to_false_for_mustuse_and_dropins( $status ) { - $original_status = isset( $_REQUEST['plugin_status'] ) ? $_REQUEST['plugin_status'] : null; + $original_status = $_REQUEST['plugin_status'] ?? null; $_REQUEST['plugin_status'] = $status; // Enable plugin auto-updates. diff --git a/tests/phpunit/tests/block-bindings/postMetaSource.php b/tests/phpunit/tests/block-bindings/postMetaSource.php index 0a305314b7869..927d290f80557 100644 --- a/tests/phpunit/tests/block-bindings/postMetaSource.php +++ b/tests/phpunit/tests/block-bindings/postMetaSource.php @@ -28,7 +28,7 @@ private function get_modified_post_content( $content ) { */ public static function wpSetUpBeforeClass( WP_UnitTest_Factory $factory ) { self::$post = $factory->post->create_and_get(); - self::$wp_meta_keys_saved = isset( $GLOBALS['wp_meta_keys'] ) ? $GLOBALS['wp_meta_keys'] : array(); + self::$wp_meta_keys_saved = $GLOBALS['wp_meta_keys'] ?? array(); } /** diff --git a/tests/phpunit/tests/cron.php b/tests/phpunit/tests/cron.php index f79772074fc83..7abaf5c92095e 100644 --- a/tests/phpunit/tests/cron.php +++ b/tests/phpunit/tests/cron.php @@ -460,7 +460,7 @@ public function filter_pre_schedule_event_filter( $result, $event ) { $this->preflight_cron_array[ $event->timestamp ][ $event->hook ][ $key ] = array( 'schedule' => $event->schedule, - 'interval' => isset( $event->interval ) ? $event->interval : 0, + 'interval' => $event->interval ?? 0, 'args' => $event->args, ); uksort( $this->preflight_cron_array, 'strnatcasecmp' ); diff --git a/tests/phpunit/tests/dependencies/scripts.php b/tests/phpunit/tests/dependencies/scripts.php index 934d7c039f1e7..ed742f4040133 100644 --- a/tests/phpunit/tests/dependencies/scripts.php +++ b/tests/phpunit/tests/dependencies/scripts.php @@ -37,9 +37,9 @@ class Tests_Dependencies_Scripts extends WP_UnitTestCase { public function set_up() { parent::set_up(); - $this->old_wp_scripts = isset( $GLOBALS['wp_scripts'] ) ? $GLOBALS['wp_scripts'] : null; - $this->old_wp_styles = isset( $GLOBALS['wp_styles'] ) ? $GLOBALS['wp_styles'] : null; - $this->old_concatenate_scripts = isset( $GLOBALS['concatenate_scripts'] ) ? $GLOBALS['concatenate_scripts'] : null; + $this->old_wp_scripts = $GLOBALS['wp_scripts'] ?? null; + $this->old_wp_styles = $GLOBALS['wp_styles'] ?? null; + $this->old_concatenate_scripts = $GLOBALS['concatenate_scripts'] ?? null; remove_action( 'wp_default_scripts', 'wp_default_scripts' ); remove_action( 'wp_default_scripts', 'wp_default_packages' ); $GLOBALS['wp_scripts'] = new WP_Scripts(); diff --git a/tests/phpunit/tests/filesystem/wpFilesystemDirect/base.php b/tests/phpunit/tests/filesystem/wpFilesystemDirect/base.php index 97165de5c88df..96b449dd0306a 100644 --- a/tests/phpunit/tests/filesystem/wpFilesystemDirect/base.php +++ b/tests/phpunit/tests/filesystem/wpFilesystemDirect/base.php @@ -90,7 +90,7 @@ public function set_up() { } elseif ( 'f' === $entry['type'] ) { $this->create_file_if_needed( $entry['path'], - isset( $entry['contents'] ) ? $entry['contents'] : '' + $entry['contents'] ?? '' ); } } diff --git a/tests/phpunit/tests/fonts/font-library/wpRestFontFamiliesController.php b/tests/phpunit/tests/fonts/font-library/wpRestFontFamiliesController.php index ef1ced421c25e..c63f9814719a0 100644 --- a/tests/phpunit/tests/fonts/font-library/wpRestFontFamiliesController.php +++ b/tests/phpunit/tests/fonts/font-library/wpRestFontFamiliesController.php @@ -1048,9 +1048,7 @@ protected function check_font_family_data( $data, $post_id, $links ) { $expected = rest_url( 'wp/v2/font-families/' . $post->ID . '/font-faces/' . $font_face_ids[ $index ] ); $this->assertSame( $expected, $link['href'], 'The links for a font faces URL from the response data should match the REST endpoint.' ); - $embeddable = isset( $link['attributes']['embeddable'] ) - ? $link['attributes']['embeddable'] - : $link['embeddable']; + $embeddable = $link['attributes']['embeddable'] ?? $link['embeddable']; $this->assertTrue( $embeddable, 'The embeddable should be true.' ); } } diff --git a/tests/phpunit/tests/general/wpResourceHints.php b/tests/phpunit/tests/general/wpResourceHints.php index d0ece5d9ac874..3b546dc6e254e 100644 --- a/tests/phpunit/tests/general/wpResourceHints.php +++ b/tests/phpunit/tests/general/wpResourceHints.php @@ -12,8 +12,8 @@ class Tests_General_wpResourceHints extends WP_UnitTestCase { public function set_up() { parent::set_up(); - $this->old_wp_scripts = isset( $GLOBALS['wp_scripts'] ) ? $GLOBALS['wp_scripts'] : null; - $this->old_wp_styles = isset( $GLOBALS['wp_styles'] ) ? $GLOBALS['wp_styles'] : null; + $this->old_wp_scripts = $GLOBALS['wp_scripts'] ?? null; + $this->old_wp_styles = $GLOBALS['wp_styles'] ?? null; remove_action( 'wp_default_scripts', 'wp_default_scripts' ); remove_action( 'wp_default_styles', 'wp_default_styles' ); diff --git a/tests/phpunit/tests/interactivity-api/wpInteractivityAPI-wp-router-region.php b/tests/phpunit/tests/interactivity-api/wpInteractivityAPI-wp-router-region.php index d6deab48ab141..f5e5e3a62d37c 100644 --- a/tests/phpunit/tests/interactivity-api/wpInteractivityAPI-wp-router-region.php +++ b/tests/phpunit/tests/interactivity-api/wpInteractivityAPI-wp-router-region.php @@ -45,7 +45,7 @@ public function set_up() { $wp_filter['wp_footer'] = new WP_Hook(); // Removes all registered styles. - $this->original_wp_styles = isset( $GLOBALS['wp_styles'] ) ? $GLOBALS['wp_styles'] : null; + $this->original_wp_styles = $GLOBALS['wp_styles'] ?? null; $GLOBALS['wp_styles'] = new WP_Styles(); remove_action( 'wp_default_styles', 'wp_default_styles' ); remove_action( 'wp_print_styles', 'print_emoji_styles' ); diff --git a/tests/phpunit/tests/l10n/loadScriptTextdomain.php b/tests/phpunit/tests/l10n/loadScriptTextdomain.php index bc028fbfa5e4d..7aedd92cc666c 100644 --- a/tests/phpunit/tests/l10n/loadScriptTextdomain.php +++ b/tests/phpunit/tests/l10n/loadScriptTextdomain.php @@ -20,7 +20,7 @@ class Tests_L10n_LoadScriptTextdomain extends WP_UnitTestCase { */ public function test_resolve_relative_path( $translation_path, $handle, $src, $textdomain, $filter = array() ) { if ( ! empty( $filter ) ) { - add_filter( $filter[0], $filter[1], 10, isset( $filter[2] ) ? $filter[2] : 1 ); + add_filter( $filter[0], $filter[1], 10, $filter[2] ?? 1 ); } wp_enqueue_script( $handle, $src, array(), null ); diff --git a/tests/phpunit/tests/link/getAdjacentPost.php b/tests/phpunit/tests/link/getAdjacentPost.php index 4d68493bfe8de..7fdd06ec75ead 100644 --- a/tests/phpunit/tests/link/getAdjacentPost.php +++ b/tests/phpunit/tests/link/getAdjacentPost.php @@ -192,7 +192,7 @@ public function test_get_adjacent_post_excluded_terms() { wp_set_post_terms( $p2, array( $t ), 'wptests_tax' ); // Fake current page. - $_post = isset( $GLOBALS['post'] ) ? $GLOBALS['post'] : null; + $_post = $GLOBALS['post'] ?? null; $GLOBALS['post'] = get_post( $p1 ); $found = get_adjacent_post( false, array( $t ), true, 'wptests_tax' ); @@ -229,7 +229,7 @@ public function test_get_adjacent_post_excluded_terms_should_not_require_posts_t wp_delete_object_term_relationships( $p3, 'category' ); // Fake current page. - $_post = isset( $GLOBALS['post'] ) ? $GLOBALS['post'] : null; + $_post = $GLOBALS['post'] ?? null; $GLOBALS['post'] = get_post( $p1 ); $found = get_adjacent_post( false, array( $t ), true, 'wptests_tax' ); diff --git a/tests/phpunit/tests/oembed/controller.php b/tests/phpunit/tests/oembed/controller.php index aa0275c4c87ee..c8d9f00af05e7 100644 --- a/tests/phpunit/tests/oembed/controller.php +++ b/tests/phpunit/tests/oembed/controller.php @@ -93,7 +93,7 @@ public function mock_embed_request( $response, $parsed_args, $url ) { unset( $response, $parsed_args ); $parsed_url = wp_parse_url( $url ); - $query = isset( $parsed_url['query'] ) ? $parsed_url['query'] : ''; + $query = $parsed_url['query'] ?? ''; parse_str( $query, $query_params ); $this->request_count += 1; diff --git a/tests/phpunit/tests/post/thumbnails.php b/tests/phpunit/tests/post/thumbnails.php index 8f596cbe7f679..4c4885b00b23e 100644 --- a/tests/phpunit/tests/post/thumbnails.php +++ b/tests/phpunit/tests/post/thumbnails.php @@ -287,7 +287,7 @@ public function test_the_post_thumbnail_url() { * @ticket 12922 */ public function test__wp_preview_post_thumbnail_filter() { - $old_post = isset( $GLOBALS['post'] ) ? $GLOBALS['post'] : null; + $old_post = $GLOBALS['post'] ?? null; $GLOBALS['post'] = self::$post; $_REQUEST['_thumbnail_id'] = self::$attachment_id; @@ -307,7 +307,7 @@ public function test__wp_preview_post_thumbnail_filter() { * @ticket 37697 */ public function test__wp_preview_post_thumbnail_filter_secondary_post() { - $old_post = isset( $GLOBALS['post'] ) ? $GLOBALS['post'] : null; + $old_post = $GLOBALS['post'] ?? null; $secondary_post = self::factory()->post->create( array( diff --git a/tests/phpunit/tests/rest-api/application-passwords.php b/tests/phpunit/tests/rest-api/application-passwords.php index 3dd76c0f94d61..65e3bf222d85f 100644 --- a/tests/phpunit/tests/rest-api/application-passwords.php +++ b/tests/phpunit/tests/rest-api/application-passwords.php @@ -154,7 +154,7 @@ public function test_update_application_password( array $update, array $existing // Check updated only given values. $updated_item = WP_Application_Passwords::get_user_application_password( self::$user_id, $uuid ); foreach ( $updated_item as $key => $update_value ) { - $expected_value = isset( $update[ $key ] ) ? $update[ $key ] : $original_item[ $key ]; + $expected_value = $update[ $key ] ?? $original_item[ $key ]; $this->assertSame( $expected_value, $update_value ); } } diff --git a/tests/phpunit/tests/rest-api/rest-pattern-directory-controller.php b/tests/phpunit/tests/rest-api/rest-pattern-directory-controller.php index 038994cdd1183..6f84306dad61f 100644 --- a/tests/phpunit/tests/rest-api/rest-pattern-directory-controller.php +++ b/tests/phpunit/tests/rest-api/rest-pattern-directory-controller.php @@ -82,7 +82,7 @@ public function tear_down() { */ public function assertPatternMatchesSchema( $pattern ) { $schema = static::$controller->get_item_schema(); - $pattern_id = isset( $pattern->id ) ? $pattern->id : '{pattern ID is missing}'; + $pattern_id = $pattern->id ?? '{pattern ID is missing}'; $this->assertTrue( rest_validate_value_from_schema( $pattern, $schema ), diff --git a/tests/phpunit/tests/rest-api/rest-post-meta-fields.php b/tests/phpunit/tests/rest-api/rest-post-meta-fields.php index 47eada094d0ee..5ce72a57fa55f 100644 --- a/tests/phpunit/tests/rest-api/rest-post-meta-fields.php +++ b/tests/phpunit/tests/rest-api/rest-post-meta-fields.php @@ -21,7 +21,7 @@ public static function wpSetUpBeforeClass( WP_UnitTest_Factory $factory ) { ) ); - self::$wp_meta_keys_saved = isset( $GLOBALS['wp_meta_keys'] ) ? $GLOBALS['wp_meta_keys'] : array(); + self::$wp_meta_keys_saved = $GLOBALS['wp_meta_keys'] ?? array(); self::$post_id = $factory->post->create(); self::$cpt_post_id = $factory->post->create( array( 'post_type' => 'cpt' ) ); } diff --git a/tests/phpunit/tests/rest-api/rest-term-meta-fields.php b/tests/phpunit/tests/rest-api/rest-term-meta-fields.php index 8d4ba295f87a5..737fa90d84633 100644 --- a/tests/phpunit/tests/rest-api/rest-term-meta-fields.php +++ b/tests/phpunit/tests/rest-api/rest-term-meta-fields.php @@ -21,7 +21,7 @@ public static function wpSetUpBeforeClass( WP_UnitTest_Factory $factory ) { ) ); - self::$wp_meta_keys_saved = isset( $GLOBALS['wp_meta_keys'] ) ? $GLOBALS['wp_meta_keys'] : array(); + self::$wp_meta_keys_saved = $GLOBALS['wp_meta_keys'] ?? array(); self::$category_id = $factory->category->create(); self::$customtax_term_id = $factory->term->create( array( 'taxonomy' => 'customtax' ) ); } diff --git a/tests/phpunit/tests/shortcode.php b/tests/phpunit/tests/shortcode.php index 269da2b05e34d..7467d1ed7e6a3 100644 --- a/tests/phpunit/tests/shortcode.php +++ b/tests/phpunit/tests/shortcode.php @@ -48,7 +48,7 @@ public function shortcode_test_shortcode_tag( $atts, $content = null, $tagname = // [footag foo="bar"] public function shortcode_footag( $atts ) { - $foo = isset( $atts['foo'] ) ? $atts['foo'] : ''; + $foo = $atts['foo'] ?? ''; return "foo = $foo"; } From e2e617682851d6ba85a304a8484c92ab5242c69a Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Sat, 3 Jan 2026 07:15:32 +0000 Subject: [PATCH 074/126] Script Loader: Simplify data structure in `wp_default_packages_vendor()` to facilitate static analysis. This resolves two PHPStan level 7 issues: `offsetAccess.notFound` and `argument.type`. Follow-up to [44114]. See #64238, #45065. git-svn-id: https://develop.svn.wordpress.org/trunk@61425 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/script-loader.php | 46 +++++++++++++++---------------- 1 file changed, 22 insertions(+), 24 deletions(-) diff --git a/src/wp-includes/script-loader.php b/src/wp-includes/script-loader.php index c0108dc848276..6408ff158a6d5 100644 --- a/src/wp-includes/script-loader.php +++ b/src/wp-includes/script-loader.php @@ -88,21 +88,21 @@ function wp_default_packages_vendor( $scripts ) { $suffix = wp_scripts_get_suffix(); $vendor_scripts = array( - 'react', - 'react-dom' => array( 'react' ), - 'react-jsx-runtime' => array( 'react' ), - 'regenerator-runtime', - 'moment', - 'lodash', - 'wp-polyfill-fetch', - 'wp-polyfill-formdata', - 'wp-polyfill-node-contains', - 'wp-polyfill-url', - 'wp-polyfill-dom-rect', - 'wp-polyfill-element-closest', - 'wp-polyfill-object-fit', - 'wp-polyfill-inert', - 'wp-polyfill', + 'react' => array(), + 'react-dom' => array( 'react' ), + 'react-jsx-runtime' => array( 'react' ), + 'regenerator-runtime' => array(), + 'moment' => array(), + 'lodash' => array(), + 'wp-polyfill-fetch' => array(), + 'wp-polyfill-formdata' => array(), + 'wp-polyfill-node-contains' => array(), + 'wp-polyfill-url' => array(), + 'wp-polyfill-dom-rect' => array(), + 'wp-polyfill-element-closest' => array(), + 'wp-polyfill-object-fit' => array(), + 'wp-polyfill-inert' => array(), + 'wp-polyfill' => array(), ); $vendor_scripts_versions = array( @@ -124,15 +124,13 @@ function wp_default_packages_vendor( $scripts ) { ); foreach ( $vendor_scripts as $handle => $dependencies ) { - if ( is_string( $dependencies ) ) { - $handle = $dependencies; - $dependencies = array(); - } - - $path = "/wp-includes/js/dist/vendor/$handle$suffix.js"; - $version = $vendor_scripts_versions[ $handle ]; - - $scripts->add( $handle, $path, $dependencies, $version, 1 ); + $scripts->add( + $handle, + "/wp-includes/js/dist/vendor/$handle$suffix.js", + $dependencies, + $vendor_scripts_versions[ $handle ], + 1 + ); } did_action( 'init' ) && $scripts->add_inline_script( 'lodash', 'window.lodash = _.noConflict();' ); From 94b1c4e0558a142b60a1b4fe801887e923afe2c6 Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Sat, 3 Jan 2026 07:37:01 +0000 Subject: [PATCH 075/126] Script Loader: Add types for arrays in phpdoc. This resolves 10 `missingType.iterableValue` issues in PHPStan. Follow-up to [61402], [61362], [61358]. See #64224, #64238. git-svn-id: https://develop.svn.wordpress.org/trunk@61426 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-includes/script-loader.php | 34 +++++++++++++++---------------- 1 file changed, 17 insertions(+), 17 deletions(-) diff --git a/src/wp-includes/script-loader.php b/src/wp-includes/script-loader.php index 6408ff158a6d5..9d2df0dac687f 100644 --- a/src/wp-includes/script-loader.php +++ b/src/wp-includes/script-loader.php @@ -2347,7 +2347,7 @@ function print_admin_styles() { * @global WP_Styles $wp_styles * @global bool $concatenate_scripts * - * @return array|void + * @return string[]|void */ function print_late_styles() { global $wp_styles, $concatenate_scripts; @@ -2504,8 +2504,8 @@ function wp_common_block_scripts_and_styles() { * * @since 6.1.0 * - * @param array $nodes The nodes to filter. - * @return array A filtered array of style nodes. + * @param array> $nodes The nodes to filter. + * @return array> A filtered array of style nodes. */ function wp_filter_out_block_nodes( $nodes ) { return array_filter( @@ -2865,7 +2865,7 @@ function wp_enqueue_editor_format_library_assets() { * * @since 5.7.0 * - * @param array $attributes Key-value pairs representing ` - ', '' ), '', ob_get_clean() ) ) . - "\n//# sourceURL=" . rawurlencode( __FUNCTION__ ) - ); -} - -/** - * Register archives block. - * - * @since 5.0.0 - */ -function register_block_core_archives() { - register_block_type_from_metadata( - __DIR__ . '/archives', - array( - 'render_callback' => 'render_block_core_archives', - ) - ); -} -add_action( 'init', 'register_block_core_archives' ); diff --git a/src/wp-includes/blocks/archives/block.json b/src/wp-includes/blocks/archives/block.json deleted file mode 100644 index 0351a4b694c00..0000000000000 --- a/src/wp-includes/blocks/archives/block.json +++ /dev/null @@ -1,71 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/archives", - "title": "Archives", - "category": "widgets", - "description": "Display a date archive of your posts.", - "textdomain": "default", - "attributes": { - "displayAsDropdown": { - "type": "boolean", - "default": false - }, - "showLabel": { - "type": "boolean", - "default": true - }, - "showPostCounts": { - "type": "boolean", - "default": false - }, - "type": { - "type": "string", - "default": "monthly" - } - }, - "supports": { - "align": true, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true - }, - "html": false, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-archives-editor" -} diff --git a/src/wp-includes/blocks/audio/block.json b/src/wp-includes/blocks/audio/block.json deleted file mode 100644 index 9b77efee23cce..0000000000000 --- a/src/wp-includes/blocks/audio/block.json +++ /dev/null @@ -1,68 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/audio", - "title": "Audio", - "category": "media", - "description": "Embed a simple audio player.", - "keywords": [ "music", "sound", "podcast", "recording" ], - "textdomain": "default", - "attributes": { - "blob": { - "type": "string", - "role": "local" - }, - "src": { - "type": "string", - "source": "attribute", - "selector": "audio", - "attribute": "src", - "role": "content" - }, - "caption": { - "type": "rich-text", - "source": "rich-text", - "selector": "figcaption", - "role": "content" - }, - "id": { - "type": "number", - "role": "content" - }, - "autoplay": { - "type": "boolean", - "source": "attribute", - "selector": "audio", - "attribute": "autoplay" - }, - "loop": { - "type": "boolean", - "source": "attribute", - "selector": "audio", - "attribute": "loop" - }, - "preload": { - "type": "string", - "source": "attribute", - "selector": "audio", - "attribute": "preload" - } - }, - "supports": { - "anchor": true, - "align": true, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-audio-editor", - "style": "wp-block-audio" -} diff --git a/src/wp-includes/blocks/avatar.php b/src/wp-includes/blocks/avatar.php deleted file mode 100644 index d4a01c1c3a1e7..0000000000000 --- a/src/wp-includes/blocks/avatar.php +++ /dev/null @@ -1,166 +0,0 @@ -context['commentId'] ) ) { - if ( isset( $attributes['userId'] ) ) { - $author_id = $attributes['userId']; - } elseif ( isset( $block->context['postId'] ) ) { - $author_id = get_post_field( 'post_author', $block->context['postId'] ); - } else { - $author_id = get_query_var( 'author' ); - } - - if ( empty( $author_id ) ) { - return ''; - } - - $author_name = get_the_author_meta( 'display_name', $author_id ); - // translators: %s: Author name. - $alt = sprintf( __( '%s Avatar' ), $author_name ); - $avatar_block = get_avatar( - $author_id, - $size, - '', - $alt, - array( - 'extra_attr' => $image_styles, - 'class' => $image_classes, - ) - ); - if ( isset( $attributes['isLink'] ) && $attributes['isLink'] ) { - $label = ''; - if ( '_blank' === $attributes['linkTarget'] ) { - // translators: %s is the Author name. - $label = 'aria-label="' . esc_attr( sprintf( __( '(%s author archive, opens in a new tab)' ), $author_name ) ) . '"'; - } - // translators: 1: Author archive link. 2: Link target. %3$s Aria label. %4$s Avatar image. - $avatar_block = sprintf( '%4$s', esc_url( get_author_posts_url( $author_id ) ), esc_attr( $attributes['linkTarget'] ), $label, $avatar_block ); - } - return sprintf( '
%2s
', $wrapper_attributes, $avatar_block ); - } - $comment = get_comment( $block->context['commentId'] ); - if ( ! $comment ) { - return ''; - } - /* translators: %s: Author name. */ - $alt = sprintf( __( '%s Avatar' ), $comment->comment_author ); - $avatar_block = get_avatar( - $comment, - $size, - '', - $alt, - array( - 'extra_attr' => $image_styles, - 'class' => $image_classes, - ) - ); - if ( isset( $attributes['isLink'] ) && $attributes['isLink'] && isset( $comment->comment_author_url ) && '' !== $comment->comment_author_url ) { - $label = ''; - if ( '_blank' === $attributes['linkTarget'] ) { - // translators: %s: Comment author name. - $label = 'aria-label="' . esc_attr( sprintf( __( '(%s website link, opens in a new tab)' ), $comment->comment_author ) ) . '"'; - } - $avatar_block = sprintf( '%4$s', esc_url( $comment->comment_author_url ), esc_attr( $attributes['linkTarget'] ), $label, $avatar_block ); - } - return sprintf( '
%2s
', $wrapper_attributes, $avatar_block ); -} - -/** - * Generates class names and styles to apply the border support styles for - * the Avatar block. - * - * @since 6.3.0 - * - * @param array $attributes The block attributes. - * @return array The border-related classnames and styles for the block. - */ -function get_block_core_avatar_border_attributes( $attributes ) { - $border_styles = array(); - $sides = array( 'top', 'right', 'bottom', 'left' ); - - // Border radius. - if ( isset( $attributes['style']['border']['radius'] ) ) { - $border_styles['radius'] = $attributes['style']['border']['radius']; - } - - // Border style. - if ( isset( $attributes['style']['border']['style'] ) ) { - $border_styles['style'] = $attributes['style']['border']['style']; - } - - // Border width. - if ( isset( $attributes['style']['border']['width'] ) ) { - $border_styles['width'] = $attributes['style']['border']['width']; - } - - // Border color. - $preset_color = array_key_exists( 'borderColor', $attributes ) ? "var:preset|color|{$attributes['borderColor']}" : null; - $custom_color = $attributes['style']['border']['color'] ?? null; - $border_styles['color'] = $preset_color ? $preset_color : $custom_color; - - // Individual border styles e.g. top, left etc. - foreach ( $sides as $side ) { - $border = $attributes['style']['border'][ $side ] ?? null; - $border_styles[ $side ] = array( - 'color' => isset( $border['color'] ) ? $border['color'] : null, - 'style' => isset( $border['style'] ) ? $border['style'] : null, - 'width' => isset( $border['width'] ) ? $border['width'] : null, - ); - } - - $styles = wp_style_engine_get_styles( array( 'border' => $border_styles ) ); - $attributes = array(); - if ( ! empty( $styles['classnames'] ) ) { - $attributes['class'] = $styles['classnames']; - } - if ( ! empty( $styles['css'] ) ) { - $attributes['style'] = $styles['css']; - } - return $attributes; -} - -/** - * Registers the `core/avatar` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_avatar() { - register_block_type_from_metadata( - __DIR__ . '/avatar', - array( - 'render_callback' => 'render_block_core_avatar', - ) - ); -} -add_action( 'init', 'register_block_core_avatar' ); diff --git a/src/wp-includes/blocks/avatar/block.json b/src/wp-includes/blocks/avatar/block.json deleted file mode 100644 index 5c13258bb3c11..0000000000000 --- a/src/wp-includes/blocks/avatar/block.json +++ /dev/null @@ -1,68 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/avatar", - "title": "Avatar", - "category": "theme", - "description": "Add a user’s avatar.", - "textdomain": "default", - "attributes": { - "userId": { - "type": "number" - }, - "size": { - "type": "number", - "default": 96 - }, - "isLink": { - "type": "boolean", - "default": false - }, - "linkTarget": { - "type": "string", - "default": "_self" - } - }, - "usesContext": [ "postType", "postId", "commentId" ], - "supports": { - "html": false, - "align": true, - "alignWide": false, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "__experimentalBorder": { - "__experimentalSkipSerialization": true, - "radius": true, - "width": true, - "color": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true - } - }, - "color": { - "text": false, - "background": false - }, - "filter": { - "duotone": true - }, - "interactivity": { - "clientNavigation": true - } - }, - "selectors": { - "border": ".wp-block-avatar img", - "filter": { - "duotone": ".wp-block-avatar img" - } - }, - "editorStyle": "wp-block-avatar-editor", - "style": "wp-block-avatar" -} diff --git a/src/wp-includes/blocks/block.php b/src/wp-includes/blocks/block.php deleted file mode 100644 index f09d5367a9c89..0000000000000 --- a/src/wp-includes/blocks/block.php +++ /dev/null @@ -1,131 +0,0 @@ -post_type ) { - return ''; - } - - if ( isset( $seen_refs[ $attributes['ref'] ] ) ) { - // WP_DEBUG_DISPLAY must only be honored when WP_DEBUG. This precedent - // is set in `wp_debug_mode()`. - $is_debug = WP_DEBUG && WP_DEBUG_DISPLAY; - - return $is_debug ? - // translators: Visible only in the front end, this warning takes the place of a faulty block. - __( '[block rendering halted]' ) : - ''; - } - - if ( 'publish' !== $reusable_block->post_status || ! empty( $reusable_block->post_password ) ) { - return ''; - } - - $seen_refs[ $attributes['ref'] ] = true; - - // Handle embeds for reusable blocks. - global $wp_embed; - $content = $wp_embed->run_shortcode( $reusable_block->post_content ); - $content = $wp_embed->autoembed( $content ); - - // Back compat. - // For blocks that have not been migrated in the editor, add some back compat - // so that front-end rendering continues to work. - - // This matches the `v2` deprecation. Removes the inner `values` property - // from every item. - if ( isset( $attributes['content'] ) ) { - foreach ( $attributes['content'] as &$content_data ) { - if ( isset( $content_data['values'] ) ) { - $is_assoc_array = is_array( $content_data['values'] ) && ! wp_is_numeric_array( $content_data['values'] ); - - if ( $is_assoc_array ) { - $content_data = $content_data['values']; - } - } - } - } - - // This matches the `v1` deprecation. Rename `overrides` to `content`. - if ( isset( $attributes['overrides'] ) && ! isset( $attributes['content'] ) ) { - $attributes['content'] = $attributes['overrides']; - } - - // Apply Block Hooks. - $content = apply_block_hooks_to_content_from_post_object( $content, $reusable_block ); - - /** - * We attach the blocks from $content as inner blocks to the Synced Pattern block instance. - * This ensures that block context available to the Synced Pattern block instance is provided to - * those blocks. - */ - $block_instance->parsed_block['innerBlocks'] = parse_blocks( $content ); - $block_instance->parsed_block['innerContent'] = array_fill( 0, count( $block_instance->parsed_block['innerBlocks'] ), null ); - if ( method_exists( $block_instance, 'refresh_context_dependents' ) ) { - // WP_Block::refresh_context_dependents() was introduced in WordPress 6.8. - $block_instance->refresh_context_dependents(); - } else { - // This branch can be removed once Gutenberg requires WordPress 6.8 or later. - if ( ! class_exists( 'WP_Block_Cloner' ) ) { - // phpcs:ignore Gutenberg.Commenting.SinceTag.MissingClassSinceTag - class WP_Block_Cloner extends WP_Block { - /** - * Static methods of subclasses have access to protected properties - * of instances of the parent class. - * In this case, this gives us access to `available_context` and `registry`. - */ - // phpcs:ignore Gutenberg.Commenting.SinceTag.MissingMethodSinceTag - public static function clone_instance( $instance ) { - return new WP_Block( - $instance->parsed_block, - $instance->available_context, - $instance->registry - ); - } - } - } - $block_instance = WP_Block_Cloner::clone_instance( $block_instance ); - } - - $content = $block_instance->render( array( 'dynamic' => false ) ); - unset( $seen_refs[ $attributes['ref'] ] ); - - return $content; -} - -/** - * Registers the `core/block` block. - * - * @since 5.3.0 - */ -function register_block_core_block() { - register_block_type_from_metadata( - __DIR__ . '/block', - array( - 'render_callback' => 'render_block_core_block', - ) - ); -} -add_action( 'init', 'register_block_core_block' ); diff --git a/src/wp-includes/blocks/block/block.json b/src/wp-includes/blocks/block/block.json deleted file mode 100644 index fdce3bcc02e07..0000000000000 --- a/src/wp-includes/blocks/block/block.json +++ /dev/null @@ -1,31 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/block", - "title": "Pattern", - "category": "reusable", - "description": "Reuse this design across your site.", - "keywords": [ "reusable" ], - "textdomain": "default", - "attributes": { - "ref": { - "type": "number" - }, - "content": { - "type": "object", - "default": {} - } - }, - "providesContext": { - "pattern/overrides": "content" - }, - "supports": { - "customClassName": false, - "html": false, - "inserter": false, - "renaming": false, - "interactivity": { - "clientNavigation": true - } - } -} diff --git a/src/wp-includes/blocks/blocks-json.php b/src/wp-includes/blocks/blocks-json.php deleted file mode 100644 index 74006dedb2e3f..0000000000000 --- a/src/wp-includes/blocks/blocks-json.php +++ /dev/null @@ -1,8198 +0,0 @@ - array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/accordion', - 'title' => 'Accordion', - 'category' => 'design', - 'description' => 'Displays a foldable layout that groups content in collapsible sections.', - 'example' => array( - - ), - 'supports' => array( - 'anchor' => true, - 'html' => false, - 'align' => array( - 'wide', - 'full' - ), - 'background' => array( - 'backgroundImage' => true, - 'backgroundSize' => true, - '__experimentalDefaultControls' => array( - 'backgroundImage' => true - ) - ), - 'color' => array( - 'background' => true, - 'gradients' => true - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ) - ), - 'spacing' => array( - 'padding' => true, - 'margin' => array( - 'top', - 'bottom' - ), - 'blockGap' => true - ), - 'shadow' => true, - 'layout' => true, - 'ariaLabel' => true, - 'interactivity' => true, - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'contentRole' => true - ), - 'attributes' => array( - 'iconPosition' => array( - 'type' => 'string', - 'default' => 'right' - ), - 'showIcon' => array( - 'type' => 'boolean', - 'default' => true - ), - 'autoclose' => array( - 'type' => 'boolean', - 'default' => false - ), - 'headingLevel' => array( - 'type' => 'number', - 'default' => 3 - ), - 'levelOptions' => array( - 'type' => 'array' - ) - ), - 'providesContext' => array( - 'core/accordion-icon-position' => 'iconPosition', - 'core/accordion-show-icon' => 'showIcon', - 'core/accordion-heading-level' => 'headingLevel' - ), - 'allowedBlocks' => array( - 'core/accordion-item' - ), - 'textdomain' => 'default', - 'viewScriptModule' => '@wordpress/block-library/accordion/view' - ), - 'accordion-heading' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/accordion-heading', - 'title' => 'Accordion Heading', - 'category' => 'design', - 'description' => 'Displays a heading that toggles the accordion panel.', - 'parent' => array( - 'core/accordion-item' - ), - 'usesContext' => array( - 'core/accordion-icon-position', - 'core/accordion-show-icon', - 'core/accordion-heading-level' - ), - 'supports' => array( - 'anchor' => true, - 'color' => array( - 'background' => true, - 'gradients' => true - ), - 'align' => false, - 'interactivity' => true, - 'spacing' => array( - 'padding' => true, - '__experimentalDefaultControls' => array( - 'padding' => true - ), - '__experimentalSkipSerialization' => true, - '__experimentalSelector' => '.wp-block-accordion-heading__toggle' - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ) - ), - 'typography' => array( - '__experimentalSkipSerialization' => array( - 'textDecoration', - 'letterSpacing' - ), - 'fontSize' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true, - 'fontFamily' => true - ) - ), - 'shadow' => true, - 'blockVisibility' => false, - 'lock' => false - ), - 'selectors' => array( - 'typography' => array( - 'letterSpacing' => '.wp-block-accordion-heading .wp-block-accordion-heading__toggle-title', - 'textDecoration' => '.wp-block-accordion-heading .wp-block-accordion-heading__toggle-title' - ) - ), - 'attributes' => array( - 'openByDefault' => array( - 'type' => 'boolean', - 'default' => false - ), - 'title' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => '.wp-block-accordion-heading__toggle-title', - 'role' => 'content' - ), - 'level' => array( - 'type' => 'number' - ), - 'iconPosition' => array( - 'type' => 'string', - 'enum' => array( - 'left', - 'right' - ), - 'default' => 'right' - ), - 'showIcon' => array( - 'type' => 'boolean', - 'default' => true - ) - ), - 'textdomain' => 'default' - ), - 'accordion-item' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/accordion-item', - 'title' => 'Accordion Item', - 'category' => 'design', - 'description' => 'Wraps the heading and panel in one unit.', - 'parent' => array( - 'core/accordion' - ), - 'allowedBlocks' => array( - 'core/accordion-heading', - 'core/accordion-panel' - ), - 'supports' => array( - 'html' => false, - 'color' => array( - 'background' => true, - 'gradients' => true - ), - 'interactivity' => true, - 'spacing' => array( - 'margin' => array( - 'top', - 'bottom' - ), - 'blockGap' => true - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ) - ), - 'shadow' => true, - 'layout' => array( - 'allowEditing' => false - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'contentRole' => true - ), - 'attributes' => array( - 'openByDefault' => array( - 'type' => 'boolean', - 'default' => false - ) - ), - 'textdomain' => 'default', - 'style' => 'wp-block-accordion-item' - ), - 'accordion-panel' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/accordion-panel', - 'title' => 'Accordion Panel', - 'category' => 'design', - 'description' => 'Contains the hidden or revealed content beneath the heading.', - 'parent' => array( - 'core/accordion-item' - ), - 'supports' => array( - 'html' => false, - 'color' => array( - 'background' => true, - 'gradients' => true - ), - 'interactivity' => true, - 'spacing' => array( - 'padding' => true, - 'blockGap' => true, - '__experimentalDefaultControls' => array( - 'padding' => true, - 'blockGap' => true - ) - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'shadow' => true, - 'layout' => array( - 'allowEditing' => false - ), - 'blockVisibility' => false, - 'contentRole' => true, - 'allowedBlocks' => true, - 'lock' => false - ), - 'attributes' => array( - 'templateLock' => array( - 'type' => array( - 'string', - 'boolean' - ), - 'enum' => array( - 'all', - 'insert', - 'contentOnly', - false - ), - 'default' => false - ), - 'openByDefault' => array( - 'type' => 'boolean', - 'default' => false - ), - 'isSelected' => array( - 'type' => 'boolean', - 'default' => false - ) - ), - 'textdomain' => 'default', - 'style' => 'wp-block-accordion-panel' - ), - 'archives' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/archives', - 'title' => 'Archives', - 'category' => 'widgets', - 'description' => 'Display a date archive of your posts.', - 'textdomain' => 'default', - 'attributes' => array( - 'displayAsDropdown' => array( - 'type' => 'boolean', - 'default' => false - ), - 'showLabel' => array( - 'type' => 'boolean', - 'default' => true - ), - 'showPostCounts' => array( - 'type' => 'boolean', - 'default' => false - ), - 'type' => array( - 'type' => 'string', - 'default' => 'monthly' - ) - ), - 'supports' => array( - 'align' => true, - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ), - 'html' => false, - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-archives-editor' - ), - 'audio' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/audio', - 'title' => 'Audio', - 'category' => 'media', - 'description' => 'Embed a simple audio player.', - 'keywords' => array( - 'music', - 'sound', - 'podcast', - 'recording' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'blob' => array( - 'type' => 'string', - 'role' => 'local' - ), - 'src' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'audio', - 'attribute' => 'src', - 'role' => 'content' - ), - 'caption' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'figcaption', - 'role' => 'content' - ), - 'id' => array( - 'type' => 'number', - 'role' => 'content' - ), - 'autoplay' => array( - 'type' => 'boolean', - 'source' => 'attribute', - 'selector' => 'audio', - 'attribute' => 'autoplay' - ), - 'loop' => array( - 'type' => 'boolean', - 'source' => 'attribute', - 'selector' => 'audio', - 'attribute' => 'loop' - ), - 'preload' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'audio', - 'attribute' => 'preload' - ) - ), - 'supports' => array( - 'anchor' => true, - 'align' => true, - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-audio-editor', - 'style' => 'wp-block-audio' - ), - 'avatar' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/avatar', - 'title' => 'Avatar', - 'category' => 'theme', - 'description' => 'Add a user’s avatar.', - 'textdomain' => 'default', - 'attributes' => array( - 'userId' => array( - 'type' => 'number' - ), - 'size' => array( - 'type' => 'number', - 'default' => 96 - ), - 'isLink' => array( - 'type' => 'boolean', - 'default' => false - ), - 'linkTarget' => array( - 'type' => 'string', - 'default' => '_self' - ) - ), - 'usesContext' => array( - 'postType', - 'postId', - 'commentId' - ), - 'supports' => array( - 'html' => false, - 'align' => true, - 'alignWide' => false, - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - '__experimentalBorder' => array( - '__experimentalSkipSerialization' => true, - 'radius' => true, - 'width' => true, - 'color' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true - ) - ), - 'color' => array( - 'text' => false, - 'background' => false - ), - 'filter' => array( - 'duotone' => true - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'selectors' => array( - 'border' => '.wp-block-avatar img', - 'filter' => array( - 'duotone' => '.wp-block-avatar img' - ) - ), - 'editorStyle' => 'wp-block-avatar-editor', - 'style' => 'wp-block-avatar' - ), - 'block' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/block', - 'title' => 'Pattern', - 'category' => 'reusable', - 'description' => 'Reuse this design across your site.', - 'keywords' => array( - 'reusable' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'ref' => array( - 'type' => 'number' - ), - 'content' => array( - 'type' => 'object', - 'default' => array( - - ) - ) - ), - 'providesContext' => array( - 'pattern/overrides' => 'content' - ), - 'supports' => array( - 'customClassName' => false, - 'html' => false, - 'inserter' => false, - 'renaming' => false, - 'interactivity' => array( - 'clientNavigation' => true - ) - ) - ), - 'button' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/button', - 'title' => 'Button', - 'category' => 'design', - 'parent' => array( - 'core/buttons' - ), - 'description' => 'Prompt visitors to take action with a button-style link.', - 'keywords' => array( - 'link' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'tagName' => array( - 'type' => 'string', - 'enum' => array( - 'a', - 'button' - ), - 'default' => 'a' - ), - 'type' => array( - 'type' => 'string', - 'default' => 'button' - ), - 'textAlign' => array( - 'type' => 'string' - ), - 'url' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'a', - 'attribute' => 'href', - 'role' => 'content' - ), - 'title' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'a,button', - 'attribute' => 'title', - 'role' => 'content' - ), - 'text' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'a,button', - 'role' => 'content' - ), - 'linkTarget' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'a', - 'attribute' => 'target', - 'role' => 'content' - ), - 'rel' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'a', - 'attribute' => 'rel', - 'role' => 'content' - ), - 'placeholder' => array( - 'type' => 'string' - ), - 'backgroundColor' => array( - 'type' => 'string' - ), - 'textColor' => array( - 'type' => 'string' - ), - 'gradient' => array( - 'type' => 'string' - ), - 'width' => array( - 'type' => 'number' - ) - ), - 'supports' => array( - 'anchor' => true, - 'splitting' => true, - 'align' => false, - 'alignWide' => false, - 'color' => array( - '__experimentalSkipSerialization' => true, - 'gradients' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'typography' => array( - '__experimentalSkipSerialization' => array( - 'fontSize', - 'lineHeight', - 'fontFamily', - 'fontWeight', - 'fontStyle', - 'textTransform', - 'textDecoration', - 'letterSpacing' - ), - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalWritingMode' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'reusable' => false, - 'shadow' => array( - '__experimentalSkipSerialization' => true - ), - 'spacing' => array( - '__experimentalSkipSerialization' => true, - 'padding' => array( - 'horizontal', - 'vertical' - ), - '__experimentalDefaultControls' => array( - 'padding' => true - ) - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - '__experimentalSkipSerialization' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'styles' => array( - array( - 'name' => 'fill', - 'label' => 'Fill', - 'isDefault' => true - ), - array( - 'name' => 'outline', - 'label' => 'Outline' - ) - ), - 'editorStyle' => 'wp-block-button-editor', - 'style' => 'wp-block-button', - 'selectors' => array( - 'root' => '.wp-block-button .wp-block-button__link', - 'typography' => array( - 'writingMode' => '.wp-block-button' - ) - ) - ), - 'buttons' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/buttons', - 'title' => 'Buttons', - 'category' => 'design', - 'allowedBlocks' => array( - 'core/button' - ), - 'description' => 'Prompt visitors to take action with a group of button-style links.', - 'keywords' => array( - 'link' - ), - 'textdomain' => 'default', - 'supports' => array( - 'anchor' => true, - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - '__experimentalExposeControlsToChildren' => true, - 'color' => array( - 'gradients' => true, - 'text' => false, - '__experimentalDefaultControls' => array( - 'background' => true - ) - ), - 'spacing' => array( - 'blockGap' => array( - 'horizontal', - 'vertical' - ), - 'padding' => true, - 'margin' => array( - 'top', - 'bottom' - ), - '__experimentalDefaultControls' => array( - 'blockGap' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ) - ), - 'layout' => array( - 'allowSwitching' => false, - 'allowInheriting' => false, - 'default' => array( - 'type' => 'flex' - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - 'contentRole' => true - ), - 'editorStyle' => 'wp-block-buttons-editor', - 'style' => 'wp-block-buttons' - ), - 'calendar' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/calendar', - 'title' => 'Calendar', - 'category' => 'widgets', - 'description' => 'A calendar of your site’s posts.', - 'keywords' => array( - 'posts', - 'archive' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'month' => array( - 'type' => 'integer' - ), - 'year' => array( - 'type' => 'integer' - ) - ), - 'supports' => array( - 'align' => true, - 'html' => false, - 'color' => array( - 'link' => true, - '__experimentalSkipSerialization' => array( - 'text', - 'background' - ), - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ), - '__experimentalSelector' => 'table, th' - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'style' => 'wp-block-calendar' - ), - 'categories' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/categories', - 'title' => 'Terms List', - 'category' => 'widgets', - 'description' => 'Display a list of all terms of a given taxonomy.', - 'keywords' => array( - 'categories' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'taxonomy' => array( - 'type' => 'string', - 'default' => 'category' - ), - 'displayAsDropdown' => array( - 'type' => 'boolean', - 'default' => false - ), - 'showHierarchy' => array( - 'type' => 'boolean', - 'default' => false - ), - 'showPostCounts' => array( - 'type' => 'boolean', - 'default' => false - ), - 'showOnlyTopLevel' => array( - 'type' => 'boolean', - 'default' => false - ), - 'showEmpty' => array( - 'type' => 'boolean', - 'default' => false - ), - 'label' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'showLabel' => array( - 'type' => 'boolean', - 'default' => true - ) - ), - 'usesContext' => array( - 'enhancedPagination' - ), - 'supports' => array( - 'align' => true, - 'html' => false, - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'editorStyle' => 'wp-block-categories-editor', - 'style' => 'wp-block-categories' - ), - 'code' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/code', - 'title' => 'Code', - 'category' => 'text', - 'description' => 'Display code snippets that respect your spacing and tabs.', - 'textdomain' => 'default', - 'attributes' => array( - 'content' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'code', - '__unstablePreserveWhiteSpace' => true, - 'role' => 'content' - ) - ), - 'supports' => array( - 'align' => array( - 'wide' - ), - 'anchor' => true, - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'spacing' => array( - 'margin' => array( - 'top', - 'bottom' - ), - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'width' => true, - 'color' => true - ) - ), - 'color' => array( - 'text' => true, - 'background' => true, - 'gradients' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'style' => 'wp-block-code' - ), - 'column' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/column', - 'title' => 'Column', - 'category' => 'design', - 'parent' => array( - 'core/columns' - ), - 'description' => 'A single column within a columns block.', - 'textdomain' => 'default', - 'attributes' => array( - 'verticalAlignment' => array( - 'type' => 'string' - ), - 'width' => array( - 'type' => 'string' - ), - 'templateLock' => array( - 'type' => array( - 'string', - 'boolean' - ), - 'enum' => array( - 'all', - 'insert', - 'contentOnly', - false - ) - ) - ), - 'supports' => array( - '__experimentalOnEnter' => true, - 'anchor' => true, - 'reusable' => false, - 'html' => false, - 'color' => array( - 'gradients' => true, - 'heading' => true, - 'button' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'shadow' => true, - 'spacing' => array( - 'blockGap' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'padding' => true, - 'blockGap' => true - ) - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'layout' => true, - 'interactivity' => array( - 'clientNavigation' => true - ), - 'allowedBlocks' => true - ) - ), - 'columns' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/columns', - 'title' => 'Columns', - 'category' => 'design', - 'allowedBlocks' => array( - 'core/column' - ), - 'description' => 'Display content in multiple columns, with blocks added to each column.', - 'textdomain' => 'default', - 'attributes' => array( - 'verticalAlignment' => array( - 'type' => 'string' - ), - 'isStackedOnMobile' => array( - 'type' => 'boolean', - 'default' => true - ), - 'templateLock' => array( - 'type' => array( - 'string', - 'boolean' - ), - 'enum' => array( - 'all', - 'insert', - 'contentOnly', - false - ) - ) - ), - 'supports' => array( - 'anchor' => true, - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - 'color' => array( - 'gradients' => true, - 'link' => true, - 'heading' => true, - 'button' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'spacing' => array( - 'blockGap' => array( - '__experimentalDefault' => '2em', - 'sides' => array( - 'horizontal', - 'vertical' - ) - ), - 'margin' => array( - 'top', - 'bottom' - ), - 'padding' => true, - '__experimentalDefaultControls' => array( - 'padding' => true, - 'blockGap' => true - ) - ), - 'layout' => array( - 'allowSwitching' => false, - 'allowInheriting' => false, - 'allowEditing' => false, - 'default' => array( - 'type' => 'flex', - 'flexWrap' => 'nowrap' - ) - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - 'shadow' => true - ), - 'editorStyle' => 'wp-block-columns-editor', - 'style' => 'wp-block-columns' - ), - 'comment-author-name' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/comment-author-name', - 'title' => 'Comment Author Name', - 'category' => 'theme', - 'ancestor' => array( - 'core/comment-template' - ), - 'description' => 'Displays the name of the author of the comment.', - 'textdomain' => 'default', - 'attributes' => array( - 'isLink' => array( - 'type' => 'boolean', - 'default' => true - ), - 'linkTarget' => array( - 'type' => 'string', - 'default' => '_self' - ), - 'textAlign' => array( - 'type' => 'string' - ) - ), - 'usesContext' => array( - 'commentId' - ), - 'supports' => array( - 'html' => false, - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'style' => 'wp-block-comment-author-name' - ), - 'comment-content' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/comment-content', - 'title' => 'Comment Content', - 'category' => 'theme', - 'ancestor' => array( - 'core/comment-template' - ), - 'description' => 'Displays the contents of a comment.', - 'textdomain' => 'default', - 'usesContext' => array( - 'commentId' - ), - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ), - 'spacing' => array( - 'padding' => array( - 'horizontal', - 'vertical' - ), - '__experimentalDefaultControls' => array( - 'padding' => true - ) - ), - 'html' => false - ), - 'style' => 'wp-block-comment-content' - ), - 'comment-date' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/comment-date', - 'title' => 'Comment Date', - 'category' => 'theme', - 'ancestor' => array( - 'core/comment-template' - ), - 'description' => 'Displays the date on which the comment was posted.', - 'textdomain' => 'default', - 'attributes' => array( - 'format' => array( - 'type' => 'string' - ), - 'isLink' => array( - 'type' => 'boolean', - 'default' => true - ) - ), - 'usesContext' => array( - 'commentId' - ), - 'supports' => array( - 'html' => false, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'style' => 'wp-block-comment-date' - ), - 'comment-edit-link' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/comment-edit-link', - 'title' => 'Comment Edit Link', - 'category' => 'theme', - 'ancestor' => array( - 'core/comment-template' - ), - 'description' => 'Displays a link to edit the comment in the WordPress Dashboard. This link is only visible to users with the edit comment capability.', - 'textdomain' => 'default', - 'usesContext' => array( - 'commentId' - ), - 'attributes' => array( - 'linkTarget' => array( - 'type' => 'string', - 'default' => '_self' - ), - 'textAlign' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - 'html' => false, - 'color' => array( - 'link' => true, - 'gradients' => true, - 'text' => false, - '__experimentalDefaultControls' => array( - 'background' => true, - 'link' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ), - 'style' => 'wp-block-comment-edit-link' - ), - 'comment-reply-link' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/comment-reply-link', - 'title' => 'Comment Reply Link', - 'category' => 'theme', - 'ancestor' => array( - 'core/comment-template' - ), - 'description' => 'Displays a link to reply to a comment.', - 'textdomain' => 'default', - 'usesContext' => array( - 'commentId' - ), - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - 'color' => array( - 'gradients' => true, - 'link' => true, - 'text' => false, - '__experimentalDefaultControls' => array( - 'background' => true, - 'link' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ), - 'html' => false - ), - 'style' => 'wp-block-comment-reply-link' - ), - 'comment-template' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/comment-template', - 'title' => 'Comment Template', - 'category' => 'design', - 'parent' => array( - 'core/comments' - ), - 'description' => 'Contains the block elements used to display a comment, like the title, date, author, avatar and more.', - 'textdomain' => 'default', - 'usesContext' => array( - 'postId' - ), - 'supports' => array( - 'align' => true, - 'html' => false, - 'reusable' => false, - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'style' => 'wp-block-comment-template' - ), - 'comments' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/comments', - 'title' => 'Comments', - 'category' => 'theme', - 'description' => 'An advanced block that allows displaying post comments using different visual configurations.', - 'textdomain' => 'default', - 'attributes' => array( - 'tagName' => array( - 'type' => 'string', - 'default' => 'div' - ), - 'legacy' => array( - 'type' => 'boolean', - 'default' => false - ) - ), - 'supports' => array( - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - 'color' => array( - 'gradients' => true, - 'heading' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'editorStyle' => 'wp-block-comments-editor', - 'usesContext' => array( - 'postId', - 'postType' - ) - ), - 'comments-pagination' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/comments-pagination', - 'title' => 'Comments Pagination', - 'category' => 'theme', - 'parent' => array( - 'core/comments' - ), - 'allowedBlocks' => array( - 'core/comments-pagination-previous', - 'core/comments-pagination-numbers', - 'core/comments-pagination-next' - ), - 'description' => 'Displays a paginated navigation to next/previous set of comments, when applicable.', - 'textdomain' => 'default', - 'attributes' => array( - 'paginationArrow' => array( - 'type' => 'string', - 'default' => 'none' - ) - ), - 'example' => array( - 'attributes' => array( - 'paginationArrow' => 'none' - ) - ), - 'providesContext' => array( - 'comments/paginationArrow' => 'paginationArrow' - ), - 'supports' => array( - 'align' => true, - 'reusable' => false, - 'html' => false, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'layout' => array( - 'allowSwitching' => false, - 'allowInheriting' => false, - 'default' => array( - 'type' => 'flex' - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-comments-pagination-editor', - 'style' => 'wp-block-comments-pagination' - ), - 'comments-pagination-next' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/comments-pagination-next', - 'title' => 'Comments Next Page', - 'category' => 'theme', - 'parent' => array( - 'core/comments-pagination' - ), - 'description' => 'Displays the next comment\'s page link.', - 'textdomain' => 'default', - 'attributes' => array( - 'label' => array( - 'type' => 'string' - ) - ), - 'usesContext' => array( - 'postId', - 'comments/paginationArrow' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'color' => array( - 'gradients' => true, - 'text' => false, - '__experimentalDefaultControls' => array( - 'background' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ) - ), - 'comments-pagination-numbers' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/comments-pagination-numbers', - 'title' => 'Comments Page Numbers', - 'category' => 'theme', - 'parent' => array( - 'core/comments-pagination' - ), - 'description' => 'Displays a list of page numbers for comments pagination.', - 'textdomain' => 'default', - 'usesContext' => array( - 'postId' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'color' => array( - 'gradients' => true, - 'text' => false, - '__experimentalDefaultControls' => array( - 'background' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ) - ), - 'comments-pagination-previous' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/comments-pagination-previous', - 'title' => 'Comments Previous Page', - 'category' => 'theme', - 'parent' => array( - 'core/comments-pagination' - ), - 'description' => 'Displays the previous comment\'s page link.', - 'textdomain' => 'default', - 'attributes' => array( - 'label' => array( - 'type' => 'string' - ) - ), - 'usesContext' => array( - 'postId', - 'comments/paginationArrow' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'color' => array( - 'gradients' => true, - 'text' => false, - '__experimentalDefaultControls' => array( - 'background' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ) - ), - 'comments-title' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/comments-title', - 'title' => 'Comments Title', - 'category' => 'theme', - 'ancestor' => array( - 'core/comments' - ), - 'description' => 'Displays a title with the number of comments.', - 'textdomain' => 'default', - 'usesContext' => array( - 'postId', - 'postType' - ), - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ), - 'showPostTitle' => array( - 'type' => 'boolean', - 'default' => true - ), - 'showCommentsCount' => array( - 'type' => 'boolean', - 'default' => true - ), - 'level' => array( - 'type' => 'number', - 'default' => 2 - ), - 'levelOptions' => array( - 'type' => 'array' - ) - ), - 'supports' => array( - 'anchor' => false, - 'align' => true, - 'html' => false, - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ), - 'color' => array( - 'gradients' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true, - '__experimentalFontFamily' => true, - '__experimentalFontStyle' => true, - '__experimentalFontWeight' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ) - ), - 'cover' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/cover', - 'title' => 'Cover', - 'category' => 'media', - 'description' => 'Add an image or video with a text overlay.', - 'textdomain' => 'default', - 'attributes' => array( - 'url' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'useFeaturedImage' => array( - 'type' => 'boolean', - 'default' => false - ), - 'id' => array( - 'type' => 'number' - ), - 'alt' => array( - 'type' => 'string', - 'default' => '' - ), - 'hasParallax' => array( - 'type' => 'boolean', - 'default' => false - ), - 'isRepeated' => array( - 'type' => 'boolean', - 'default' => false - ), - 'dimRatio' => array( - 'type' => 'number', - 'default' => 100 - ), - 'overlayColor' => array( - 'type' => 'string' - ), - 'customOverlayColor' => array( - 'type' => 'string' - ), - 'isUserOverlayColor' => array( - 'type' => 'boolean' - ), - 'backgroundType' => array( - 'type' => 'string', - 'default' => 'image' - ), - 'focalPoint' => array( - 'type' => 'object' - ), - 'minHeight' => array( - 'type' => 'number' - ), - 'minHeightUnit' => array( - 'type' => 'string' - ), - 'gradient' => array( - 'type' => 'string' - ), - 'customGradient' => array( - 'type' => 'string' - ), - 'contentPosition' => array( - 'type' => 'string' - ), - 'isDark' => array( - 'type' => 'boolean', - 'default' => true - ), - 'templateLock' => array( - 'type' => array( - 'string', - 'boolean' - ), - 'enum' => array( - 'all', - 'insert', - 'contentOnly', - false - ) - ), - 'tagName' => array( - 'type' => 'string', - 'default' => 'div' - ), - 'sizeSlug' => array( - 'type' => 'string' - ), - 'poster' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'video', - 'attribute' => 'poster' - ) - ), - 'usesContext' => array( - 'postId', - 'postType' - ), - 'supports' => array( - 'anchor' => true, - 'align' => true, - 'html' => false, - 'shadow' => true, - 'spacing' => array( - 'padding' => true, - 'margin' => array( - 'top', - 'bottom' - ), - 'blockGap' => true, - '__experimentalDefaultControls' => array( - 'padding' => true, - 'blockGap' => true - ) - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ) - ), - 'color' => array( - 'heading' => true, - 'text' => true, - 'background' => false, - '__experimentalSkipSerialization' => array( - 'gradients' - ), - 'enableContrastChecker' => false - ), - 'dimensions' => array( - 'aspectRatio' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'layout' => array( - 'allowJustification' => false - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - 'filter' => array( - 'duotone' => true - ), - 'allowedBlocks' => true - ), - 'selectors' => array( - 'filter' => array( - 'duotone' => '.wp-block-cover > .wp-block-cover__image-background, .wp-block-cover > .wp-block-cover__video-background' - ) - ), - 'editorStyle' => 'wp-block-cover-editor', - 'style' => 'wp-block-cover' - ), - 'details' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/details', - 'title' => 'Details', - 'category' => 'text', - 'description' => 'Hide and show additional content.', - 'keywords' => array( - 'summary', - 'toggle', - 'disclosure' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'showContent' => array( - 'type' => 'boolean', - 'default' => false - ), - 'summary' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'summary', - 'role' => 'content' - ), - 'name' => array( - 'type' => 'string', - 'source' => 'attribute', - 'attribute' => 'name', - 'selector' => '.wp-block-details' - ), - 'placeholder' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - '__experimentalOnEnter' => true, - 'align' => array( - 'wide', - 'full' - ), - 'anchor' => true, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - '__experimentalBorder' => array( - 'color' => true, - 'width' => true, - 'style' => true - ), - 'html' => false, - 'spacing' => array( - 'margin' => true, - 'padding' => true, - 'blockGap' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'layout' => array( - 'allowEditing' => false - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - 'allowedBlocks' => true - ), - 'editorStyle' => 'wp-block-details-editor', - 'style' => 'wp-block-details' - ), - 'embed' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/embed', - 'title' => 'Embed', - 'category' => 'embed', - 'description' => 'Add a block that displays content pulled from other sites, like Twitter or YouTube.', - 'textdomain' => 'default', - 'attributes' => array( - 'url' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'caption' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'figcaption', - 'role' => 'content' - ), - 'type' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'providerNameSlug' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'allowResponsive' => array( - 'type' => 'boolean', - 'default' => true - ), - 'responsive' => array( - 'type' => 'boolean', - 'default' => false, - 'role' => 'content' - ), - 'previewable' => array( - 'type' => 'boolean', - 'default' => true, - 'role' => 'content' - ) - ), - 'supports' => array( - 'align' => true, - 'spacing' => array( - 'margin' => true - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-embed-editor', - 'style' => 'wp-block-embed' - ), - 'file' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/file', - 'title' => 'File', - 'category' => 'media', - 'description' => 'Add a link to a downloadable file.', - 'keywords' => array( - 'document', - 'pdf', - 'download' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'id' => array( - 'type' => 'number' - ), - 'blob' => array( - 'type' => 'string', - 'role' => 'local' - ), - 'href' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'fileId' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'a:not([download])', - 'attribute' => 'id' - ), - 'fileName' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'a:not([download])', - 'role' => 'content' - ), - 'textLinkHref' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'a:not([download])', - 'attribute' => 'href', - 'role' => 'content' - ), - 'textLinkTarget' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'a:not([download])', - 'attribute' => 'target' - ), - 'showDownloadButton' => array( - 'type' => 'boolean', - 'default' => true - ), - 'downloadButtonText' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'a[download]', - 'role' => 'content' - ), - 'displayPreview' => array( - 'type' => 'boolean' - ), - 'previewHeight' => array( - 'type' => 'number', - 'default' => 600 - ) - ), - 'supports' => array( - 'anchor' => true, - 'align' => true, - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'color' => array( - 'gradients' => true, - 'link' => true, - 'text' => false, - '__experimentalDefaultControls' => array( - 'background' => true, - 'link' => true - ) - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ), - 'interactivity' => true - ), - 'editorStyle' => 'wp-block-file-editor', - 'style' => 'wp-block-file' - ), - 'footnotes' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/footnotes', - 'title' => 'Footnotes', - 'category' => 'text', - 'description' => 'Display footnotes added to the page.', - 'keywords' => array( - 'references' - ), - 'textdomain' => 'default', - 'usesContext' => array( - 'postId', - 'postType' - ), - 'supports' => array( - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => false, - 'color' => false, - 'width' => false, - 'style' => false - ) - ), - 'color' => array( - 'background' => true, - 'link' => true, - 'text' => true, - '__experimentalDefaultControls' => array( - 'link' => true, - 'text' => true - ) - ), - 'html' => false, - 'multiple' => false, - 'reusable' => false, - 'inserter' => false, - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalTextDecoration' => true, - '__experimentalFontStyle' => true, - '__experimentalFontWeight' => true, - '__experimentalLetterSpacing' => true, - '__experimentalTextTransform' => true, - '__experimentalWritingMode' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'style' => 'wp-block-footnotes' - ), - 'freeform' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/freeform', - 'title' => 'Classic', - 'category' => 'text', - 'description' => 'Use the classic WordPress editor.', - 'textdomain' => 'default', - 'attributes' => array( - 'content' => array( - 'type' => 'string', - 'source' => 'raw' - ) - ), - 'supports' => array( - 'html' => false, - 'className' => false, - 'customClassName' => false, - 'lock' => false, - 'reusable' => false, - 'renaming' => false, - 'blockVisibility' => false - ), - 'editorStyle' => 'wp-block-freeform-editor' - ), - 'gallery' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/gallery', - 'title' => 'Gallery', - 'category' => 'media', - 'allowedBlocks' => array( - 'core/image' - ), - 'description' => 'Display multiple images in a rich gallery.', - 'keywords' => array( - 'images', - 'photos' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'images' => array( - 'type' => 'array', - 'default' => array( - - ), - 'source' => 'query', - 'selector' => '.blocks-gallery-item', - 'query' => array( - 'url' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'img', - 'attribute' => 'src' - ), - 'fullUrl' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'img', - 'attribute' => 'data-full-url' - ), - 'link' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'img', - 'attribute' => 'data-link' - ), - 'alt' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'img', - 'attribute' => 'alt', - 'default' => '' - ), - 'id' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'img', - 'attribute' => 'data-id' - ), - 'caption' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => '.blocks-gallery-item__caption' - ) - ) - ), - 'ids' => array( - 'type' => 'array', - 'items' => array( - 'type' => 'number' - ), - 'default' => array( - - ) - ), - 'shortCodeTransforms' => array( - 'type' => 'array', - 'items' => array( - 'type' => 'object' - ), - 'default' => array( - - ) - ), - 'columns' => array( - 'type' => 'number', - 'minimum' => 1, - 'maximum' => 8 - ), - 'caption' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => '.blocks-gallery-caption', - 'role' => 'content' - ), - 'imageCrop' => array( - 'type' => 'boolean', - 'default' => true - ), - 'randomOrder' => array( - 'type' => 'boolean', - 'default' => false - ), - 'fixedHeight' => array( - 'type' => 'boolean', - 'default' => true - ), - 'linkTarget' => array( - 'type' => 'string' - ), - 'linkTo' => array( - 'type' => 'string' - ), - 'sizeSlug' => array( - 'type' => 'string', - 'default' => 'large' - ), - 'allowResize' => array( - 'type' => 'boolean', - 'default' => false - ), - 'aspectRatio' => array( - 'type' => 'string', - 'default' => 'auto' - ) - ), - 'providesContext' => array( - 'allowResize' => 'allowResize', - 'imageCrop' => 'imageCrop', - 'fixedHeight' => 'fixedHeight' - ), - 'supports' => array( - 'anchor' => true, - 'align' => true, - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true - ) - ), - 'html' => false, - 'units' => array( - 'px', - 'em', - 'rem', - 'vh', - 'vw' - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - 'blockGap' => array( - 'horizontal', - 'vertical' - ), - '__experimentalSkipSerialization' => array( - 'blockGap' - ), - '__experimentalDefaultControls' => array( - 'blockGap' => true, - 'margin' => false, - 'padding' => false - ) - ), - 'color' => array( - 'text' => false, - 'background' => true, - 'gradients' => true - ), - 'layout' => array( - 'allowSwitching' => false, - 'allowInheriting' => false, - 'allowEditing' => false, - 'default' => array( - 'type' => 'flex' - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-gallery-editor', - 'style' => 'wp-block-gallery' - ), - 'group' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/group', - 'title' => 'Group', - 'category' => 'design', - 'description' => 'Gather blocks in a layout container.', - 'keywords' => array( - 'container', - 'wrapper', - 'row', - 'section' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'tagName' => array( - 'type' => 'string', - 'default' => 'div' - ), - 'templateLock' => array( - 'type' => array( - 'string', - 'boolean' - ), - 'enum' => array( - 'all', - 'insert', - 'contentOnly', - false - ) - ) - ), - 'supports' => array( - '__experimentalOnEnter' => true, - '__experimentalOnMerge' => true, - '__experimentalSettings' => true, - 'align' => array( - 'wide', - 'full' - ), - 'anchor' => true, - 'ariaLabel' => true, - 'html' => false, - 'background' => array( - 'backgroundImage' => true, - 'backgroundSize' => true, - '__experimentalDefaultControls' => array( - 'backgroundImage' => true - ) - ), - 'color' => array( - 'gradients' => true, - 'heading' => true, - 'button' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'shadow' => true, - 'spacing' => array( - 'margin' => array( - 'top', - 'bottom' - ), - 'padding' => true, - 'blockGap' => true, - '__experimentalDefaultControls' => array( - 'padding' => true, - 'blockGap' => true - ) - ), - 'dimensions' => array( - 'minHeight' => true - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ) - ), - 'position' => array( - 'sticky' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'layout' => array( - 'allowSizingOnChildren' => true - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - 'allowedBlocks' => true - ), - 'editorStyle' => 'wp-block-group-editor', - 'style' => 'wp-block-group' - ), - 'heading' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/heading', - 'title' => 'Heading', - 'category' => 'text', - 'description' => 'Introduce new sections and organize content to help visitors (and search engines) understand the structure of your content.', - 'keywords' => array( - 'title', - 'subtitle' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ), - 'content' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'h1,h2,h3,h4,h5,h6', - 'role' => 'content' - ), - 'level' => array( - 'type' => 'number', - 'default' => 2 - ), - 'levelOptions' => array( - 'type' => 'array' - ), - 'placeholder' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - 'align' => array( - 'wide', - 'full' - ), - 'anchor' => true, - 'className' => true, - 'splitting' => true, - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ), - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontStyle' => true, - '__experimentalFontWeight' => true, - '__experimentalLetterSpacing' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalWritingMode' => true, - 'fitText' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__unstablePasteTextInline' => true, - '__experimentalSlashInserter' => true, - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-heading-editor', - 'style' => 'wp-block-heading' - ), - 'home-link' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/home-link', - 'category' => 'design', - 'parent' => array( - 'core/navigation' - ), - 'title' => 'Home Link', - 'description' => 'Create a link that always points to the homepage of the site. Usually not necessary if there is already a site title link present in the header.', - 'textdomain' => 'default', - 'attributes' => array( - 'label' => array( - 'type' => 'string', - 'role' => 'content' - ) - ), - 'usesContext' => array( - 'textColor', - 'customTextColor', - 'backgroundColor', - 'customBackgroundColor', - 'fontSize', - 'customFontSize', - 'style' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-home-link-editor', - 'style' => 'wp-block-home-link' - ), - 'html' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/html', - 'title' => 'Custom HTML', - 'category' => 'widgets', - 'description' => 'Add custom HTML code and preview it as you edit.', - 'keywords' => array( - 'embed' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'content' => array( - 'type' => 'string', - 'source' => 'raw', - 'role' => 'content' - ) - ), - 'supports' => array( - 'customClassName' => false, - 'className' => false, - 'html' => false, - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-html-editor' - ), - 'image' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/image', - 'title' => 'Image', - 'category' => 'media', - 'usesContext' => array( - 'allowResize', - 'imageCrop', - 'fixedHeight', - 'postId', - 'postType', - 'queryId' - ), - 'description' => 'Insert an image to make a visual statement.', - 'keywords' => array( - 'img', - 'photo', - 'picture' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'blob' => array( - 'type' => 'string', - 'role' => 'local' - ), - 'url' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'img', - 'attribute' => 'src', - 'role' => 'content' - ), - 'alt' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'img', - 'attribute' => 'alt', - 'default' => '', - 'role' => 'content' - ), - 'caption' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'figcaption', - 'role' => 'content' - ), - 'lightbox' => array( - 'type' => 'object', - 'enabled' => array( - 'type' => 'boolean' - ) - ), - 'title' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'img', - 'attribute' => 'title', - 'role' => 'content' - ), - 'href' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'figure > a', - 'attribute' => 'href', - 'role' => 'content' - ), - 'rel' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'figure > a', - 'attribute' => 'rel' - ), - 'linkClass' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'figure > a', - 'attribute' => 'class' - ), - 'id' => array( - 'type' => 'number', - 'role' => 'content' - ), - 'width' => array( - 'type' => 'string' - ), - 'height' => array( - 'type' => 'string' - ), - 'aspectRatio' => array( - 'type' => 'string' - ), - 'scale' => array( - 'type' => 'string' - ), - 'sizeSlug' => array( - 'type' => 'string' - ), - 'linkDestination' => array( - 'type' => 'string' - ), - 'linkTarget' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'figure > a', - 'attribute' => 'target' - ) - ), - 'supports' => array( - 'interactivity' => true, - 'align' => array( - 'left', - 'center', - 'right', - 'wide', - 'full' - ), - 'anchor' => true, - 'color' => array( - 'text' => false, - 'background' => false - ), - 'filter' => array( - 'duotone' => true - ), - 'spacing' => array( - 'margin' => true - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'width' => true, - '__experimentalSkipSerialization' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'width' => true - ) - ), - 'shadow' => array( - '__experimentalSkipSerialization' => true - ) - ), - 'selectors' => array( - 'border' => '.wp-block-image img, .wp-block-image .wp-block-image__crop-area, .wp-block-image .components-placeholder', - 'shadow' => '.wp-block-image img, .wp-block-image .wp-block-image__crop-area, .wp-block-image .components-placeholder', - 'filter' => array( - 'duotone' => '.wp-block-image img, .wp-block-image .components-placeholder' - ) - ), - 'styles' => array( - array( - 'name' => 'default', - 'label' => 'Default', - 'isDefault' => true - ), - array( - 'name' => 'rounded', - 'label' => 'Rounded' - ) - ), - 'editorStyle' => 'wp-block-image-editor', - 'style' => 'wp-block-image' - ), - 'latest-comments' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/latest-comments', - 'title' => 'Latest Comments', - 'category' => 'widgets', - 'description' => 'Display a list of your most recent comments.', - 'keywords' => array( - 'recent comments' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'commentsToShow' => array( - 'type' => 'number', - 'default' => 5, - 'minimum' => 1, - 'maximum' => 100 - ), - 'displayAvatar' => array( - 'type' => 'boolean', - 'default' => true - ), - 'displayDate' => array( - 'type' => 'boolean', - 'default' => true - ), - 'displayExcerpt' => array( - 'type' => 'boolean', - 'default' => true - ) - ), - 'supports' => array( - 'align' => true, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'html' => false, - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-latest-comments-editor', - 'style' => 'wp-block-latest-comments' - ), - 'latest-posts' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/latest-posts', - 'title' => 'Latest Posts', - 'category' => 'widgets', - 'description' => 'Display a list of your most recent posts.', - 'keywords' => array( - 'recent posts' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'categories' => array( - 'type' => 'array', - 'items' => array( - 'type' => 'object' - ) - ), - 'selectedAuthor' => array( - 'type' => 'number' - ), - 'postsToShow' => array( - 'type' => 'number', - 'default' => 5 - ), - 'displayPostContent' => array( - 'type' => 'boolean', - 'default' => false - ), - 'displayPostContentRadio' => array( - 'type' => 'string', - 'default' => 'excerpt' - ), - 'excerptLength' => array( - 'type' => 'number', - 'default' => 55 - ), - 'displayAuthor' => array( - 'type' => 'boolean', - 'default' => false - ), - 'displayPostDate' => array( - 'type' => 'boolean', - 'default' => false - ), - 'postLayout' => array( - 'type' => 'string', - 'default' => 'list' - ), - 'columns' => array( - 'type' => 'number', - 'default' => 3 - ), - 'order' => array( - 'type' => 'string', - 'default' => 'desc' - ), - 'orderBy' => array( - 'type' => 'string', - 'default' => 'date' - ), - 'displayFeaturedImage' => array( - 'type' => 'boolean', - 'default' => false - ), - 'featuredImageAlign' => array( - 'type' => 'string', - 'enum' => array( - 'left', - 'center', - 'right' - ) - ), - 'featuredImageSizeSlug' => array( - 'type' => 'string', - 'default' => 'thumbnail' - ), - 'featuredImageSizeWidth' => array( - 'type' => 'number', - 'default' => null - ), - 'featuredImageSizeHeight' => array( - 'type' => 'number', - 'default' => null - ), - 'addLinkToFeaturedImage' => array( - 'type' => 'boolean', - 'default' => false - ) - ), - 'supports' => array( - 'align' => true, - 'html' => false, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-latest-posts-editor', - 'style' => 'wp-block-latest-posts' - ), - 'legacy-widget' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/legacy-widget', - 'title' => 'Legacy Widget', - 'category' => 'widgets', - 'description' => 'Display a legacy widget.', - 'textdomain' => 'default', - 'attributes' => array( - 'id' => array( - 'type' => 'string', - 'default' => null - ), - 'idBase' => array( - 'type' => 'string', - 'default' => null - ), - 'instance' => array( - 'type' => 'object', - 'default' => null - ) - ), - 'supports' => array( - 'html' => false, - 'customClassName' => false, - 'reusable' => false - ), - 'editorStyle' => 'wp-block-legacy-widget-editor' - ), - 'list' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/list', - 'title' => 'List', - 'category' => 'text', - 'allowedBlocks' => array( - 'core/list-item' - ), - 'description' => 'An organized collection of items displayed in a specific order.', - 'keywords' => array( - 'bullet list', - 'ordered list', - 'numbered list' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'ordered' => array( - 'type' => 'boolean', - 'default' => false, - 'role' => 'content' - ), - 'values' => array( - 'type' => 'string', - 'source' => 'html', - 'selector' => 'ol,ul', - 'multiline' => 'li', - 'default' => '', - 'role' => 'content' - ), - 'type' => array( - 'type' => 'string' - ), - 'start' => array( - 'type' => 'number' - ), - 'reversed' => array( - 'type' => 'boolean' - ), - 'placeholder' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - 'anchor' => true, - 'html' => false, - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - '__unstablePasteTextInline' => true, - '__experimentalOnMerge' => true, - '__experimentalSlashInserter' => true, - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'selectors' => array( - 'border' => '.wp-block-list:not(.wp-block-list .wp-block-list)' - ), - 'editorStyle' => 'wp-block-list-editor', - 'style' => 'wp-block-list' - ), - 'list-item' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/list-item', - 'title' => 'List Item', - 'category' => 'text', - 'parent' => array( - 'core/list' - ), - 'allowedBlocks' => array( - 'core/list' - ), - 'description' => 'An individual item within a list.', - 'textdomain' => 'default', - 'attributes' => array( - 'placeholder' => array( - 'type' => 'string' - ), - 'content' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'li', - 'role' => 'content' - ) - ), - 'supports' => array( - 'anchor' => true, - 'className' => false, - 'splitting' => true, - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ), - 'color' => array( - 'gradients' => true, - 'link' => true, - 'background' => true, - '__experimentalDefaultControls' => array( - 'text' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'selectors' => array( - 'root' => '.wp-block-list > li', - 'border' => '.wp-block-list:not(.wp-block-list .wp-block-list) > li' - ) - ), - 'loginout' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/loginout', - 'title' => 'Login/out', - 'category' => 'theme', - 'description' => 'Show login & logout links.', - 'keywords' => array( - 'login', - 'logout', - 'form' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'displayLoginAsForm' => array( - 'type' => 'boolean', - 'default' => false - ), - 'redirectToCurrent' => array( - 'type' => 'boolean', - 'default' => true - ) - ), - 'example' => array( - 'viewportWidth' => 350 - ), - 'supports' => array( - 'className' => true, - 'color' => array( - 'background' => true, - 'text' => false, - 'gradients' => true, - 'link' => true - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'style' => 'wp-block-loginout' - ), - 'math' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/math', - 'title' => 'Math', - 'category' => 'text', - 'description' => 'Display mathematical notation using LaTeX.', - 'keywords' => array( - 'equation', - 'formula', - 'latex', - 'mathematics' - ), - 'textdomain' => 'default', - 'supports' => array( - 'html' => false - ), - 'attributes' => array( - 'latex' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'mathML' => array( - 'type' => 'string', - 'source' => 'html', - 'selector' => 'math' - ) - ) - ), - 'media-text' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/media-text', - 'title' => 'Media & Text', - 'category' => 'media', - 'description' => 'Set media and words side-by-side for a richer layout.', - 'keywords' => array( - 'image', - 'video' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'align' => array( - 'type' => 'string', - 'default' => 'none' - ), - 'mediaAlt' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'figure img', - 'attribute' => 'alt', - 'default' => '', - 'role' => 'content' - ), - 'mediaPosition' => array( - 'type' => 'string', - 'default' => 'left' - ), - 'mediaId' => array( - 'type' => 'number', - 'role' => 'content' - ), - 'mediaUrl' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'figure video,figure img', - 'attribute' => 'src', - 'role' => 'content' - ), - 'mediaLink' => array( - 'type' => 'string' - ), - 'linkDestination' => array( - 'type' => 'string' - ), - 'linkTarget' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'figure a', - 'attribute' => 'target' - ), - 'href' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'figure a', - 'attribute' => 'href', - 'role' => 'content' - ), - 'rel' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'figure a', - 'attribute' => 'rel' - ), - 'linkClass' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'figure a', - 'attribute' => 'class' - ), - 'mediaType' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'mediaWidth' => array( - 'type' => 'number', - 'default' => 50 - ), - 'mediaSizeSlug' => array( - 'type' => 'string' - ), - 'isStackedOnMobile' => array( - 'type' => 'boolean', - 'default' => true - ), - 'verticalAlignment' => array( - 'type' => 'string' - ), - 'imageFill' => array( - 'type' => 'boolean' - ), - 'focalPoint' => array( - 'type' => 'object' - ), - 'useFeaturedImage' => array( - 'type' => 'boolean', - 'default' => false - ) - ), - 'usesContext' => array( - 'postId', - 'postType' - ), - 'supports' => array( - 'anchor' => true, - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ) - ), - 'color' => array( - 'gradients' => true, - 'heading' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - 'allowedBlocks' => true - ), - 'editorStyle' => 'wp-block-media-text-editor', - 'style' => 'wp-block-media-text' - ), - 'missing' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/missing', - 'title' => 'Unsupported', - 'category' => 'text', - 'description' => 'Your site doesn’t include support for this block.', - 'textdomain' => 'default', - 'attributes' => array( - 'originalName' => array( - 'type' => 'string' - ), - 'originalUndelimitedContent' => array( - 'type' => 'string' - ), - 'originalContent' => array( - 'type' => 'string', - 'source' => 'raw' - ) - ), - 'supports' => array( - 'className' => false, - 'customClassName' => false, - 'inserter' => false, - 'html' => false, - 'lock' => false, - 'reusable' => false, - 'renaming' => false, - 'blockVisibility' => false, - 'interactivity' => array( - 'clientNavigation' => true - ) - ) - ), - 'more' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/more', - 'title' => 'More', - 'category' => 'design', - 'description' => 'Content before this block will be shown in the excerpt on your archives page.', - 'keywords' => array( - 'read more' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'customText' => array( - 'type' => 'string', - 'default' => '', - 'role' => 'content' - ), - 'noTeaser' => array( - 'type' => 'boolean', - 'default' => false - ) - ), - 'supports' => array( - 'customClassName' => false, - 'className' => false, - 'html' => false, - 'multiple' => false, - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-more-editor' - ), - 'navigation' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/navigation', - 'title' => 'Navigation', - 'category' => 'theme', - 'allowedBlocks' => array( - 'core/navigation-link', - 'core/search', - 'core/social-links', - 'core/page-list', - 'core/spacer', - 'core/home-link', - 'core/site-title', - 'core/site-logo', - 'core/navigation-submenu', - 'core/loginout', - 'core/buttons' - ), - 'description' => 'A collection of blocks that allow visitors to get around your site.', - 'keywords' => array( - 'menu', - 'navigation', - 'links' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'ref' => array( - 'type' => 'number' - ), - 'textColor' => array( - 'type' => 'string' - ), - 'customTextColor' => array( - 'type' => 'string' - ), - 'rgbTextColor' => array( - 'type' => 'string' - ), - 'backgroundColor' => array( - 'type' => 'string' - ), - 'customBackgroundColor' => array( - 'type' => 'string' - ), - 'rgbBackgroundColor' => array( - 'type' => 'string' - ), - 'showSubmenuIcon' => array( - 'type' => 'boolean', - 'default' => true - ), - 'openSubmenusOnClick' => array( - 'type' => 'boolean', - 'default' => false - ), - 'overlayMenu' => array( - 'type' => 'string', - 'default' => 'mobile' - ), - 'icon' => array( - 'type' => 'string', - 'default' => 'handle' - ), - 'hasIcon' => array( - 'type' => 'boolean', - 'default' => true - ), - '__unstableLocation' => array( - 'type' => 'string' - ), - 'overlayBackgroundColor' => array( - 'type' => 'string' - ), - 'customOverlayBackgroundColor' => array( - 'type' => 'string' - ), - 'overlayTextColor' => array( - 'type' => 'string' - ), - 'customOverlayTextColor' => array( - 'type' => 'string' - ), - 'maxNestingLevel' => array( - 'type' => 'number', - 'default' => 5 - ), - 'templateLock' => array( - 'type' => array( - 'string', - 'boolean' - ), - 'enum' => array( - 'all', - 'insert', - 'contentOnly', - false - ) - ) - ), - 'providesContext' => array( - 'textColor' => 'textColor', - 'customTextColor' => 'customTextColor', - 'backgroundColor' => 'backgroundColor', - 'customBackgroundColor' => 'customBackgroundColor', - 'overlayTextColor' => 'overlayTextColor', - 'customOverlayTextColor' => 'customOverlayTextColor', - 'overlayBackgroundColor' => 'overlayBackgroundColor', - 'customOverlayBackgroundColor' => 'customOverlayBackgroundColor', - 'fontSize' => 'fontSize', - 'customFontSize' => 'customFontSize', - 'showSubmenuIcon' => 'showSubmenuIcon', - 'openSubmenusOnClick' => 'openSubmenusOnClick', - 'style' => 'style', - 'maxNestingLevel' => 'maxNestingLevel' - ), - 'supports' => array( - 'align' => array( - 'wide', - 'full' - ), - 'ariaLabel' => true, - 'html' => false, - 'inserter' => true, - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontStyle' => true, - '__experimentalFontWeight' => true, - '__experimentalTextTransform' => true, - '__experimentalFontFamily' => true, - '__experimentalLetterSpacing' => true, - '__experimentalTextDecoration' => true, - '__experimentalSkipSerialization' => array( - 'textDecoration' - ), - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'spacing' => array( - 'blockGap' => true, - 'units' => array( - 'px', - 'em', - 'rem', - 'vh', - 'vw' - ), - '__experimentalDefaultControls' => array( - 'blockGap' => true - ) - ), - 'layout' => array( - 'allowSwitching' => false, - 'allowInheriting' => false, - 'allowVerticalAlignment' => false, - 'allowSizingOnChildren' => true, - 'default' => array( - 'type' => 'flex' - ) - ), - 'interactivity' => true, - 'renaming' => false, - 'contentRole' => true - ), - 'editorStyle' => 'wp-block-navigation-editor', - 'style' => 'wp-block-navigation' - ), - 'navigation-link' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/navigation-link', - 'title' => 'Custom Link', - 'category' => 'design', - 'parent' => array( - 'core/navigation' - ), - 'allowedBlocks' => array( - 'core/navigation-link', - 'core/navigation-submenu', - 'core/page-list' - ), - 'description' => 'Add a page, link, or another item to your navigation.', - 'textdomain' => 'default', - 'attributes' => array( - 'label' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'type' => array( - 'type' => 'string' - ), - 'description' => array( - 'type' => 'string' - ), - 'rel' => array( - 'type' => 'string' - ), - 'id' => array( - 'type' => 'number' - ), - 'opensInNewTab' => array( - 'type' => 'boolean', - 'default' => false - ), - 'url' => array( - 'type' => 'string' - ), - 'title' => array( - 'type' => 'string' - ), - 'kind' => array( - 'type' => 'string' - ), - 'isTopLevelLink' => array( - 'type' => 'boolean' - ) - ), - 'usesContext' => array( - 'textColor', - 'customTextColor', - 'backgroundColor', - 'customBackgroundColor', - 'overlayTextColor', - 'customOverlayTextColor', - 'overlayBackgroundColor', - 'customOverlayBackgroundColor', - 'fontSize', - 'customFontSize', - 'showSubmenuIcon', - 'maxNestingLevel', - 'style' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - '__experimentalSlashInserter' => true, - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'renaming' => false, - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-navigation-link-editor', - 'style' => 'wp-block-navigation-link' - ), - 'navigation-submenu' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/navigation-submenu', - 'title' => 'Submenu', - 'category' => 'design', - 'parent' => array( - 'core/navigation' - ), - 'description' => 'Add a submenu to your navigation.', - 'textdomain' => 'default', - 'attributes' => array( - 'label' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'type' => array( - 'type' => 'string' - ), - 'description' => array( - 'type' => 'string' - ), - 'rel' => array( - 'type' => 'string' - ), - 'id' => array( - 'type' => 'number' - ), - 'opensInNewTab' => array( - 'type' => 'boolean', - 'default' => false - ), - 'url' => array( - 'type' => 'string' - ), - 'title' => array( - 'type' => 'string' - ), - 'kind' => array( - 'type' => 'string' - ), - 'isTopLevelItem' => array( - 'type' => 'boolean' - ) - ), - 'usesContext' => array( - 'textColor', - 'customTextColor', - 'backgroundColor', - 'customBackgroundColor', - 'overlayTextColor', - 'customOverlayTextColor', - 'overlayBackgroundColor', - 'customOverlayBackgroundColor', - 'fontSize', - 'customFontSize', - 'showSubmenuIcon', - 'maxNestingLevel', - 'openSubmenusOnClick', - 'style' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-navigation-submenu-editor', - 'style' => 'wp-block-navigation-submenu' - ), - 'nextpage' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/nextpage', - 'title' => 'Page Break', - 'category' => 'design', - 'description' => 'Separate your content into a multi-page experience.', - 'keywords' => array( - 'next page', - 'pagination' - ), - 'parent' => array( - 'core/post-content' - ), - 'textdomain' => 'default', - 'supports' => array( - 'customClassName' => false, - 'className' => false, - 'html' => false, - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-nextpage-editor' - ), - 'page-list' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/page-list', - 'title' => 'Page List', - 'category' => 'widgets', - 'allowedBlocks' => array( - 'core/page-list-item' - ), - 'description' => 'Display a list of all pages.', - 'keywords' => array( - 'menu', - 'navigation' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'parentPageID' => array( - 'type' => 'integer', - 'default' => 0 - ), - 'isNested' => array( - 'type' => 'boolean', - 'default' => false - ) - ), - 'usesContext' => array( - 'textColor', - 'customTextColor', - 'backgroundColor', - 'customBackgroundColor', - 'overlayTextColor', - 'customOverlayTextColor', - 'overlayBackgroundColor', - 'customOverlayBackgroundColor', - 'fontSize', - 'customFontSize', - 'showSubmenuIcon', - 'style', - 'openSubmenusOnClick' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - 'color' => array( - 'text' => true, - 'background' => true, - 'link' => true, - 'gradients' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ), - 'spacing' => array( - 'padding' => true, - 'margin' => true, - '__experimentalDefaultControls' => array( - 'padding' => false, - 'margin' => false - ) - ), - 'contentRole' => true - ), - 'editorStyle' => 'wp-block-page-list-editor', - 'style' => 'wp-block-page-list' - ), - 'page-list-item' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/page-list-item', - 'title' => 'Page List Item', - 'category' => 'widgets', - 'parent' => array( - 'core/page-list' - ), - 'description' => 'Displays a page inside a list of all pages.', - 'keywords' => array( - 'page', - 'menu', - 'navigation' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'id' => array( - 'type' => 'number' - ), - 'label' => array( - 'type' => 'string' - ), - 'title' => array( - 'type' => 'string' - ), - 'link' => array( - 'type' => 'string' - ), - 'hasChildren' => array( - 'type' => 'boolean' - ) - ), - 'usesContext' => array( - 'textColor', - 'customTextColor', - 'backgroundColor', - 'customBackgroundColor', - 'overlayTextColor', - 'customOverlayTextColor', - 'overlayBackgroundColor', - 'customOverlayBackgroundColor', - 'fontSize', - 'customFontSize', - 'showSubmenuIcon', - 'style', - 'openSubmenusOnClick' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'lock' => false, - 'inserter' => false, - '__experimentalToolbar' => false, - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-page-list-editor', - 'style' => 'wp-block-page-list' - ), - 'paragraph' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/paragraph', - 'title' => 'Paragraph', - 'category' => 'text', - 'description' => 'Start with the basic building block of all narrative.', - 'keywords' => array( - 'text' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'align' => array( - 'type' => 'string' - ), - 'content' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'p', - 'role' => 'content' - ), - 'dropCap' => array( - 'type' => 'boolean', - 'default' => false - ), - 'placeholder' => array( - 'type' => 'string' - ), - 'direction' => array( - 'type' => 'string', - 'enum' => array( - 'ltr', - 'rtl' - ) - ) - ), - 'supports' => array( - 'splitting' => true, - 'anchor' => true, - 'className' => false, - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ), - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalTextDecoration' => true, - '__experimentalFontStyle' => true, - '__experimentalFontWeight' => true, - '__experimentalLetterSpacing' => true, - '__experimentalTextTransform' => true, - '__experimentalWritingMode' => true, - 'fitText' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__experimentalSelector' => 'p', - '__unstablePasteTextInline' => true, - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-paragraph-editor', - 'style' => 'wp-block-paragraph' - ), - 'pattern' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/pattern', - 'title' => 'Pattern Placeholder', - 'category' => 'theme', - 'description' => 'Show a block pattern.', - 'supports' => array( - 'html' => false, - 'inserter' => false, - 'renaming' => false, - 'blockVisibility' => false, - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'textdomain' => 'default', - 'attributes' => array( - 'slug' => array( - 'type' => 'string' - ) - ) - ), - 'post-author' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-author', - 'title' => 'Author', - 'category' => 'theme', - 'description' => 'Display post author details such as name, avatar, and bio.', - 'textdomain' => 'default', - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ), - 'avatarSize' => array( - 'type' => 'number', - 'default' => 48 - ), - 'showAvatar' => array( - 'type' => 'boolean', - 'default' => true - ), - 'showBio' => array( - 'type' => 'boolean' - ), - 'byline' => array( - 'type' => 'string' - ), - 'isLink' => array( - 'type' => 'boolean', - 'default' => false, - 'role' => 'content' - ), - 'linkTarget' => array( - 'type' => 'string', - 'default' => '_self', - 'role' => 'content' - ) - ), - 'usesContext' => array( - 'postType', - 'postId', - 'queryId' - ), - 'supports' => array( - 'html' => false, - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ), - 'filter' => array( - 'duotone' => true - ) - ), - 'selectors' => array( - 'filter' => array( - 'duotone' => '.wp-block-post-author .wp-block-post-author__avatar img' - ) - ), - 'editorStyle' => 'wp-block-post-author-editor', - 'style' => 'wp-block-post-author' - ), - 'post-author-biography' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-author-biography', - 'title' => 'Author Biography', - 'category' => 'theme', - 'description' => 'The author biography.', - 'textdomain' => 'default', - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ) - ), - 'usesContext' => array( - 'postType', - 'postId' - ), - 'example' => array( - 'viewportWidth' => 350 - ), - 'supports' => array( - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'style' => 'wp-block-post-author-biography' - ), - 'post-author-name' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-author-name', - 'title' => 'Author Name', - 'category' => 'theme', - 'description' => 'The author name.', - 'textdomain' => 'default', - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ), - 'isLink' => array( - 'type' => 'boolean', - 'default' => false, - 'role' => 'content' - ), - 'linkTarget' => array( - 'type' => 'string', - 'default' => '_self', - 'role' => 'content' - ) - ), - 'usesContext' => array( - 'postType', - 'postId' - ), - 'example' => array( - 'viewportWidth' => 350 - ), - 'supports' => array( - 'html' => false, - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'style' => 'wp-block-post-author-name' - ), - 'post-comments-count' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-comments-count', - 'title' => 'Comments Count', - 'category' => 'theme', - 'description' => 'Display a post\'s comments count.', - 'textdomain' => 'default', - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ) - ), - 'usesContext' => array( - 'postId' - ), - 'example' => array( - 'viewportWidth' => 350 - ), - 'supports' => array( - 'html' => false, - 'color' => array( - 'gradients' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'style' => 'wp-block-post-comments-count' - ), - 'post-comments-form' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-comments-form', - 'title' => 'Comments Form', - 'category' => 'theme', - 'description' => 'Display a post\'s comments form.', - 'textdomain' => 'default', - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ) - ), - 'usesContext' => array( - 'postId', - 'postType' - ), - 'supports' => array( - 'html' => false, - 'color' => array( - 'gradients' => true, - 'heading' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontStyle' => true, - '__experimentalFontWeight' => true, - '__experimentalLetterSpacing' => true, - '__experimentalTextTransform' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'editorStyle' => 'wp-block-post-comments-form-editor', - 'style' => array( - 'wp-block-post-comments-form', - 'wp-block-buttons', - 'wp-block-button' - ), - 'example' => array( - 'attributes' => array( - 'textAlign' => 'center' - ) - ) - ), - 'post-comments-link' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-comments-link', - 'title' => 'Comments Link', - 'category' => 'theme', - 'description' => 'Displays the link to the current post comments.', - 'textdomain' => 'default', - 'usesContext' => array( - 'postType', - 'postId' - ), - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ) - ), - 'example' => array( - 'viewportWidth' => 350 - ), - 'supports' => array( - 'html' => false, - 'color' => array( - 'link' => true, - 'text' => false, - '__experimentalDefaultControls' => array( - 'background' => true, - 'link' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'style' => 'wp-block-post-comments-link' - ), - 'post-content' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-content', - 'title' => 'Content', - 'category' => 'theme', - 'description' => 'Displays the contents of a post or page.', - 'textdomain' => 'default', - 'usesContext' => array( - 'postId', - 'postType', - 'queryId' - ), - 'attributes' => array( - 'tagName' => array( - 'type' => 'string', - 'default' => 'div' - ) - ), - 'example' => array( - 'viewportWidth' => 350 - ), - 'supports' => array( - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - 'layout' => true, - 'background' => array( - 'backgroundImage' => true, - 'backgroundSize' => true, - '__experimentalDefaultControls' => array( - 'backgroundImage' => true - ) - ), - 'dimensions' => array( - 'minHeight' => true - ), - 'spacing' => array( - 'blockGap' => true, - 'padding' => true, - 'margin' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'color' => array( - 'gradients' => true, - 'heading' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => false, - 'text' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'style' => 'wp-block-post-content', - 'editorStyle' => 'wp-block-post-content-editor' - ), - 'post-date' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-date', - 'title' => 'Date', - 'category' => 'theme', - 'description' => 'Display a custom date.', - 'textdomain' => 'default', - 'attributes' => array( - 'datetime' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'textAlign' => array( - 'type' => 'string' - ), - 'format' => array( - 'type' => 'string' - ), - 'isLink' => array( - 'type' => 'boolean', - 'default' => false, - 'role' => 'content' - ) - ), - 'usesContext' => array( - 'postId', - 'postType', - 'queryId' - ), - 'example' => array( - 'viewportWidth' => 350 - ), - 'supports' => array( - 'html' => false, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ) - ), - 'post-excerpt' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-excerpt', - 'title' => 'Excerpt', - 'category' => 'theme', - 'description' => 'Display the excerpt.', - 'textdomain' => 'default', - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ), - 'moreText' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'showMoreOnNewLine' => array( - 'type' => 'boolean', - 'default' => true - ), - 'excerptLength' => array( - 'type' => 'number', - 'default' => 55 - ) - ), - 'usesContext' => array( - 'postId', - 'postType', - 'queryId' - ), - 'example' => array( - 'viewportWidth' => 350 - ), - 'supports' => array( - 'html' => false, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'editorStyle' => 'wp-block-post-excerpt-editor', - 'style' => 'wp-block-post-excerpt' - ), - 'post-featured-image' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-featured-image', - 'title' => 'Featured Image', - 'category' => 'theme', - 'description' => 'Display a post\'s featured image.', - 'textdomain' => 'default', - 'attributes' => array( - 'isLink' => array( - 'type' => 'boolean', - 'default' => false, - 'role' => 'content' - ), - 'aspectRatio' => array( - 'type' => 'string' - ), - 'width' => array( - 'type' => 'string' - ), - 'height' => array( - 'type' => 'string' - ), - 'scale' => array( - 'type' => 'string', - 'default' => 'cover' - ), - 'sizeSlug' => array( - 'type' => 'string' - ), - 'rel' => array( - 'type' => 'string', - 'attribute' => 'rel', - 'default' => '', - 'role' => 'content' - ), - 'linkTarget' => array( - 'type' => 'string', - 'default' => '_self', - 'role' => 'content' - ), - 'overlayColor' => array( - 'type' => 'string' - ), - 'customOverlayColor' => array( - 'type' => 'string' - ), - 'dimRatio' => array( - 'type' => 'number', - 'default' => 0 - ), - 'gradient' => array( - 'type' => 'string' - ), - 'customGradient' => array( - 'type' => 'string' - ), - 'useFirstImageFromPost' => array( - 'type' => 'boolean', - 'default' => false - ) - ), - 'usesContext' => array( - 'postId', - 'postType', - 'queryId' - ), - 'example' => array( - 'viewportWidth' => 350 - ), - 'supports' => array( - 'align' => array( - 'left', - 'right', - 'center', - 'wide', - 'full' - ), - 'color' => array( - 'text' => false, - 'background' => false - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'width' => true, - '__experimentalSkipSerialization' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'width' => true - ) - ), - 'filter' => array( - 'duotone' => true - ), - 'shadow' => array( - '__experimentalSkipSerialization' => true - ), - 'html' => false, - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'selectors' => array( - 'border' => '.wp-block-post-featured-image img, .wp-block-post-featured-image .block-editor-media-placeholder, .wp-block-post-featured-image .wp-block-post-featured-image__overlay', - 'shadow' => '.wp-block-post-featured-image img, .wp-block-post-featured-image .components-placeholder', - 'filter' => array( - 'duotone' => '.wp-block-post-featured-image img, .wp-block-post-featured-image .wp-block-post-featured-image__placeholder, .wp-block-post-featured-image .components-placeholder__illustration, .wp-block-post-featured-image .components-placeholder::before' - ) - ), - 'editorStyle' => 'wp-block-post-featured-image-editor', - 'style' => 'wp-block-post-featured-image' - ), - 'post-navigation-link' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-navigation-link', - 'title' => 'Post Navigation Link', - 'category' => 'theme', - 'description' => 'Displays the next or previous post link that is adjacent to the current post.', - 'textdomain' => 'default', - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ), - 'type' => array( - 'type' => 'string', - 'default' => 'next' - ), - 'label' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'showTitle' => array( - 'type' => 'boolean', - 'default' => false - ), - 'linkLabel' => array( - 'type' => 'boolean', - 'default' => false - ), - 'arrow' => array( - 'type' => 'string', - 'default' => 'none' - ), - 'taxonomy' => array( - 'type' => 'string', - 'default' => '' - ) - ), - 'usesContext' => array( - 'postType' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'color' => array( - 'link' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalWritingMode' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'style' => 'wp-block-post-navigation-link' - ), - 'post-template' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-template', - 'title' => 'Post Template', - 'category' => 'theme', - 'ancestor' => array( - 'core/query' - ), - 'description' => 'Contains the block elements used to render a post, like the title, date, featured image, content or excerpt, and more.', - 'textdomain' => 'default', - 'usesContext' => array( - 'queryId', - 'query', - 'displayLayout', - 'templateSlug', - 'previewPostType', - 'enhancedPagination', - 'postType' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'align' => array( - 'wide', - 'full' - ), - 'layout' => true, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - 'blockGap' => array( - '__experimentalDefault' => '1.25em' - ), - '__experimentalDefaultControls' => array( - 'blockGap' => true, - 'padding' => false, - 'margin' => false - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ), - 'style' => 'wp-block-post-template', - 'editorStyle' => 'wp-block-post-template-editor' - ), - 'post-terms' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-terms', - 'title' => 'Post Terms', - 'category' => 'theme', - 'description' => 'Post terms.', - 'textdomain' => 'default', - 'attributes' => array( - 'term' => array( - 'type' => 'string' - ), - 'textAlign' => array( - 'type' => 'string' - ), - 'separator' => array( - 'type' => 'string', - 'default' => ', ' - ), - 'prefix' => array( - 'type' => 'string', - 'default' => '', - 'role' => 'content' - ), - 'suffix' => array( - 'type' => 'string', - 'default' => '', - 'role' => 'content' - ) - ), - 'usesContext' => array( - 'postId', - 'postType' - ), - 'example' => array( - 'viewportWidth' => 350 - ), - 'supports' => array( - 'html' => false, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'style' => 'wp-block-post-terms' - ), - 'post-time-to-read' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-time-to-read', - 'title' => 'Time to Read', - 'category' => 'theme', - 'description' => 'Show minutes required to finish reading the post. Can also show a word count.', - 'textdomain' => 'default', - 'usesContext' => array( - 'postId', - 'postType' - ), - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ), - 'displayAsRange' => array( - 'type' => 'boolean', - 'default' => true - ), - 'displayMode' => array( - 'type' => 'string', - 'default' => 'time' - ), - 'averageReadingSpeed' => array( - 'type' => 'number', - 'default' => 189 - ) - ), - 'supports' => array( - 'color' => array( - 'gradients' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'html' => false, - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'post-title' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/post-title', - 'title' => 'Title', - 'category' => 'theme', - 'description' => 'Displays the title of a post, page, or any other content-type.', - 'textdomain' => 'default', - 'usesContext' => array( - 'postId', - 'postType', - 'queryId' - ), - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ), - 'level' => array( - 'type' => 'number', - 'default' => 2 - ), - 'levelOptions' => array( - 'type' => 'array' - ), - 'isLink' => array( - 'type' => 'boolean', - 'default' => false, - 'role' => 'content' - ), - 'rel' => array( - 'type' => 'string', - 'attribute' => 'rel', - 'default' => '', - 'role' => 'content' - ), - 'linkTarget' => array( - 'type' => 'string', - 'default' => '_self', - 'role' => 'content' - ) - ), - 'example' => array( - 'viewportWidth' => 350 - ), - 'supports' => array( - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'style' => 'wp-block-post-title' - ), - 'preformatted' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/preformatted', - 'title' => 'Preformatted', - 'category' => 'text', - 'description' => 'Add text that respects your spacing and tabs, and also allows styling.', - 'textdomain' => 'default', - 'attributes' => array( - 'content' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'pre', - '__unstablePreserveWhiteSpace' => true, - 'role' => 'content' - ) - ), - 'supports' => array( - 'anchor' => true, - 'color' => array( - 'gradients' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'spacing' => array( - 'padding' => true, - 'margin' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'style' => 'wp-block-preformatted' - ), - 'pullquote' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/pullquote', - 'title' => 'Pullquote', - 'category' => 'text', - 'description' => 'Give special visual emphasis to a quote from your text.', - 'textdomain' => 'default', - 'attributes' => array( - 'value' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'p', - 'role' => 'content' - ), - 'citation' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'cite', - 'role' => 'content' - ), - 'textAlign' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - 'anchor' => true, - 'align' => array( - 'left', - 'right', - 'wide', - 'full' - ), - 'background' => array( - 'backgroundImage' => true, - 'backgroundSize' => true, - '__experimentalDefaultControls' => array( - 'backgroundImage' => true - ) - ), - 'color' => array( - 'gradients' => true, - 'background' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'dimensions' => array( - 'minHeight' => true, - '__experimentalDefaultControls' => array( - 'minHeight' => false - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ) - ), - '__experimentalStyle' => array( - 'typography' => array( - 'fontSize' => '1.5em', - 'lineHeight' => '1.6' - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-pullquote-editor', - 'style' => 'wp-block-pullquote' - ), - 'query' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/query', - 'title' => 'Query Loop', - 'category' => 'theme', - 'description' => 'An advanced block that allows displaying post types based on different query parameters and visual configurations.', - 'keywords' => array( - 'posts', - 'list', - 'blog', - 'blogs', - 'custom post types' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'queryId' => array( - 'type' => 'number' - ), - 'query' => array( - 'type' => 'object', - 'default' => array( - 'perPage' => null, - 'pages' => 0, - 'offset' => 0, - 'postType' => 'post', - 'order' => 'desc', - 'orderBy' => 'date', - 'author' => '', - 'search' => '', - 'exclude' => array( - - ), - 'sticky' => '', - 'inherit' => true, - 'taxQuery' => null, - 'parents' => array( - - ), - 'format' => array( - - ) - ) - ), - 'tagName' => array( - 'type' => 'string', - 'default' => 'div' - ), - 'namespace' => array( - 'type' => 'string' - ), - 'enhancedPagination' => array( - 'type' => 'boolean', - 'default' => false - ) - ), - 'usesContext' => array( - 'templateSlug' - ), - 'providesContext' => array( - 'queryId' => 'queryId', - 'query' => 'query', - 'displayLayout' => 'displayLayout', - 'enhancedPagination' => 'enhancedPagination' - ), - 'supports' => array( - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - 'layout' => true, - 'interactivity' => true, - 'contentRole' => true - ), - 'editorStyle' => 'wp-block-query-editor' - ), - 'query-no-results' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/query-no-results', - 'title' => 'No Results', - 'category' => 'theme', - 'description' => 'Contains the block elements used to render content when no query results are found.', - 'ancestor' => array( - 'core/query' - ), - 'textdomain' => 'default', - 'usesContext' => array( - 'queryId', - 'query' - ), - 'supports' => array( - 'align' => true, - 'reusable' => false, - 'html' => false, - 'color' => array( - 'gradients' => true, - 'link' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ) - ), - 'query-pagination' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/query-pagination', - 'title' => 'Pagination', - 'category' => 'theme', - 'ancestor' => array( - 'core/query' - ), - 'allowedBlocks' => array( - 'core/query-pagination-previous', - 'core/query-pagination-numbers', - 'core/query-pagination-next' - ), - 'description' => 'Displays a paginated navigation to next/previous set of posts, when applicable.', - 'textdomain' => 'default', - 'attributes' => array( - 'paginationArrow' => array( - 'type' => 'string', - 'default' => 'none' - ), - 'showLabel' => array( - 'type' => 'boolean', - 'default' => true - ) - ), - 'usesContext' => array( - 'queryId', - 'query' - ), - 'providesContext' => array( - 'paginationArrow' => 'paginationArrow', - 'showLabel' => 'showLabel' - ), - 'supports' => array( - 'align' => true, - 'reusable' => false, - 'html' => false, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'layout' => array( - 'allowSwitching' => false, - 'allowInheriting' => false, - 'default' => array( - 'type' => 'flex' - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-query-pagination-editor', - 'style' => 'wp-block-query-pagination' - ), - 'query-pagination-next' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/query-pagination-next', - 'title' => 'Next Page', - 'category' => 'theme', - 'parent' => array( - 'core/query-pagination' - ), - 'description' => 'Displays the next posts page link.', - 'textdomain' => 'default', - 'attributes' => array( - 'label' => array( - 'type' => 'string' - ) - ), - 'usesContext' => array( - 'queryId', - 'query', - 'paginationArrow', - 'showLabel', - 'enhancedPagination' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'color' => array( - 'gradients' => true, - 'text' => false, - '__experimentalDefaultControls' => array( - 'background' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ) - ), - 'query-pagination-numbers' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/query-pagination-numbers', - 'title' => 'Page Numbers', - 'category' => 'theme', - 'parent' => array( - 'core/query-pagination' - ), - 'description' => 'Displays a list of page numbers for pagination.', - 'textdomain' => 'default', - 'attributes' => array( - 'midSize' => array( - 'type' => 'number', - 'default' => 2 - ) - ), - 'usesContext' => array( - 'queryId', - 'query', - 'enhancedPagination' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'color' => array( - 'gradients' => true, - 'text' => false, - '__experimentalDefaultControls' => array( - 'background' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-query-pagination-numbers-editor' - ), - 'query-pagination-previous' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/query-pagination-previous', - 'title' => 'Previous Page', - 'category' => 'theme', - 'parent' => array( - 'core/query-pagination' - ), - 'description' => 'Displays the previous posts page link.', - 'textdomain' => 'default', - 'attributes' => array( - 'label' => array( - 'type' => 'string' - ) - ), - 'usesContext' => array( - 'queryId', - 'query', - 'paginationArrow', - 'showLabel', - 'enhancedPagination' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'color' => array( - 'gradients' => true, - 'text' => false, - '__experimentalDefaultControls' => array( - 'background' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ) - ), - 'query-title' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/query-title', - 'title' => 'Query Title', - 'category' => 'theme', - 'description' => 'Display the query title.', - 'textdomain' => 'default', - 'attributes' => array( - 'type' => array( - 'type' => 'string' - ), - 'textAlign' => array( - 'type' => 'string' - ), - 'level' => array( - 'type' => 'number', - 'default' => 1 - ), - 'levelOptions' => array( - 'type' => 'array' - ), - 'showPrefix' => array( - 'type' => 'boolean', - 'default' => true - ), - 'showSearchTerm' => array( - 'type' => 'boolean', - 'default' => true - ) - ), - 'example' => array( - 'attributes' => array( - 'type' => 'search' - ) - ), - 'usesContext' => array( - 'query' - ), - 'supports' => array( - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - 'color' => array( - 'gradients' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontStyle' => true, - '__experimentalFontWeight' => true, - '__experimentalLetterSpacing' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'style' => 'wp-block-query-title' - ), - 'query-total' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/query-total', - 'title' => 'Query Total', - 'category' => 'theme', - 'ancestor' => array( - 'core/query' - ), - 'description' => 'Display the total number of results in a query.', - 'textdomain' => 'default', - 'attributes' => array( - 'displayType' => array( - 'type' => 'string', - 'default' => 'total-results' - ) - ), - 'usesContext' => array( - 'queryId', - 'query' - ), - 'supports' => array( - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'color' => array( - 'gradients' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'style' => 'wp-block-query-total' - ), - 'quote' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/quote', - 'title' => 'Quote', - 'category' => 'text', - 'description' => 'Give quoted text visual emphasis. "In quoting others, we cite ourselves." — Julio Cortázar', - 'keywords' => array( - 'blockquote', - 'cite' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'value' => array( - 'type' => 'string', - 'source' => 'html', - 'selector' => 'blockquote', - 'multiline' => 'p', - 'default' => '', - 'role' => 'content' - ), - 'citation' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'cite', - 'role' => 'content' - ), - 'textAlign' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - 'anchor' => true, - 'align' => array( - 'left', - 'right', - 'wide', - 'full' - ), - 'html' => false, - 'background' => array( - 'backgroundImage' => true, - 'backgroundSize' => true, - '__experimentalDefaultControls' => array( - 'backgroundImage' => true - ) - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'style' => true, - 'width' => true - ) - ), - 'dimensions' => array( - 'minHeight' => true, - '__experimentalDefaultControls' => array( - 'minHeight' => false - ) - ), - '__experimentalOnEnter' => true, - '__experimentalOnMerge' => true, - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'color' => array( - 'gradients' => true, - 'heading' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'layout' => array( - 'allowEditing' => false - ), - 'spacing' => array( - 'blockGap' => true, - 'padding' => true, - 'margin' => true - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - 'allowedBlocks' => true - ), - 'styles' => array( - array( - 'name' => 'default', - 'label' => 'Default', - 'isDefault' => true - ), - array( - 'name' => 'plain', - 'label' => 'Plain' - ) - ), - 'editorStyle' => 'wp-block-quote-editor', - 'style' => 'wp-block-quote' - ), - 'read-more' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/read-more', - 'title' => 'Read More', - 'category' => 'theme', - 'description' => 'Displays the link of a post, page, or any other content-type.', - 'textdomain' => 'default', - 'attributes' => array( - 'content' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'linkTarget' => array( - 'type' => 'string', - 'default' => '_self' - ) - ), - 'usesContext' => array( - 'postId' - ), - 'supports' => array( - 'html' => false, - 'color' => array( - 'gradients' => true, - 'text' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalLetterSpacing' => true, - '__experimentalTextDecoration' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true, - 'textDecoration' => true - ) - ), - 'spacing' => array( - 'margin' => array( - 'top', - 'bottom' - ), - 'padding' => true, - '__experimentalDefaultControls' => array( - 'padding' => true - ) - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'width' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'style' => 'wp-block-read-more' - ), - 'rss' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/rss', - 'title' => 'RSS', - 'category' => 'widgets', - 'description' => 'Display entries from any RSS or Atom feed.', - 'keywords' => array( - 'atom', - 'feed' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'columns' => array( - 'type' => 'number', - 'default' => 2 - ), - 'blockLayout' => array( - 'type' => 'string', - 'default' => 'list' - ), - 'feedURL' => array( - 'type' => 'string', - 'default' => '', - 'role' => 'content' - ), - 'itemsToShow' => array( - 'type' => 'number', - 'default' => 5 - ), - 'displayExcerpt' => array( - 'type' => 'boolean', - 'default' => false - ), - 'displayAuthor' => array( - 'type' => 'boolean', - 'default' => false - ), - 'displayDate' => array( - 'type' => 'boolean', - 'default' => false - ), - 'excerptLength' => array( - 'type' => 'number', - 'default' => 55 - ), - 'openInNewTab' => array( - 'type' => 'boolean', - 'default' => false - ), - 'rel' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - 'align' => true, - 'html' => false, - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'padding' => false, - 'margin' => false - ) - ), - 'color' => array( - 'background' => true, - 'text' => true, - 'gradients' => true, - 'link' => true - ) - ), - 'editorStyle' => 'wp-block-rss-editor', - 'style' => 'wp-block-rss' - ), - 'search' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/search', - 'title' => 'Search', - 'category' => 'widgets', - 'description' => 'Help visitors find your content.', - 'keywords' => array( - 'find' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'label' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'showLabel' => array( - 'type' => 'boolean', - 'default' => true - ), - 'placeholder' => array( - 'type' => 'string', - 'default' => '', - 'role' => 'content' - ), - 'width' => array( - 'type' => 'number' - ), - 'widthUnit' => array( - 'type' => 'string' - ), - 'buttonText' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'buttonPosition' => array( - 'type' => 'string', - 'default' => 'button-outside' - ), - 'buttonUseIcon' => array( - 'type' => 'boolean', - 'default' => false - ), - 'query' => array( - 'type' => 'object', - 'default' => array( - - ) - ), - 'isSearchFieldHidden' => array( - 'type' => 'boolean', - 'default' => false - ) - ), - 'supports' => array( - 'align' => array( - 'left', - 'center', - 'right' - ), - 'color' => array( - 'gradients' => true, - '__experimentalSkipSerialization' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'interactivity' => true, - 'typography' => array( - '__experimentalSkipSerialization' => true, - '__experimentalSelector' => '.wp-block-search__label, .wp-block-search__input, .wp-block-search__button', - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__experimentalBorder' => array( - 'color' => true, - 'radius' => true, - 'width' => true, - '__experimentalSkipSerialization' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'radius' => true, - 'width' => true - ) - ), - 'spacing' => array( - 'margin' => true - ), - 'html' => false - ), - 'editorStyle' => 'wp-block-search-editor', - 'style' => 'wp-block-search' - ), - 'separator' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/separator', - 'title' => 'Separator', - 'category' => 'design', - 'description' => 'Create a break between ideas or sections with a horizontal separator.', - 'keywords' => array( - 'horizontal-line', - 'hr', - 'divider' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'opacity' => array( - 'type' => 'string', - 'default' => 'alpha-channel' - ), - 'tagName' => array( - 'type' => 'string', - 'enum' => array( - 'hr', - 'div' - ), - 'default' => 'hr' - ) - ), - 'supports' => array( - 'anchor' => true, - 'align' => array( - 'center', - 'wide', - 'full' - ), - 'color' => array( - 'enableContrastChecker' => false, - '__experimentalSkipSerialization' => true, - 'gradients' => true, - 'background' => true, - 'text' => false, - '__experimentalDefaultControls' => array( - 'background' => true - ) - ), - 'spacing' => array( - 'margin' => array( - 'top', - 'bottom' - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'styles' => array( - array( - 'name' => 'default', - 'label' => 'Default', - 'isDefault' => true - ), - array( - 'name' => 'wide', - 'label' => 'Wide Line' - ), - array( - 'name' => 'dots', - 'label' => 'Dots' - ) - ), - 'editorStyle' => 'wp-block-separator-editor', - 'style' => 'wp-block-separator' - ), - 'shortcode' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/shortcode', - 'title' => 'Shortcode', - 'category' => 'widgets', - 'description' => 'Insert additional custom elements with a WordPress shortcode.', - 'textdomain' => 'default', - 'attributes' => array( - 'text' => array( - 'type' => 'string', - 'source' => 'raw', - 'role' => 'content' - ) - ), - 'supports' => array( - 'className' => false, - 'customClassName' => false, - 'html' => false - ), - 'editorStyle' => 'wp-block-shortcode-editor' - ), - 'site-logo' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/site-logo', - 'title' => 'Site Logo', - 'category' => 'theme', - 'description' => 'Display an image to represent this site. Update this block and the changes apply everywhere.', - 'textdomain' => 'default', - 'attributes' => array( - 'width' => array( - 'type' => 'number' - ), - 'isLink' => array( - 'type' => 'boolean', - 'default' => true, - 'role' => 'content' - ), - 'linkTarget' => array( - 'type' => 'string', - 'default' => '_self', - 'role' => 'content' - ), - 'shouldSyncIcon' => array( - 'type' => 'boolean' - ) - ), - 'example' => array( - 'viewportWidth' => 500, - 'attributes' => array( - 'width' => 350, - 'className' => 'block-editor-block-types-list__site-logo-example' - ) - ), - 'supports' => array( - 'html' => false, - 'align' => true, - 'alignWide' => false, - 'color' => array( - 'text' => false, - 'background' => false - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - 'filter' => array( - 'duotone' => true - ) - ), - 'styles' => array( - array( - 'name' => 'default', - 'label' => 'Default', - 'isDefault' => true - ), - array( - 'name' => 'rounded', - 'label' => 'Rounded' - ) - ), - 'selectors' => array( - 'filter' => array( - 'duotone' => '.wp-block-site-logo img, .wp-block-site-logo .components-placeholder__illustration, .wp-block-site-logo .components-placeholder::before' - ) - ), - 'editorStyle' => 'wp-block-site-logo-editor', - 'style' => 'wp-block-site-logo' - ), - 'site-tagline' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/site-tagline', - 'title' => 'Site Tagline', - 'category' => 'theme', - 'description' => 'Describe in a few words what this site is about. This is important for search results, sharing on social media, and gives overall clarity to visitors.', - 'keywords' => array( - 'description' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ), - 'level' => array( - 'type' => 'number', - 'default' => 0 - ), - 'levelOptions' => array( - 'type' => 'array', - 'default' => array( - 0, - 1, - 2, - 3, - 4, - 5, - 6 - ) - ) - ), - 'example' => array( - 'viewportWidth' => 350, - 'attributes' => array( - 'textAlign' => 'center' - ) - ), - 'supports' => array( - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - 'color' => array( - 'gradients' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'contentRole' => true, - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalFontStyle' => true, - '__experimentalFontWeight' => true, - '__experimentalLetterSpacing' => true, - '__experimentalWritingMode' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ), - 'editorStyle' => 'wp-block-site-tagline-editor', - 'style' => 'wp-block-site-tagline' - ), - 'site-title' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/site-title', - 'title' => 'Site Title', - 'category' => 'theme', - 'description' => 'Displays the name of this site. Update the block, and the changes apply everywhere it’s used. This will also appear in the browser title bar and in search results.', - 'textdomain' => 'default', - 'attributes' => array( - 'level' => array( - 'type' => 'number', - 'default' => 1 - ), - 'levelOptions' => array( - 'type' => 'array', - 'default' => array( - 0, - 1, - 2, - 3, - 4, - 5, - 6 - ) - ), - 'textAlign' => array( - 'type' => 'string' - ), - 'isLink' => array( - 'type' => 'boolean', - 'default' => true, - 'role' => 'content' - ), - 'linkTarget' => array( - 'type' => 'string', - 'default' => '_self', - 'role' => 'content' - ) - ), - 'example' => array( - 'viewportWidth' => 500 - ), - 'supports' => array( - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'spacing' => array( - 'padding' => true, - 'margin' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalFontStyle' => true, - '__experimentalFontWeight' => true, - '__experimentalLetterSpacing' => true, - '__experimentalWritingMode' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ), - 'editorStyle' => 'wp-block-site-title-editor', - 'style' => 'wp-block-site-title' - ), - 'social-link' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/social-link', - 'title' => 'Social Icon', - 'category' => 'widgets', - 'parent' => array( - 'core/social-links' - ), - 'description' => 'Display an icon linking to a social profile or site.', - 'textdomain' => 'default', - 'attributes' => array( - 'url' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'service' => array( - 'type' => 'string' - ), - 'label' => array( - 'type' => 'string', - 'role' => 'content' - ), - 'rel' => array( - 'type' => 'string' - ) - ), - 'usesContext' => array( - 'openInNewTab', - 'showLabels', - 'iconColor', - 'iconColorValue', - 'iconBackgroundColor', - 'iconBackgroundColorValue' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-social-link-editor' - ), - 'social-links' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/social-links', - 'title' => 'Social Icons', - 'category' => 'widgets', - 'allowedBlocks' => array( - 'core/social-link' - ), - 'description' => 'Display icons linking to your social profiles or sites.', - 'keywords' => array( - 'links' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'iconColor' => array( - 'type' => 'string' - ), - 'customIconColor' => array( - 'type' => 'string' - ), - 'iconColorValue' => array( - 'type' => 'string' - ), - 'iconBackgroundColor' => array( - 'type' => 'string' - ), - 'customIconBackgroundColor' => array( - 'type' => 'string' - ), - 'iconBackgroundColorValue' => array( - 'type' => 'string' - ), - 'openInNewTab' => array( - 'type' => 'boolean', - 'default' => false - ), - 'showLabels' => array( - 'type' => 'boolean', - 'default' => false - ), - 'size' => array( - 'type' => 'string' - ) - ), - 'providesContext' => array( - 'openInNewTab' => 'openInNewTab', - 'showLabels' => 'showLabels', - 'iconColor' => 'iconColor', - 'iconColorValue' => 'iconColorValue', - 'iconBackgroundColor' => 'iconBackgroundColor', - 'iconBackgroundColorValue' => 'iconBackgroundColorValue' - ), - 'supports' => array( - 'align' => array( - 'left', - 'center', - 'right' - ), - 'anchor' => true, - 'html' => false, - '__experimentalExposeControlsToChildren' => true, - 'layout' => array( - 'allowSwitching' => false, - 'allowInheriting' => false, - 'allowVerticalAlignment' => false, - 'default' => array( - 'type' => 'flex' - ) - ), - 'color' => array( - 'enableContrastChecker' => false, - 'background' => true, - 'gradients' => true, - 'text' => false, - '__experimentalDefaultControls' => array( - 'background' => false - ) - ), - 'spacing' => array( - 'blockGap' => array( - 'horizontal', - 'vertical' - ), - 'margin' => true, - 'padding' => true, - 'units' => array( - 'px', - 'em', - 'rem', - 'vh', - 'vw' - ), - '__experimentalDefaultControls' => array( - 'blockGap' => true, - 'margin' => true, - 'padding' => false - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ), - 'contentRole' => true - ), - 'styles' => array( - array( - 'name' => 'default', - 'label' => 'Default', - 'isDefault' => true - ), - array( - 'name' => 'logos-only', - 'label' => 'Logos Only' - ), - array( - 'name' => 'pill-shape', - 'label' => 'Pill Shape' - ) - ), - 'editorStyle' => 'wp-block-social-links-editor', - 'style' => 'wp-block-social-links' - ), - 'spacer' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/spacer', - 'title' => 'Spacer', - 'category' => 'design', - 'description' => 'Add white space between blocks and customize its height.', - 'textdomain' => 'default', - 'attributes' => array( - 'height' => array( - 'type' => 'string', - 'default' => '100px' - ), - 'width' => array( - 'type' => 'string' - ) - ), - 'usesContext' => array( - 'orientation' - ), - 'supports' => array( - 'anchor' => true, - 'spacing' => array( - 'margin' => array( - 'top', - 'bottom' - ), - '__experimentalDefaultControls' => array( - 'margin' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-spacer-editor', - 'style' => 'wp-block-spacer' - ), - 'table' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/table', - 'title' => 'Table', - 'category' => 'text', - 'description' => 'Create structured content in rows and columns to display information.', - 'textdomain' => 'default', - 'attributes' => array( - 'hasFixedLayout' => array( - 'type' => 'boolean', - 'default' => true - ), - 'caption' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'figcaption', - 'role' => 'content' - ), - 'head' => array( - 'type' => 'array', - 'default' => array( - - ), - 'source' => 'query', - 'selector' => 'thead tr', - 'query' => array( - 'cells' => array( - 'type' => 'array', - 'default' => array( - - ), - 'source' => 'query', - 'selector' => 'td,th', - 'query' => array( - 'content' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'role' => 'content' - ), - 'tag' => array( - 'type' => 'string', - 'default' => 'td', - 'source' => 'tag' - ), - 'scope' => array( - 'type' => 'string', - 'source' => 'attribute', - 'attribute' => 'scope' - ), - 'align' => array( - 'type' => 'string', - 'source' => 'attribute', - 'attribute' => 'data-align' - ), - 'colspan' => array( - 'type' => 'string', - 'source' => 'attribute', - 'attribute' => 'colspan' - ), - 'rowspan' => array( - 'type' => 'string', - 'source' => 'attribute', - 'attribute' => 'rowspan' - ) - ) - ) - ) - ), - 'body' => array( - 'type' => 'array', - 'default' => array( - - ), - 'source' => 'query', - 'selector' => 'tbody tr', - 'query' => array( - 'cells' => array( - 'type' => 'array', - 'default' => array( - - ), - 'source' => 'query', - 'selector' => 'td,th', - 'query' => array( - 'content' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'role' => 'content' - ), - 'tag' => array( - 'type' => 'string', - 'default' => 'td', - 'source' => 'tag' - ), - 'scope' => array( - 'type' => 'string', - 'source' => 'attribute', - 'attribute' => 'scope' - ), - 'align' => array( - 'type' => 'string', - 'source' => 'attribute', - 'attribute' => 'data-align' - ), - 'colspan' => array( - 'type' => 'string', - 'source' => 'attribute', - 'attribute' => 'colspan' - ), - 'rowspan' => array( - 'type' => 'string', - 'source' => 'attribute', - 'attribute' => 'rowspan' - ) - ) - ) - ) - ), - 'foot' => array( - 'type' => 'array', - 'default' => array( - - ), - 'source' => 'query', - 'selector' => 'tfoot tr', - 'query' => array( - 'cells' => array( - 'type' => 'array', - 'default' => array( - - ), - 'source' => 'query', - 'selector' => 'td,th', - 'query' => array( - 'content' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'role' => 'content' - ), - 'tag' => array( - 'type' => 'string', - 'default' => 'td', - 'source' => 'tag' - ), - 'scope' => array( - 'type' => 'string', - 'source' => 'attribute', - 'attribute' => 'scope' - ), - 'align' => array( - 'type' => 'string', - 'source' => 'attribute', - 'attribute' => 'data-align' - ), - 'colspan' => array( - 'type' => 'string', - 'source' => 'attribute', - 'attribute' => 'colspan' - ), - 'rowspan' => array( - 'type' => 'string', - 'source' => 'attribute', - 'attribute' => 'rowspan' - ) - ) - ) - ) - ) - ), - 'supports' => array( - 'anchor' => true, - 'align' => true, - 'color' => array( - '__experimentalSkipSerialization' => true, - 'gradients' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontStyle' => true, - '__experimentalFontWeight' => true, - '__experimentalLetterSpacing' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - '__experimentalBorder' => array( - '__experimentalSkipSerialization' => true, - 'color' => true, - 'style' => true, - 'width' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'style' => true, - 'width' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'selectors' => array( - 'root' => '.wp-block-table > table', - 'spacing' => '.wp-block-table' - ), - 'styles' => array( - array( - 'name' => 'regular', - 'label' => 'Default', - 'isDefault' => true - ), - array( - 'name' => 'stripes', - 'label' => 'Stripes' - ) - ), - 'editorStyle' => 'wp-block-table-editor', - 'style' => 'wp-block-table' - ), - 'tag-cloud' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/tag-cloud', - 'title' => 'Tag Cloud', - 'category' => 'widgets', - 'description' => 'A cloud of popular keywords, each sized by how often it appears.', - 'textdomain' => 'default', - 'attributes' => array( - 'numberOfTags' => array( - 'type' => 'number', - 'default' => 45, - 'minimum' => 1, - 'maximum' => 100 - ), - 'taxonomy' => array( - 'type' => 'string', - 'default' => 'post_tag' - ), - 'showTagCounts' => array( - 'type' => 'boolean', - 'default' => false - ), - 'smallestFontSize' => array( - 'type' => 'string', - 'default' => '8pt' - ), - 'largestFontSize' => array( - 'type' => 'string', - 'default' => '22pt' - ) - ), - 'styles' => array( - array( - 'name' => 'default', - 'label' => 'Default', - 'isDefault' => true - ), - array( - 'name' => 'outline', - 'label' => 'Outline' - ) - ), - 'supports' => array( - 'html' => false, - 'align' => true, - 'spacing' => array( - 'margin' => true, - 'padding' => true - ), - 'typography' => array( - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalLetterSpacing' => true - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'editorStyle' => 'wp-block-tag-cloud-editor' - ), - 'template-part' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/template-part', - 'title' => 'Template Part', - 'category' => 'theme', - 'description' => 'Edit the different global regions of your site, like the header, footer, sidebar, or create your own.', - 'textdomain' => 'default', - 'attributes' => array( - 'slug' => array( - 'type' => 'string' - ), - 'theme' => array( - 'type' => 'string' - ), - 'tagName' => array( - 'type' => 'string' - ), - 'area' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - 'align' => true, - 'html' => false, - 'reusable' => false, - 'renaming' => false, - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-template-part-editor' - ), - 'term-count' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/term-count', - 'title' => 'Term Count', - 'category' => 'theme', - 'description' => 'Displays the post count of a taxonomy term.', - 'textdomain' => 'default', - 'usesContext' => array( - 'termId', - 'taxonomy' - ), - 'attributes' => array( - 'bracketType' => array( - 'type' => 'string', - 'enum' => array( - 'none', - 'round', - 'square', - 'curly', - 'angle' - ), - 'default' => 'round' - ) - ), - 'supports' => array( - 'html' => false, - 'color' => array( - 'gradients' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'spacing' => array( - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'style' => 'wp-block-term-count' - ), - 'term-description' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/term-description', - 'title' => 'Term Description', - 'category' => 'theme', - 'description' => 'Display the description of categories, tags and custom taxonomies when viewing an archive.', - 'textdomain' => 'default', - 'usesContext' => array( - 'termId', - 'taxonomy' - ), - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - 'color' => array( - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'spacing' => array( - 'padding' => true, - 'margin' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ) - ), - 'term-name' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/term-name', - 'title' => 'Term Name', - 'category' => 'theme', - 'description' => 'Displays the name of a taxonomy term.', - 'keywords' => array( - 'term title' - ), - 'textdomain' => 'default', - 'usesContext' => array( - 'termId', - 'taxonomy' - ), - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string' - ), - 'level' => array( - 'type' => 'number', - 'default' => 0 - ), - 'isLink' => array( - 'type' => 'boolean', - 'default' => false - ) - ), - 'supports' => array( - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - 'link' => true - ) - ), - 'spacing' => array( - 'padding' => true - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true, - '__experimentalDefaultControls' => array( - 'color' => true, - 'width' => true, - 'style' => true - ) - ) - ), - 'style' => 'wp-block-term-name' - ), - 'term-template' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/term-template', - 'title' => 'Term Template', - 'category' => 'theme', - 'ancestor' => array( - 'core/terms-query' - ), - 'description' => 'Contains the block elements used to render a taxonomy term, like the name, description, and more.', - 'textdomain' => 'default', - 'usesContext' => array( - 'termQuery' - ), - 'supports' => array( - 'reusable' => false, - 'html' => false, - 'align' => array( - 'wide', - 'full' - ), - 'layout' => true, - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontFamily' => true, - '__experimentalFontWeight' => true, - '__experimentalFontStyle' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalLetterSpacing' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - 'blockGap' => array( - '__experimentalDefault' => '1.25em' - ), - '__experimentalDefaultControls' => array( - 'blockGap' => true, - 'padding' => false, - 'margin' => false - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ), - '__experimentalBorder' => array( - 'radius' => true, - 'color' => true, - 'width' => true, - 'style' => true - ) - ), - 'style' => 'wp-block-term-template', - 'editorStyle' => 'wp-block-term-template-editor' - ), - 'terms-query' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/terms-query', - 'title' => 'Terms Query', - 'category' => 'theme', - 'description' => 'An advanced block that allows displaying taxonomy terms based on different query parameters and visual configurations.', - 'keywords' => array( - 'terms', - 'taxonomy', - 'categories', - 'tags', - 'list' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'termQuery' => array( - 'type' => 'object', - 'default' => array( - 'perPage' => 10, - 'taxonomy' => 'category', - 'order' => 'asc', - 'orderBy' => 'name', - 'include' => array( - - ), - 'hideEmpty' => true, - 'showNested' => false, - 'inherit' => false - ) - ), - 'tagName' => array( - 'type' => 'string', - 'default' => 'div' - ) - ), - 'usesContext' => array( - 'templateSlug' - ), - 'providesContext' => array( - 'termQuery' => 'termQuery' - ), - 'supports' => array( - 'align' => array( - 'wide', - 'full' - ), - 'html' => false, - 'layout' => true, - 'interactivity' => true - ) - ), - 'text-columns' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/text-columns', - 'title' => 'Text Columns (deprecated)', - 'icon' => 'columns', - 'category' => 'design', - 'description' => 'This block is deprecated. Please use the Columns block instead.', - 'textdomain' => 'default', - 'attributes' => array( - 'content' => array( - 'type' => 'array', - 'source' => 'query', - 'selector' => 'p', - 'query' => array( - 'children' => array( - 'type' => 'string', - 'source' => 'html' - ) - ), - 'default' => array( - array( - - ), - array( - - ) - ) - ), - 'columns' => array( - 'type' => 'number', - 'default' => 2 - ), - 'width' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - 'inserter' => false, - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-text-columns-editor', - 'style' => 'wp-block-text-columns' - ), - 'verse' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/verse', - 'title' => 'Verse', - 'category' => 'text', - 'description' => 'Insert poetry. Use special spacing formats. Or quote song lyrics.', - 'keywords' => array( - 'poetry', - 'poem' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'content' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'pre', - '__unstablePreserveWhiteSpace' => true, - 'role' => 'content' - ), - 'textAlign' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - 'anchor' => true, - 'background' => array( - 'backgroundImage' => true, - 'backgroundSize' => true, - '__experimentalDefaultControls' => array( - 'backgroundImage' => true - ) - ), - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true - ) - ), - 'dimensions' => array( - 'minHeight' => true, - '__experimentalDefaultControls' => array( - 'minHeight' => false - ) - ), - 'typography' => array( - 'fontSize' => true, - '__experimentalFontFamily' => true, - 'lineHeight' => true, - '__experimentalFontStyle' => true, - '__experimentalFontWeight' => true, - '__experimentalLetterSpacing' => true, - '__experimentalTextTransform' => true, - '__experimentalTextDecoration' => true, - '__experimentalWritingMode' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true - ) - ), - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - '__experimentalBorder' => array( - 'radius' => true, - 'width' => true, - 'color' => true, - 'style' => true - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'style' => 'wp-block-verse', - 'editorStyle' => 'wp-block-verse-editor' - ), - 'video' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/video', - 'title' => 'Video', - 'category' => 'media', - 'description' => 'Embed a video from your media library or upload a new one.', - 'keywords' => array( - 'movie' - ), - 'textdomain' => 'default', - 'attributes' => array( - 'autoplay' => array( - 'type' => 'boolean', - 'source' => 'attribute', - 'selector' => 'video', - 'attribute' => 'autoplay' - ), - 'caption' => array( - 'type' => 'rich-text', - 'source' => 'rich-text', - 'selector' => 'figcaption', - 'role' => 'content' - ), - 'controls' => array( - 'type' => 'boolean', - 'source' => 'attribute', - 'selector' => 'video', - 'attribute' => 'controls', - 'default' => true - ), - 'id' => array( - 'type' => 'number', - 'role' => 'content' - ), - 'loop' => array( - 'type' => 'boolean', - 'source' => 'attribute', - 'selector' => 'video', - 'attribute' => 'loop' - ), - 'muted' => array( - 'type' => 'boolean', - 'source' => 'attribute', - 'selector' => 'video', - 'attribute' => 'muted' - ), - 'poster' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'video', - 'attribute' => 'poster' - ), - 'preload' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'video', - 'attribute' => 'preload', - 'default' => 'metadata' - ), - 'blob' => array( - 'type' => 'string', - 'role' => 'local' - ), - 'src' => array( - 'type' => 'string', - 'source' => 'attribute', - 'selector' => 'video', - 'attribute' => 'src', - 'role' => 'content' - ), - 'playsInline' => array( - 'type' => 'boolean', - 'source' => 'attribute', - 'selector' => 'video', - 'attribute' => 'playsinline' - ), - 'tracks' => array( - 'role' => 'content', - 'type' => 'array', - 'items' => array( - 'type' => 'object' - ), - 'default' => array( - - ) - ) - ), - 'supports' => array( - 'anchor' => true, - 'align' => true, - 'spacing' => array( - 'margin' => true, - 'padding' => true, - '__experimentalDefaultControls' => array( - 'margin' => false, - 'padding' => false - ) - ), - 'interactivity' => array( - 'clientNavigation' => true - ) - ), - 'editorStyle' => 'wp-block-video-editor', - 'style' => 'wp-block-video' - ), - 'widget-group' => array( - '$schema' => 'https://schemas.wp.org/trunk/block.json', - 'apiVersion' => 3, - 'name' => 'core/widget-group', - 'title' => 'Widget Group', - 'category' => 'widgets', - 'attributes' => array( - 'title' => array( - 'type' => 'string' - ) - ), - 'supports' => array( - 'html' => false, - 'inserter' => true, - 'customClassName' => true, - 'reusable' => false - ), - 'editorStyle' => 'wp-block-widget-group-editor', - 'style' => 'wp-block-widget-group' - ) -); \ No newline at end of file diff --git a/src/wp-includes/blocks/button.php b/src/wp-includes/blocks/button.php deleted file mode 100644 index 0d03440b1cb0f..0000000000000 --- a/src/wp-includes/blocks/button.php +++ /dev/null @@ -1,79 +0,0 @@ -` or `
', - $wrapper_attributes, - $calendar - ); - - $monthnum = $previous_monthnum; - $year = $previous_year; - - return $output; -} - -/** - * Registers the `core/calendar` block on server. - * - * @since 5.2.0 - */ -function register_block_core_calendar() { - register_block_type_from_metadata( - __DIR__ . '/calendar', - array( - 'render_callback' => 'render_block_core_calendar', - ) - ); -} - -add_action( 'init', 'register_block_core_calendar' ); - -/** - * Returns whether or not there are any published posts. - * - * Used to hide the calendar block when there are no published posts. - * This compensates for a known Core bug: https://core.trac.wordpress.org/ticket/12016 - * - * @since 5.9.0 - * - * @return bool Has any published posts or not. - */ -function block_core_calendar_has_published_posts() { - // Multisite already has an option that stores the count of the published posts. - // Let's use that for multisites. - if ( is_multisite() ) { - return 0 < (int) get_option( 'post_count' ); - } - - // On single sites we try our own cached option first. - $has_published_posts = get_option( 'wp_calendar_block_has_published_posts', null ); - if ( null !== $has_published_posts ) { - return (bool) $has_published_posts; - } - - // No cache hit, let's update the cache and return the cached value. - return block_core_calendar_update_has_published_posts(); -} - -/** - * Queries the database for any published post and saves - * a flag whether any published post exists or not. - * - * @since 5.9.0 - * - * @global wpdb $wpdb WordPress database abstraction object. - * - * @return bool Has any published posts or not. - */ -function block_core_calendar_update_has_published_posts() { - global $wpdb; - $has_published_posts = (bool) $wpdb->get_var( "SELECT 1 as test FROM {$wpdb->posts} WHERE post_type = 'post' AND post_status = 'publish' LIMIT 1" ); - update_option( 'wp_calendar_block_has_published_posts', $has_published_posts ); - return $has_published_posts; -} - -// We only want to register these functions and actions when -// we are on single sites. On multi sites we use `post_count` option. -if ( ! is_multisite() ) { - /** - * Handler for updating the has published posts flag when a post is deleted. - * - * @since 5.9.0 - * - * @param int $post_id Deleted post ID. - */ - function block_core_calendar_update_has_published_post_on_delete( $post_id ) { - $post = get_post( $post_id ); - - if ( ! $post || 'publish' !== $post->post_status || 'post' !== $post->post_type ) { - return; - } - - block_core_calendar_update_has_published_posts(); - } - - /** - * Handler for updating the has published posts flag when a post status changes. - * - * @since 5.9.0 - * - * @param string $new_status The status the post is changing to. - * @param string $old_status The status the post is changing from. - * @param WP_Post $post Post object. - */ - function block_core_calendar_update_has_published_post_on_transition_post_status( $new_status, $old_status, $post ) { - if ( $new_status === $old_status ) { - return; - } - - if ( 'post' !== get_post_type( $post ) ) { - return; - } - - if ( 'publish' !== $new_status && 'publish' !== $old_status ) { - return; - } - - block_core_calendar_update_has_published_posts(); - } - - add_action( 'delete_post', 'block_core_calendar_update_has_published_post_on_delete' ); - add_action( 'transition_post_status', 'block_core_calendar_update_has_published_post_on_transition_post_status', 10, 3 ); -} diff --git a/src/wp-includes/blocks/calendar/block.json b/src/wp-includes/blocks/calendar/block.json deleted file mode 100644 index 5816b8c75eaca..0000000000000 --- a/src/wp-includes/blocks/calendar/block.json +++ /dev/null @@ -1,47 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/calendar", - "title": "Calendar", - "category": "widgets", - "description": "A calendar of your site’s posts.", - "keywords": [ "posts", "archive" ], - "textdomain": "default", - "attributes": { - "month": { - "type": "integer" - }, - "year": { - "type": "integer" - } - }, - "supports": { - "align": true, - "html": false, - "color": { - "link": true, - "__experimentalSkipSerialization": [ "text", "background" ], - "__experimentalDefaultControls": { - "background": true, - "text": true - }, - "__experimentalSelector": "table, th" - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "style": "wp-block-calendar" -} diff --git a/src/wp-includes/blocks/categories.php b/src/wp-includes/blocks/categories.php deleted file mode 100644 index 5ff5858166bb0..0000000000000 --- a/src/wp-includes/blocks/categories.php +++ /dev/null @@ -1,155 +0,0 @@ - false, - 'hierarchical' => ! empty( $attributes['showHierarchy'] ), - 'orderby' => 'name', - 'show_count' => ! empty( $attributes['showPostCounts'] ), - 'taxonomy' => $attributes['taxonomy'], - 'title_li' => '', - 'hide_empty' => empty( $attributes['showEmpty'] ), - ); - if ( ! empty( $attributes['showOnlyTopLevel'] ) && $attributes['showOnlyTopLevel'] ) { - $args['parent'] = 0; - } - - if ( ! empty( $attributes['displayAsDropdown'] ) ) { - $id = 'wp-block-categories-' . $block_id; - $args['id'] = $id; - $args['name'] = $taxonomy->query_var; - $args['value_field'] = 'slug'; - $args['show_option_none'] = sprintf( - /* translators: %s: taxonomy's singular name */ - __( 'Select %s' ), - $taxonomy->labels->singular_name - ); - - $show_label = empty( $attributes['showLabel'] ) ? ' screen-reader-text' : ''; - $default_label = $taxonomy->label; - $label_text = ! empty( $attributes['label'] ) ? wp_kses_post( $attributes['label'] ) : $default_label; - $wrapper_markup = '
%2$s
'; - $items_markup = wp_dropdown_categories( $args ); - $type = 'dropdown'; - - if ( ! is_admin() ) { - // Inject the dropdown script immediately after the select dropdown. - $items_markup = preg_replace( - '#(?<=)#', - build_dropdown_script_block_core_categories( $id ), - $items_markup, - 1 - ); - } - } else { - $args['show_option_none'] = $taxonomy->labels->no_terms; - - $wrapper_markup = '
    %2$s
'; - $items_markup = wp_list_categories( $args ); - $type = 'list'; - - if ( ! empty( $block->context['enhancedPagination'] ) ) { - $p = new WP_HTML_Tag_Processor( $items_markup ); - while ( $p->next_tag( 'a' ) ) { - $p->set_attribute( 'data-wp-on--click', 'core/query::actions.navigate' ); - } - $items_markup = $p->get_updated_html(); - } - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => "wp-block-categories-{$type}" ) ); - - return sprintf( - $wrapper_markup, - $wrapper_attributes, - $items_markup - ); -} - -/** - * Generates the inline script for a categories dropdown field. - * - * @since 5.0.0 - * - * @param string $dropdown_id ID of the dropdown field. - * - * @return string Returns the dropdown onChange redirection script. - */ -function build_dropdown_script_block_core_categories( $dropdown_id ) { - ob_start(); - - $exports = array( $dropdown_id, home_url() ); - ?> - - ', '' ), '', ob_get_clean() ) ) . - "\n//# sourceURL=" . rawurlencode( __FUNCTION__ ) - ); -} - -/** - * Registers the `core/categories` block on server. - * - * @since 5.0.0 - */ -function register_block_core_categories() { - register_block_type_from_metadata( - __DIR__ . '/categories', - array( - 'render_callback' => 'render_block_core_categories', - ) - ); -} -add_action( 'init', 'register_block_core_categories' ); diff --git a/src/wp-includes/blocks/categories/block.json b/src/wp-includes/blocks/categories/block.json deleted file mode 100644 index 8320fa912a175..0000000000000 --- a/src/wp-includes/blocks/categories/block.json +++ /dev/null @@ -1,96 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/categories", - "title": "Terms List", - "category": "widgets", - "description": "Display a list of all terms of a given taxonomy.", - "keywords": [ "categories" ], - "textdomain": "default", - "attributes": { - "taxonomy": { - "type": "string", - "default": "category" - }, - "displayAsDropdown": { - "type": "boolean", - "default": false - }, - "showHierarchy": { - "type": "boolean", - "default": false - }, - "showPostCounts": { - "type": "boolean", - "default": false - }, - "showOnlyTopLevel": { - "type": "boolean", - "default": false - }, - "showEmpty": { - "type": "boolean", - "default": false - }, - "label": { - "type": "string", - "role": "content" - }, - "showLabel": { - "type": "boolean", - "default": true - } - }, - "usesContext": [ "enhancedPagination" ], - "supports": { - "align": true, - "html": false, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "editorStyle": "wp-block-categories-editor", - "style": "wp-block-categories" -} diff --git a/src/wp-includes/blocks/code/block.json b/src/wp-includes/blocks/code/block.json deleted file mode 100644 index 547c370f2bc50..0000000000000 --- a/src/wp-includes/blocks/code/block.json +++ /dev/null @@ -1,66 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/code", - "title": "Code", - "category": "text", - "description": "Display code snippets that respect your spacing and tabs.", - "textdomain": "default", - "attributes": { - "content": { - "type": "rich-text", - "source": "rich-text", - "selector": "code", - "__unstablePreserveWhiteSpace": true, - "role": "content" - } - }, - "supports": { - "align": [ "wide" ], - "anchor": true, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "spacing": { - "margin": [ "top", "bottom" ], - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "width": true, - "color": true - } - }, - "color": { - "text": true, - "background": true, - "gradients": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "style": "wp-block-code" -} diff --git a/src/wp-includes/blocks/column/block.json b/src/wp-includes/blocks/column/block.json deleted file mode 100644 index e842baac05dcf..0000000000000 --- a/src/wp-includes/blocks/column/block.json +++ /dev/null @@ -1,77 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/column", - "title": "Column", - "category": "design", - "parent": [ "core/columns" ], - "description": "A single column within a columns block.", - "textdomain": "default", - "attributes": { - "verticalAlignment": { - "type": "string" - }, - "width": { - "type": "string" - }, - "templateLock": { - "type": [ "string", "boolean" ], - "enum": [ "all", "insert", "contentOnly", false ] - } - }, - "supports": { - "__experimentalOnEnter": true, - "anchor": true, - "reusable": false, - "html": false, - "color": { - "gradients": true, - "heading": true, - "button": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "shadow": true, - "spacing": { - "blockGap": true, - "padding": true, - "__experimentalDefaultControls": { - "padding": true, - "blockGap": true - } - }, - "__experimentalBorder": { - "color": true, - "radius": true, - "style": true, - "width": true, - "__experimentalDefaultControls": { - "color": true, - "radius": true, - "style": true, - "width": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "layout": true, - "interactivity": { - "clientNavigation": true - }, - "allowedBlocks": true - } -} diff --git a/src/wp-includes/blocks/columns/block.json b/src/wp-includes/blocks/columns/block.json deleted file mode 100644 index 6d49a27e82eb0..0000000000000 --- a/src/wp-includes/blocks/columns/block.json +++ /dev/null @@ -1,90 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/columns", - "title": "Columns", - "category": "design", - "allowedBlocks": [ "core/column" ], - "description": "Display content in multiple columns, with blocks added to each column.", - "textdomain": "default", - "attributes": { - "verticalAlignment": { - "type": "string" - }, - "isStackedOnMobile": { - "type": "boolean", - "default": true - }, - "templateLock": { - "type": [ "string", "boolean" ], - "enum": [ "all", "insert", "contentOnly", false ] - } - }, - "supports": { - "anchor": true, - "align": [ "wide", "full" ], - "html": false, - "color": { - "gradients": true, - "link": true, - "heading": true, - "button": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "spacing": { - "blockGap": { - "__experimentalDefault": "2em", - "sides": [ "horizontal", "vertical" ] - }, - "margin": [ "top", "bottom" ], - "padding": true, - "__experimentalDefaultControls": { - "padding": true, - "blockGap": true - } - }, - "layout": { - "allowSwitching": false, - "allowInheriting": false, - "allowEditing": false, - "default": { - "type": "flex", - "flexWrap": "nowrap" - } - }, - "__experimentalBorder": { - "color": true, - "radius": true, - "style": true, - "width": true, - "__experimentalDefaultControls": { - "color": true, - "radius": true, - "style": true, - "width": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "shadow": true - }, - "editorStyle": "wp-block-columns-editor", - "style": "wp-block-columns" -} diff --git a/src/wp-includes/blocks/comment-author-name.php b/src/wp-includes/blocks/comment-author-name.php deleted file mode 100644 index 2f9227964ad44..0000000000000 --- a/src/wp-includes/blocks/comment-author-name.php +++ /dev/null @@ -1,69 +0,0 @@ -context['commentId'] ) ) { - return ''; - } - - $comment = get_comment( $block->context['commentId'] ); - $commenter = wp_get_current_commenter(); - $show_pending_links = isset( $commenter['comment_author'] ) && $commenter['comment_author']; - if ( empty( $comment ) ) { - return ''; - } - - $classes = array(); - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - $comment_author = get_comment_author( $comment ); - $link = get_comment_author_url( $comment ); - - if ( ! empty( $link ) && ! empty( $attributes['isLink'] ) && ! empty( $attributes['linkTarget'] ) ) { - $comment_author = sprintf( '%3s', esc_url( $link ), esc_attr( $attributes['linkTarget'] ), $comment_author ); - } - if ( '0' === $comment->comment_approved && ! $show_pending_links ) { - $comment_author = wp_kses( $comment_author, array() ); - } - - return sprintf( - '
%2$s
', - $wrapper_attributes, - $comment_author - ); -} - -/** - * Registers the `core/comment-author-name` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_comment_author_name() { - register_block_type_from_metadata( - __DIR__ . '/comment-author-name', - array( - 'render_callback' => 'render_block_core_comment_author_name', - ) - ); -} -add_action( 'init', 'register_block_core_comment_author_name' ); diff --git a/src/wp-includes/blocks/comment-author-name/block.json b/src/wp-includes/blocks/comment-author-name/block.json deleted file mode 100644 index 1889d054c940e..0000000000000 --- a/src/wp-includes/blocks/comment-author-name/block.json +++ /dev/null @@ -1,69 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/comment-author-name", - "title": "Comment Author Name", - "category": "theme", - "ancestor": [ "core/comment-template" ], - "description": "Displays the name of the author of the comment.", - "textdomain": "default", - "attributes": { - "isLink": { - "type": "boolean", - "default": true - }, - "linkTarget": { - "type": "string", - "default": "_self" - }, - "textAlign": { - "type": "string" - } - }, - "usesContext": [ "commentId" ], - "supports": { - "html": false, - "spacing": { - "margin": true, - "padding": true - }, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "style": "wp-block-comment-author-name" -} diff --git a/src/wp-includes/blocks/comment-content.php b/src/wp-includes/blocks/comment-content.php deleted file mode 100644 index 3f7f5e1f4083b..0000000000000 --- a/src/wp-includes/blocks/comment-content.php +++ /dev/null @@ -1,85 +0,0 @@ -context['commentId'] ) ) { - return ''; - } - - $comment = get_comment( $block->context['commentId'] ); - $commenter = wp_get_current_commenter(); - $show_pending_links = isset( $commenter['comment_author'] ) && $commenter['comment_author']; - if ( empty( $comment ) ) { - return ''; - } - - $args = array(); - $comment_text = get_comment_text( $comment, $args ); - if ( ! $comment_text ) { - return ''; - } - - /** This filter is documented in wp-includes/comment-template.php */ - $comment_text = apply_filters( 'comment_text', $comment_text, $comment, $args ); - - $moderation_note = ''; - if ( '0' === $comment->comment_approved ) { - $commenter = wp_get_current_commenter(); - - if ( $commenter['comment_author_email'] ) { - $moderation_note = __( 'Your comment is awaiting moderation.' ); - } else { - $moderation_note = __( 'Your comment is awaiting moderation. This is a preview; your comment will be visible after it has been approved.' ); - } - $moderation_note = '

' . $moderation_note . '

'; - if ( ! $show_pending_links ) { - $comment_text = wp_kses( $comment_text, array() ); - } - } - - $classes = array(); - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - - return sprintf( - '
%2$s%3$s
', - $wrapper_attributes, - $moderation_note, - $comment_text - ); -} - -/** - * Registers the `core/comment-content` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_comment_content() { - register_block_type_from_metadata( - __DIR__ . '/comment-content', - array( - 'render_callback' => 'render_block_core_comment_content', - ) - ); -} -add_action( 'init', 'register_block_core_comment_content' ); diff --git a/src/wp-includes/blocks/comment-content/block.json b/src/wp-includes/blocks/comment-content/block.json deleted file mode 100644 index 0e812299a45e8..0000000000000 --- a/src/wp-includes/blocks/comment-content/block.json +++ /dev/null @@ -1,59 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/comment-content", - "title": "Comment Content", - "category": "theme", - "ancestor": [ "core/comment-template" ], - "description": "Displays the contents of a comment.", - "textdomain": "default", - "usesContext": [ "commentId" ], - "attributes": { - "textAlign": { - "type": "string" - } - }, - "supports": { - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - }, - "spacing": { - "padding": [ "horizontal", "vertical" ], - "__experimentalDefaultControls": { - "padding": true - } - }, - "html": false - }, - "style": "wp-block-comment-content" -} diff --git a/src/wp-includes/blocks/comment-date.php b/src/wp-includes/blocks/comment-date.php deleted file mode 100644 index bdb6fd5ba42ae..0000000000000 --- a/src/wp-includes/blocks/comment-date.php +++ /dev/null @@ -1,64 +0,0 @@ -context['commentId'] ) ) { - return ''; - } - - $comment = get_comment( $block->context['commentId'] ); - if ( empty( $comment ) ) { - return ''; - } - - $classes = ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) ? 'has-link-color' : ''; - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => $classes ) ); - if ( isset( $attributes['format'] ) && 'human-diff' === $attributes['format'] ) { - // translators: %s: human-readable time difference. - $formatted_date = sprintf( __( '%s ago' ), human_time_diff( get_comment_date( 'U', $comment ) ) ); - } else { - $formatted_date = get_comment_date( empty( $attributes['format'] ) ? '' : $attributes['format'], $comment ); - } - $link = get_comment_link( $comment ); - - if ( ! empty( $attributes['isLink'] ) ) { - $formatted_date = sprintf( '%2s', esc_url( $link ), $formatted_date ); - } - - return sprintf( - '
', - $wrapper_attributes, - esc_attr( get_comment_date( 'c', $comment ) ), - $formatted_date - ); -} - -/** - * Registers the `core/comment-date` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_comment_date() { - register_block_type_from_metadata( - __DIR__ . '/comment-date', - array( - 'render_callback' => 'render_block_core_comment_date', - ) - ); -} -add_action( 'init', 'register_block_core_comment_date' ); diff --git a/src/wp-includes/blocks/comment-date/block.json b/src/wp-includes/blocks/comment-date/block.json deleted file mode 100644 index 1e8110f836d93..0000000000000 --- a/src/wp-includes/blocks/comment-date/block.json +++ /dev/null @@ -1,65 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/comment-date", - "title": "Comment Date", - "category": "theme", - "ancestor": [ "core/comment-template" ], - "description": "Displays the date on which the comment was posted.", - "textdomain": "default", - "attributes": { - "format": { - "type": "string" - }, - "isLink": { - "type": "boolean", - "default": true - } - }, - "usesContext": [ "commentId" ], - "supports": { - "html": false, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "style": "wp-block-comment-date" -} diff --git a/src/wp-includes/blocks/comment-edit-link.php b/src/wp-includes/blocks/comment-edit-link.php deleted file mode 100644 index 53eaf9a2cda6c..0000000000000 --- a/src/wp-includes/blocks/comment-edit-link.php +++ /dev/null @@ -1,65 +0,0 @@ -context['commentId'] ) || ! current_user_can( 'edit_comment', $block->context['commentId'] ) ) { - return ''; - } - - $edit_comment_link = get_edit_comment_link( $block->context['commentId'] ); - - $link_atts = ''; - - if ( ! empty( $attributes['linkTarget'] ) ) { - $link_atts .= sprintf( 'target="%s"', esc_attr( $attributes['linkTarget'] ) ); - } - - $classes = array(); - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - - return sprintf( - '
%4$s
', - $wrapper_attributes, - esc_url( $edit_comment_link ), - $link_atts, - esc_html__( 'Edit' ) - ); -} - -/** - * Registers the `core/comment-edit-link` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_comment_edit_link() { - register_block_type_from_metadata( - __DIR__ . '/comment-edit-link', - array( - 'render_callback' => 'render_block_core_comment_edit_link', - ) - ); -} - -add_action( 'init', 'register_block_core_comment_edit_link' ); diff --git a/src/wp-includes/blocks/comment-edit-link/block.json b/src/wp-includes/blocks/comment-edit-link/block.json deleted file mode 100644 index 578b284715c2a..0000000000000 --- a/src/wp-includes/blocks/comment-edit-link/block.json +++ /dev/null @@ -1,63 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/comment-edit-link", - "title": "Comment Edit Link", - "category": "theme", - "ancestor": [ "core/comment-template" ], - "description": "Displays a link to edit the comment in the WordPress Dashboard. This link is only visible to users with the edit comment capability.", - "textdomain": "default", - "usesContext": [ "commentId" ], - "attributes": { - "linkTarget": { - "type": "string", - "default": "_self" - }, - "textAlign": { - "type": "string" - } - }, - "supports": { - "html": false, - "color": { - "link": true, - "gradients": true, - "text": false, - "__experimentalDefaultControls": { - "background": true, - "link": true - } - }, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true - } - }, - "style": "wp-block-comment-edit-link" -} diff --git a/src/wp-includes/blocks/comment-reply-link.php b/src/wp-includes/blocks/comment-reply-link.php deleted file mode 100644 index 7121b6f25a195..0000000000000 --- a/src/wp-includes/blocks/comment-reply-link.php +++ /dev/null @@ -1,87 +0,0 @@ -context['commentId'] ) ) { - return ''; - } - - $thread_comments = get_option( 'thread_comments' ); - if ( ! $thread_comments ) { - return ''; - } - - $comment = get_comment( $block->context['commentId'] ); - if ( empty( $comment ) ) { - return ''; - } - - $depth = 1; - $max_depth = get_option( 'thread_comments_depth' ); - $parent_id = $comment->comment_parent; - - // Compute comment's depth iterating over its ancestors. - while ( ! empty( $parent_id ) ) { - ++$depth; - $parent_id = get_comment( $parent_id )->comment_parent; - } - - $comment_reply_link = get_comment_reply_link( - array( - 'depth' => $depth, - 'max_depth' => $max_depth, - ), - $comment - ); - - // Render nothing if the generated reply link is empty. - if ( empty( $comment_reply_link ) ) { - return; - } - - $classes = array(); - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - - return sprintf( - '
%2$s
', - $wrapper_attributes, - $comment_reply_link - ); -} - -/** - * Registers the `core/comment-reply-link` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_comment_reply_link() { - register_block_type_from_metadata( - __DIR__ . '/comment-reply-link', - array( - 'render_callback' => 'render_block_core_comment_reply_link', - ) - ); -} - -add_action( 'init', 'register_block_core_comment_reply_link' ); diff --git a/src/wp-includes/blocks/comment-reply-link/block.json b/src/wp-includes/blocks/comment-reply-link/block.json deleted file mode 100644 index 68aa93c3c1526..0000000000000 --- a/src/wp-includes/blocks/comment-reply-link/block.json +++ /dev/null @@ -1,56 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/comment-reply-link", - "title": "Comment Reply Link", - "category": "theme", - "ancestor": [ "core/comment-template" ], - "description": "Displays a link to reply to a comment.", - "textdomain": "default", - "usesContext": [ "commentId" ], - "attributes": { - "textAlign": { - "type": "string" - } - }, - "supports": { - "color": { - "gradients": true, - "link": true, - "text": false, - "__experimentalDefaultControls": { - "background": true, - "link": true - } - }, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true - }, - "html": false - }, - "style": "wp-block-comment-reply-link" -} diff --git a/src/wp-includes/blocks/comment-template.php b/src/wp-includes/blocks/comment-template.php deleted file mode 100644 index ec462e6a050de..0000000000000 --- a/src/wp-includes/blocks/comment-template.php +++ /dev/null @@ -1,153 +0,0 @@ -comment_ID; - $filter_block_context = static function ( $context ) use ( $comment_id ) { - $context['commentId'] = $comment_id; - return $context; - }; - - /* - * We set commentId context through the `render_block_context` filter so - * that dynamically inserted blocks (at `render_block` filter stage) - * will also receive that context. - * - * Use an early priority to so that other 'render_block_context' filters - * have access to the values. - */ - add_filter( 'render_block_context', $filter_block_context, 1 ); - - /* - * We construct a new WP_Block instance from the parsed block so that - * it'll receive any changes made by the `render_block_data` filter. - */ - $block_content = ( new WP_Block( $block->parsed_block ) )->render( array( 'dynamic' => false ) ); - - remove_filter( 'render_block_context', $filter_block_context, 1 ); - - $children = $comment->get_children(); - - /* - * We need to create the CSS classes BEFORE recursing into the children. - * This is because comment_class() uses globals like `$comment_alt` - * and `$comment_thread_alt` which are order-sensitive. - * - * The `false` parameter at the end means that we do NOT want the function - * to `echo` the output but to return a string. - * See https://developer.wordpress.org/reference/functions/comment_class/#parameters. - */ - $comment_classes = comment_class( '', $comment->comment_ID, $comment->comment_post_ID, false ); - - // If the comment has children, recurse to create the HTML for the nested - // comments. - if ( ! empty( $children ) && ! empty( $thread_comments ) ) { - if ( $comment_depth < $thread_comments_depth ) { - ++$comment_depth; - $inner_content = block_core_comment_template_render_comments( - $children, - $block - ); - $block_content .= sprintf( '
    %1$s
', $inner_content ); - --$comment_depth; - } else { - $block_content .= block_core_comment_template_render_comments( - $children, - $block - ); - } - } - - $content .= sprintf( '
  • %3$s
  • ', $comment->comment_ID, $comment_classes, $block_content ); - } - - return $content; -} - -/** - * Renders the `core/comment-template` block on the server. - * - * @since 6.0.0 - * - * @param array $attributes Block attributes. - * @param string $content Block default content. - * @param WP_Block $block Block instance. - * - * @return string Returns the HTML representing the comments using the layout - * defined by the block's inner blocks. - */ -function render_block_core_comment_template( $attributes, $content, $block ) { - // Bail out early if the post ID is not set for some reason. - if ( empty( $block->context['postId'] ) ) { - return ''; - } - - if ( post_password_required( $block->context['postId'] ) ) { - return; - } - - $comment_query = new WP_Comment_Query( - build_comment_query_vars_from_block( $block ) - ); - - // Get an array of comments for the current post. - $comments = $comment_query->get_comments(); - if ( count( $comments ) === 0 ) { - return ''; - } - - $comment_order = get_option( 'comment_order' ); - - if ( 'desc' === $comment_order ) { - $comments = array_reverse( $comments ); - } - - $wrapper_attributes = get_block_wrapper_attributes(); - - return sprintf( - '
      %2$s
    ', - $wrapper_attributes, - block_core_comment_template_render_comments( $comments, $block ) - ); -} - -/** - * Registers the `core/comment-template` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_comment_template() { - register_block_type_from_metadata( - __DIR__ . '/comment-template', - array( - 'render_callback' => 'render_block_core_comment_template', - 'skip_inner_blocks' => true, - ) - ); -} -add_action( 'init', 'register_block_core_comment_template' ); diff --git a/src/wp-includes/blocks/comment-template/block.json b/src/wp-includes/blocks/comment-template/block.json deleted file mode 100644 index 08fd591b42409..0000000000000 --- a/src/wp-includes/blocks/comment-template/block.json +++ /dev/null @@ -1,49 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/comment-template", - "title": "Comment Template", - "category": "design", - "parent": [ "core/comments" ], - "description": "Contains the block elements used to display a comment, like the title, date, author, avatar and more.", - "textdomain": "default", - "usesContext": [ "postId" ], - "supports": { - "align": true, - "html": false, - "reusable": false, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "style": "wp-block-comment-template" -} diff --git a/src/wp-includes/blocks/comments-pagination-next.php b/src/wp-includes/blocks/comments-pagination-next.php deleted file mode 100644 index 0fd9519a56d30..0000000000000 --- a/src/wp-includes/blocks/comments-pagination-next.php +++ /dev/null @@ -1,64 +0,0 @@ -context['postId'] ) ) { - return ''; - } - - $comment_vars = build_comment_query_vars_from_block( $block ); - $max_page = ( new WP_Comment_Query( $comment_vars ) )->max_num_pages; - $default_label = __( 'Newer Comments' ); - $label = isset( $attributes['label'] ) && ! empty( $attributes['label'] ) ? $attributes['label'] : $default_label; - $pagination_arrow = get_comments_pagination_arrow( $block, 'next' ); - - $filter_link_attributes = static function () { - return get_block_wrapper_attributes(); - }; - add_filter( 'next_comments_link_attributes', $filter_link_attributes ); - - if ( $pagination_arrow ) { - $label .= $pagination_arrow; - } - - $next_comments_link = get_next_comments_link( $label, $max_page, $comment_vars['paged'] ?? null ); - - remove_filter( 'next_posts_link_attributes', $filter_link_attributes ); - - if ( ! isset( $next_comments_link ) ) { - return ''; - } - return $next_comments_link; -} - - -/** - * Registers the `core/comments-pagination-next` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_comments_pagination_next() { - register_block_type_from_metadata( - __DIR__ . '/comments-pagination-next', - array( - 'render_callback' => 'render_block_core_comments_pagination_next', - ) - ); -} -add_action( 'init', 'register_block_core_comments_pagination_next' ); diff --git a/src/wp-includes/blocks/comments-pagination-next/block.json b/src/wp-includes/blocks/comments-pagination-next/block.json deleted file mode 100644 index 22e20bfa8dbf2..0000000000000 --- a/src/wp-includes/blocks/comments-pagination-next/block.json +++ /dev/null @@ -1,43 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/comments-pagination-next", - "title": "Comments Next Page", - "category": "theme", - "parent": [ "core/comments-pagination" ], - "description": "Displays the next comment's page link.", - "textdomain": "default", - "attributes": { - "label": { - "type": "string" - } - }, - "usesContext": [ "postId", "comments/paginationArrow" ], - "supports": { - "reusable": false, - "html": false, - "color": { - "gradients": true, - "text": false, - "__experimentalDefaultControls": { - "background": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - } -} diff --git a/src/wp-includes/blocks/comments-pagination-numbers.php b/src/wp-includes/blocks/comments-pagination-numbers.php deleted file mode 100644 index 093a6450930f1..0000000000000 --- a/src/wp-includes/blocks/comments-pagination-numbers.php +++ /dev/null @@ -1,66 +0,0 @@ -context['postId'] ) ) { - return ''; - } - - $comment_vars = build_comment_query_vars_from_block( $block ); - - $total = ( new WP_Comment_Query( $comment_vars ) )->max_num_pages; - $current = ! empty( $comment_vars['paged'] ) ? $comment_vars['paged'] : null; - - // Render links. - $content = paginate_comments_links( - array( - 'total' => $total, - 'current' => $current, - 'prev_next' => false, - 'echo' => false, - ) - ); - - if ( empty( $content ) ) { - return ''; - } - - $wrapper_attributes = get_block_wrapper_attributes(); - - return sprintf( - '
    %2$s
    ', - $wrapper_attributes, - $content - ); -} - -/** - * Registers the `core/comments-pagination-numbers` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_comments_pagination_numbers() { - register_block_type_from_metadata( - __DIR__ . '/comments-pagination-numbers', - array( - 'render_callback' => 'render_block_core_comments_pagination_numbers', - ) - ); -} -add_action( 'init', 'register_block_core_comments_pagination_numbers' ); diff --git a/src/wp-includes/blocks/comments-pagination-numbers/block.json b/src/wp-includes/blocks/comments-pagination-numbers/block.json deleted file mode 100644 index 9e9017af63197..0000000000000 --- a/src/wp-includes/blocks/comments-pagination-numbers/block.json +++ /dev/null @@ -1,38 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/comments-pagination-numbers", - "title": "Comments Page Numbers", - "category": "theme", - "parent": [ "core/comments-pagination" ], - "description": "Displays a list of page numbers for comments pagination.", - "textdomain": "default", - "usesContext": [ "postId" ], - "supports": { - "reusable": false, - "html": false, - "color": { - "gradients": true, - "text": false, - "__experimentalDefaultControls": { - "background": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - } -} diff --git a/src/wp-includes/blocks/comments-pagination-previous.php b/src/wp-includes/blocks/comments-pagination-previous.php deleted file mode 100644 index ba9bef97ad34d..0000000000000 --- a/src/wp-includes/blocks/comments-pagination-previous.php +++ /dev/null @@ -1,57 +0,0 @@ - 'render_block_core_comments_pagination_previous', - ) - ); -} -add_action( 'init', 'register_block_core_comments_pagination_previous' ); diff --git a/src/wp-includes/blocks/comments-pagination-previous/block.json b/src/wp-includes/blocks/comments-pagination-previous/block.json deleted file mode 100644 index 0871b000c569d..0000000000000 --- a/src/wp-includes/blocks/comments-pagination-previous/block.json +++ /dev/null @@ -1,43 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/comments-pagination-previous", - "title": "Comments Previous Page", - "category": "theme", - "parent": [ "core/comments-pagination" ], - "description": "Displays the previous comment's page link.", - "textdomain": "default", - "attributes": { - "label": { - "type": "string" - } - }, - "usesContext": [ "postId", "comments/paginationArrow" ], - "supports": { - "reusable": false, - "html": false, - "color": { - "gradients": true, - "text": false, - "__experimentalDefaultControls": { - "background": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - } -} diff --git a/src/wp-includes/blocks/comments-pagination.php b/src/wp-includes/blocks/comments-pagination.php deleted file mode 100644 index e42a9a760fc41..0000000000000 --- a/src/wp-includes/blocks/comments-pagination.php +++ /dev/null @@ -1,55 +0,0 @@ - __( 'Comments pagination' ), - 'class' => $classes, - ) - ); - - return sprintf( - '', - $wrapper_attributes, - $content - ); -} - -/** - * Registers the `core/comments-pagination` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_comments_pagination() { - register_block_type_from_metadata( - __DIR__ . '/comments-pagination', - array( - 'render_callback' => 'render_block_core_comments_pagination', - ) - ); -} -add_action( 'init', 'register_block_core_comments_pagination' ); diff --git a/src/wp-includes/blocks/comments-pagination/block.json b/src/wp-includes/blocks/comments-pagination/block.json deleted file mode 100644 index b29d95bc4f1c9..0000000000000 --- a/src/wp-includes/blocks/comments-pagination/block.json +++ /dev/null @@ -1,68 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/comments-pagination", - "title": "Comments Pagination", - "category": "theme", - "parent": [ "core/comments" ], - "allowedBlocks": [ - "core/comments-pagination-previous", - "core/comments-pagination-numbers", - "core/comments-pagination-next" - ], - "description": "Displays a paginated navigation to next/previous set of comments, when applicable.", - "textdomain": "default", - "attributes": { - "paginationArrow": { - "type": "string", - "default": "none" - } - }, - "example": { - "attributes": { - "paginationArrow": "none" - } - }, - "providesContext": { - "comments/paginationArrow": "paginationArrow" - }, - "supports": { - "align": true, - "reusable": false, - "html": false, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "layout": { - "allowSwitching": false, - "allowInheriting": false, - "default": { - "type": "flex" - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-comments-pagination-editor", - "style": "wp-block-comments-pagination" -} diff --git a/src/wp-includes/blocks/comments-title.php b/src/wp-includes/blocks/comments-title.php deleted file mode 100644 index 130132ec3fa52..0000000000000 --- a/src/wp-includes/blocks/comments-title.php +++ /dev/null @@ -1,101 +0,0 @@ - $align_class_name ) ); - $comments_count = get_comments_number(); - /* translators: %s: Post title. */ - $post_title = sprintf( __( '“%s”' ), get_the_title() ); - $tag_name = 'h2'; - if ( isset( $attributes['level'] ) ) { - $tag_name = 'h' . $attributes['level']; - } - - if ( '0' === $comments_count ) { - return; - } - - if ( $show_comments_count ) { - if ( $show_post_title ) { - if ( '1' === $comments_count ) { - /* translators: %s: Post title. */ - $comments_title = sprintf( __( 'One response to %s' ), $post_title ); - } else { - $comments_title = sprintf( - /* translators: 1: Number of comments, 2: Post title. */ - _n( - '%1$s response to %2$s', - '%1$s responses to %2$s', - $comments_count - ), - number_format_i18n( $comments_count ), - $post_title - ); - } - } elseif ( '1' === $comments_count ) { - $comments_title = __( 'One response' ); - } else { - $comments_title = sprintf( - /* translators: %s: Number of comments. */ - _n( '%s response', '%s responses', $comments_count ), - number_format_i18n( $comments_count ) - ); - } - } elseif ( $show_post_title ) { - if ( '1' === $comments_count ) { - /* translators: %s: Post title. */ - $comments_title = sprintf( __( 'Response to %s' ), $post_title ); - } else { - /* translators: %s: Post title. */ - $comments_title = sprintf( __( 'Responses to %s' ), $post_title ); - } - } elseif ( '1' === $comments_count ) { - $comments_title = __( 'Response' ); - } else { - $comments_title = __( 'Responses' ); - } - - return sprintf( - '<%1$s id="comments" %2$s>%3$s', - $tag_name, - $wrapper_attributes, - $comments_title - ); -} - -/** - * Registers the `core/comments-title` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_comments_title() { - register_block_type_from_metadata( - __DIR__ . '/comments-title', - array( - 'render_callback' => 'render_block_core_comments_title', - ) - ); -} - -add_action( 'init', 'register_block_core_comments_title' ); diff --git a/src/wp-includes/blocks/comments-title/block.json b/src/wp-includes/blocks/comments-title/block.json deleted file mode 100644 index b66b741e1916a..0000000000000 --- a/src/wp-includes/blocks/comments-title/block.json +++ /dev/null @@ -1,72 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/comments-title", - "title": "Comments Title", - "category": "theme", - "ancestor": [ "core/comments" ], - "description": "Displays a title with the number of comments.", - "textdomain": "default", - "usesContext": [ "postId", "postType" ], - "attributes": { - "textAlign": { - "type": "string" - }, - "showPostTitle": { - "type": "boolean", - "default": true - }, - "showCommentsCount": { - "type": "boolean", - "default": true - }, - "level": { - "type": "number", - "default": 2 - }, - "levelOptions": { - "type": "array" - } - }, - "supports": { - "anchor": false, - "align": true, - "html": false, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true - }, - "color": { - "gradients": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true, - "__experimentalFontFamily": true, - "__experimentalFontStyle": true, - "__experimentalFontWeight": true - } - }, - "interactivity": { - "clientNavigation": true - } - } -} diff --git a/src/wp-includes/blocks/comments.php b/src/wp-includes/blocks/comments.php deleted file mode 100644 index cb80352edca8e..0000000000000 --- a/src/wp-includes/blocks/comments.php +++ /dev/null @@ -1,227 +0,0 @@ -context['postId'] ) ) { - return ''; - } - - $post_id = $block->context['postId']; - // Return early if there are no comments and comments are closed. - if ( ! comments_open( $post_id ) && (int) get_comments_number( $post_id ) === 0 ) { - return ''; - } - - // If this isn't the legacy block, we need to render the static version of this block. - $is_legacy = 'core/post-comments' === $block->name || ! empty( $attributes['legacy'] ); - if ( ! $is_legacy ) { - return $block->render( array( 'dynamic' => false ) ); - } - - $post_before = $post; - $post = get_post( $post_id ); - setup_postdata( $post ); - - ob_start(); - - /* - * There's a deprecation warning generated by WP Core. - * Ideally this deprecation is removed from Core. - * In the meantime, this removes it from the output. - */ - add_filter( 'deprecated_file_trigger_error', '__return_false' ); - comments_template(); - remove_filter( 'deprecated_file_trigger_error', '__return_false' ); - - $output = ob_get_clean(); - $post = $post_before; - - $classnames = array(); - // Adds the old class name for styles' backwards compatibility. - if ( isset( $attributes['legacy'] ) ) { - $classnames[] = 'wp-block-post-comments'; - } - if ( isset( $attributes['textAlign'] ) ) { - $classnames[] = 'has-text-align-' . $attributes['textAlign']; - } - - $wrapper_attributes = get_block_wrapper_attributes( - array( 'class' => implode( ' ', $classnames ) ) - ); - - /* - * Enqueues scripts and styles required only for the legacy version. That is - * why they are not defined in `block.json`. - */ - wp_enqueue_script( 'comment-reply' ); - enqueue_legacy_post_comments_block_styles( $block->name ); - - return sprintf( '
    %2$s
    ', $wrapper_attributes, $output ); -} - -/** - * Registers the `core/comments` block on the server. - * - * @since 6.1.0 - */ -function register_block_core_comments() { - register_block_type_from_metadata( - __DIR__ . '/comments', - array( - 'render_callback' => 'render_block_core_comments', - 'skip_inner_blocks' => true, - ) - ); -} -add_action( 'init', 'register_block_core_comments' ); - -/** - * Use the button block classes for the form-submit button. - * - * @since 6.1.0 - * - * @param array $fields The default comment form arguments. - * - * @return array Returns the modified fields. - */ -function comments_block_form_defaults( $fields ) { - if ( wp_is_block_theme() ) { - $fields['submit_button'] = ''; - $fields['submit_field'] = '

    %1$s %2$s

    '; - } - - return $fields; -} -add_filter( 'comment_form_defaults', 'comments_block_form_defaults' ); - -/** - * Enqueues styles from the legacy `core/post-comments` block. These styles are - * required only by the block's fallback. - * - * @since 6.1.0 - * - * @param string $block_name Name of the new block type. - */ -function enqueue_legacy_post_comments_block_styles( $block_name ) { - static $are_styles_enqueued = false; - - if ( ! $are_styles_enqueued ) { - $handles = array( - 'wp-block-post-comments', - 'wp-block-buttons', - 'wp-block-button', - ); - foreach ( $handles as $handle ) { - wp_enqueue_block_style( $block_name, array( 'handle' => $handle ) ); - } - $are_styles_enqueued = true; - } -} - -/** - * Ensures backwards compatibility for any users running the Gutenberg plugin - * who have used Post Comments before it was merged into Comments Query Loop. - * - * The same approach was followed when core/query-loop was renamed to - * core/post-template. - * - * @since 6.1.0 - * - * @see https://github.com/WordPress/gutenberg/pull/41807 - * @see https://github.com/WordPress/gutenberg/pull/32514 - */ -function register_legacy_post_comments_block() { - $registry = WP_Block_Type_Registry::get_instance(); - - /* - * Remove the old `post-comments` block if it was already registered, as it - * is about to be replaced by the type defined below. - */ - if ( $registry->is_registered( 'core/post-comments' ) ) { - unregister_block_type( 'core/post-comments' ); - } - - // Recreate the legacy block metadata. - $metadata = array( - 'name' => 'core/post-comments', - 'category' => 'theme', - 'attributes' => array( - 'textAlign' => array( - 'type' => 'string', - ), - ), - 'uses_context' => array( - 'postId', - 'postType', - ), - 'supports' => array( - 'html' => false, - 'align' => array( 'wide', 'full' ), - 'typography' => array( - 'fontSize' => true, - 'lineHeight' => true, - '__experimentalFontStyle' => true, - '__experimentalFontWeight' => true, - '__experimentalLetterSpacing' => true, - '__experimentalTextTransform' => true, - '__experimentalDefaultControls' => array( - 'fontSize' => true, - ), - ), - 'color' => array( - 'gradients' => true, - 'link' => true, - '__experimentalDefaultControls' => array( - 'background' => true, - 'text' => true, - ), - ), - 'inserter' => false, - ), - 'style' => array( - 'wp-block-post-comments', - 'wp-block-buttons', - 'wp-block-button', - ), - 'render_callback' => 'render_block_core_comments', - 'skip_inner_blocks' => true, - ); - - /* - * Filters the metadata object, the same way it's done inside - * `register_block_type_from_metadata()`. This applies some default filters, - * like `_wp_multiple_block_styles`, which is required in this case because - * the block has multiple styles. - */ - /** This filter is documented in wp-includes/blocks.php */ - $metadata = apply_filters( 'block_type_metadata', $metadata ); - - register_block_type( 'core/post-comments', $metadata ); -} -add_action( 'init', 'register_legacy_post_comments_block', 21 ); diff --git a/src/wp-includes/blocks/comments/block.json b/src/wp-includes/blocks/comments/block.json deleted file mode 100644 index ceb8f750c3472..0000000000000 --- a/src/wp-includes/blocks/comments/block.json +++ /dev/null @@ -1,64 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/comments", - "title": "Comments", - "category": "theme", - "description": "An advanced block that allows displaying post comments using different visual configurations.", - "textdomain": "default", - "attributes": { - "tagName": { - "type": "string", - "default": "div" - }, - "legacy": { - "type": "boolean", - "default": false - } - }, - "supports": { - "align": [ "wide", "full" ], - "html": false, - "color": { - "gradients": true, - "heading": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "editorStyle": "wp-block-comments-editor", - "usesContext": [ "postId", "postType" ] -} diff --git a/src/wp-includes/blocks/cover.php b/src/wp-includes/blocks/cover.php deleted file mode 100644 index 630835a47947b..0000000000000 --- a/src/wp-includes/blocks/cover.php +++ /dev/null @@ -1,101 +0,0 @@ - 'wp-block-cover__image-background', - 'data-object-fit' => 'cover', - ); - - if ( $object_position ) { - $attr['data-object-position'] = $object_position; - $attr['style'] = 'object-position:' . $object_position . ';'; - } - - $image = get_the_post_thumbnail( null, $attributes['sizeSlug'] ?? 'post-thumbnail', $attr ); - } else { - if ( in_the_loop() ) { - update_post_thumbnail_cache(); - } - $current_featured_image = get_the_post_thumbnail_url( null, $attributes['sizeSlug'] ?? null ); - if ( ! $current_featured_image ) { - return $content; - } - - $current_thumbnail_id = get_post_thumbnail_id(); - - $processor = new WP_HTML_Tag_Processor( '
    ' ); - $processor->next_tag(); - - $current_alt = trim( strip_tags( get_post_meta( $current_thumbnail_id, '_wp_attachment_image_alt', true ) ) ); - if ( $current_alt ) { - $processor->set_attribute( 'role', 'img' ); - $processor->set_attribute( 'aria-label', $current_alt ); - } - - $processor->add_class( 'wp-block-cover__image-background' ); - $processor->add_class( 'wp-image-' . $current_thumbnail_id ); - if ( $attributes['hasParallax'] ) { - $processor->add_class( 'has-parallax' ); - } - if ( $attributes['isRepeated'] ) { - $processor->add_class( 'is-repeated' ); - } - - $styles = 'background-position:' . ( $object_position ?? '50% 50%' ) . ';'; - $styles .= 'background-image:url(' . esc_url( $current_featured_image ) . ');'; - $processor->set_attribute( 'style', $styles ); - - $image = $processor->get_updated_html(); - } - - /* - * Inserts the featured image between the (1st) cover 'background' `span` and 'inner_container' `div`, - * and removes eventual whitespace characters between the two (typically introduced at template level) - */ - $inner_container_start = '/]+wp-block-cover__inner-container[\s|"][^>]*>/U'; - if ( 1 === preg_match( $inner_container_start, $content, $matches, PREG_OFFSET_CAPTURE ) ) { - $offset = $matches[0][1]; - $content = substr( $content, 0, $offset ) . $image . substr( $content, $offset ); - } - - return $content; -} - -/** - * Registers the `core/cover` block renderer on server. - * - * @since 6.0.0 - */ -function register_block_core_cover() { - register_block_type_from_metadata( - __DIR__ . '/cover', - array( - 'render_callback' => 'render_block_core_cover', - ) - ); -} -add_action( 'init', 'register_block_core_cover' ); diff --git a/src/wp-includes/blocks/cover/block.json b/src/wp-includes/blocks/cover/block.json deleted file mode 100644 index 97095ab4b9515..0000000000000 --- a/src/wp-includes/blocks/cover/block.json +++ /dev/null @@ -1,158 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/cover", - "title": "Cover", - "category": "media", - "description": "Add an image or video with a text overlay.", - "textdomain": "default", - "attributes": { - "url": { - "type": "string", - "role": "content" - }, - "useFeaturedImage": { - "type": "boolean", - "default": false - }, - "id": { - "type": "number" - }, - "alt": { - "type": "string", - "default": "" - }, - "hasParallax": { - "type": "boolean", - "default": false - }, - "isRepeated": { - "type": "boolean", - "default": false - }, - "dimRatio": { - "type": "number", - "default": 100 - }, - "overlayColor": { - "type": "string" - }, - "customOverlayColor": { - "type": "string" - }, - "isUserOverlayColor": { - "type": "boolean" - }, - "backgroundType": { - "type": "string", - "default": "image" - }, - "focalPoint": { - "type": "object" - }, - "minHeight": { - "type": "number" - }, - "minHeightUnit": { - "type": "string" - }, - "gradient": { - "type": "string" - }, - "customGradient": { - "type": "string" - }, - "contentPosition": { - "type": "string" - }, - "isDark": { - "type": "boolean", - "default": true - }, - "templateLock": { - "type": [ "string", "boolean" ], - "enum": [ "all", "insert", "contentOnly", false ] - }, - "tagName": { - "type": "string", - "default": "div" - }, - "sizeSlug": { - "type": "string" - }, - "poster": { - "type": "string", - "source": "attribute", - "selector": "video", - "attribute": "poster" - } - }, - "usesContext": [ "postId", "postType" ], - "supports": { - "anchor": true, - "align": true, - "html": false, - "shadow": true, - "spacing": { - "padding": true, - "margin": [ "top", "bottom" ], - "blockGap": true, - "__experimentalDefaultControls": { - "padding": true, - "blockGap": true - } - }, - "__experimentalBorder": { - "color": true, - "radius": true, - "style": true, - "width": true, - "__experimentalDefaultControls": { - "color": true, - "radius": true, - "style": true, - "width": true - } - }, - "color": { - "heading": true, - "text": true, - "background": false, - "__experimentalSkipSerialization": [ "gradients" ], - "enableContrastChecker": false - }, - "dimensions": { - "aspectRatio": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "layout": { - "allowJustification": false - }, - "interactivity": { - "clientNavigation": true - }, - "filter": { - "duotone": true - }, - "allowedBlocks": true - }, - "selectors": { - "filter": { - "duotone": ".wp-block-cover > .wp-block-cover__image-background, .wp-block-cover > .wp-block-cover__video-background" - } - }, - "editorStyle": "wp-block-cover-editor", - "style": "wp-block-cover" -} diff --git a/src/wp-includes/blocks/details/block.json b/src/wp-includes/blocks/details/block.json deleted file mode 100644 index 7130700db2c88..0000000000000 --- a/src/wp-includes/blocks/details/block.json +++ /dev/null @@ -1,81 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/details", - "title": "Details", - "category": "text", - "description": "Hide and show additional content.", - "keywords": [ "summary", "toggle", "disclosure" ], - "textdomain": "default", - "attributes": { - "showContent": { - "type": "boolean", - "default": false - }, - "summary": { - "type": "rich-text", - "source": "rich-text", - "selector": "summary", - "role": "content" - }, - "name": { - "type": "string", - "source": "attribute", - "attribute": "name", - "selector": ".wp-block-details" - }, - "placeholder": { - "type": "string" - } - }, - "supports": { - "__experimentalOnEnter": true, - "align": [ "wide", "full" ], - "anchor": true, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "__experimentalBorder": { - "color": true, - "width": true, - "style": true - }, - "html": false, - "spacing": { - "margin": true, - "padding": true, - "blockGap": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "layout": { - "allowEditing": false - }, - "interactivity": { - "clientNavigation": true - }, - "allowedBlocks": true - }, - "editorStyle": "wp-block-details-editor", - "style": "wp-block-details" -} diff --git a/src/wp-includes/blocks/embed/block.json b/src/wp-includes/blocks/embed/block.json deleted file mode 100644 index 5bfb63b0fa9e9..0000000000000 --- a/src/wp-includes/blocks/embed/block.json +++ /dev/null @@ -1,54 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/embed", - "title": "Embed", - "category": "embed", - "description": "Add a block that displays content pulled from other sites, like Twitter or YouTube.", - "textdomain": "default", - "attributes": { - "url": { - "type": "string", - "role": "content" - }, - "caption": { - "type": "rich-text", - "source": "rich-text", - "selector": "figcaption", - "role": "content" - }, - "type": { - "type": "string", - "role": "content" - }, - "providerNameSlug": { - "type": "string", - "role": "content" - }, - "allowResponsive": { - "type": "boolean", - "default": true - }, - "responsive": { - "type": "boolean", - "default": false, - "role": "content" - }, - "previewable": { - "type": "boolean", - "default": true, - "role": "content" - } - }, - "supports": { - "align": true, - "spacing": { - "margin": true - }, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-embed-editor", - "style": "wp-block-embed" -} diff --git a/src/wp-includes/blocks/file.php b/src/wp-includes/blocks/file.php deleted file mode 100644 index 42a3e022ee4d9..0000000000000 --- a/src/wp-includes/blocks/file.php +++ /dev/null @@ -1,67 +0,0 @@ -next_tag() ) { - $processor->set_attribute( 'data-wp-interactive', 'core/file' ); - } - - // If there are no OBJECT elements, something might have already modified the block. - if ( ! $processor->next_tag( 'OBJECT' ) ) { - return $content; - } - - $processor->set_attribute( 'data-wp-bind--hidden', '!state.hasPdfPreview' ); - $processor->set_attribute( 'hidden', true ); - - $filename = $processor->get_attribute( 'aria-label' ); - $has_filename = is_string( $filename ) && ! empty( $filename ) && 'PDF embed' !== $filename; - $label = $has_filename ? sprintf( - /* translators: %s: filename. */ - __( 'Embed of %s.' ), - $filename - ) : __( 'PDF embed' ); - - // Update object's aria-label attribute if present in block HTML. - // Match an aria-label attribute from an object tag. - $processor->set_attribute( 'aria-label', $label ); - - return $processor->get_updated_html(); -} - -/** - * Registers the `core/file` block on server. - * - * @since 5.8.0 - */ -function register_block_core_file() { - register_block_type_from_metadata( - __DIR__ . '/file', - array( - 'render_callback' => 'render_block_core_file', - ) - ); -} -add_action( 'init', 'register_block_core_file' ); diff --git a/src/wp-includes/blocks/file/block.json b/src/wp-includes/blocks/file/block.json deleted file mode 100644 index 2c5e888c2aff6..0000000000000 --- a/src/wp-includes/blocks/file/block.json +++ /dev/null @@ -1,97 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/file", - "title": "File", - "category": "media", - "description": "Add a link to a downloadable file.", - "keywords": [ "document", "pdf", "download" ], - "textdomain": "default", - "attributes": { - "id": { - "type": "number" - }, - "blob": { - "type": "string", - "role": "local" - }, - "href": { - "type": "string", - "role": "content" - }, - "fileId": { - "type": "string", - "source": "attribute", - "selector": "a:not([download])", - "attribute": "id" - }, - "fileName": { - "type": "rich-text", - "source": "rich-text", - "selector": "a:not([download])", - "role": "content" - }, - "textLinkHref": { - "type": "string", - "source": "attribute", - "selector": "a:not([download])", - "attribute": "href", - "role": "content" - }, - "textLinkTarget": { - "type": "string", - "source": "attribute", - "selector": "a:not([download])", - "attribute": "target" - }, - "showDownloadButton": { - "type": "boolean", - "default": true - }, - "downloadButtonText": { - "type": "rich-text", - "source": "rich-text", - "selector": "a[download]", - "role": "content" - }, - "displayPreview": { - "type": "boolean" - }, - "previewHeight": { - "type": "number", - "default": 600 - } - }, - "supports": { - "anchor": true, - "align": true, - "spacing": { - "margin": true, - "padding": true - }, - "color": { - "gradients": true, - "link": true, - "text": false, - "__experimentalDefaultControls": { - "background": true, - "link": true - } - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - }, - "interactivity": true - }, - "editorStyle": "wp-block-file-editor", - "style": "wp-block-file" -} diff --git a/src/wp-includes/blocks/file/view.asset.php b/src/wp-includes/blocks/file/view.asset.php deleted file mode 100644 index ce536d2611595..0000000000000 --- a/src/wp-includes/blocks/file/view.asset.php +++ /dev/null @@ -1 +0,0 @@ - array(), 'version' => '498971a8a9512421f3b5'); diff --git a/src/wp-includes/blocks/file/view.min.asset.php b/src/wp-includes/blocks/file/view.min.asset.php deleted file mode 100644 index 76f2ca1fbc30c..0000000000000 --- a/src/wp-includes/blocks/file/view.min.asset.php +++ /dev/null @@ -1 +0,0 @@ - array(), 'version' => '9c04187f1796859989c3'); diff --git a/src/wp-includes/blocks/footnotes.php b/src/wp-includes/blocks/footnotes.php deleted file mode 100644 index 380c093c8117e..0000000000000 --- a/src/wp-includes/blocks/footnotes.php +++ /dev/null @@ -1,142 +0,0 @@ -context['postId'] ) ) { - return ''; - } - - if ( post_password_required( $block->context['postId'] ) ) { - return; - } - - $footnotes = get_post_meta( $block->context['postId'], 'footnotes', true ); - - if ( ! $footnotes ) { - return; - } - - $footnotes = json_decode( $footnotes, true ); - - if ( ! is_array( $footnotes ) || count( $footnotes ) === 0 ) { - return ''; - } - - $wrapper_attributes = get_block_wrapper_attributes(); - $footnote_index = 1; - - $block_content = ''; - - foreach ( $footnotes as $footnote ) { - // Translators: %d: Integer representing the number of return links on the page. - $aria_label = sprintf( __( 'Jump to footnote reference %1$d' ), $footnote_index ); - $block_content .= sprintf( - '
  • %2$s ↩︎
  • ', - $footnote['id'], - $footnote['content'], - $aria_label - ); - ++$footnote_index; - } - - return sprintf( - '
      %2$s
    ', - $wrapper_attributes, - $block_content - ); -} - -/** - * Registers the `core/footnotes` block on the server. - * - * @since 6.3.0 - */ -function register_block_core_footnotes() { - register_block_type_from_metadata( - __DIR__ . '/footnotes', - array( - 'render_callback' => 'render_block_core_footnotes', - ) - ); -} -add_action( 'init', 'register_block_core_footnotes' ); - - -/** - * Registers the footnotes meta field required for footnotes to work. - * - * @since 6.5.0 - */ -function register_block_core_footnotes_post_meta() { - $post_types = get_post_types( array( 'show_in_rest' => true ) ); - foreach ( $post_types as $post_type ) { - // Only register the meta field if the post type supports the editor, custom fields, and revisions. - if ( - post_type_supports( $post_type, 'editor' ) && - post_type_supports( $post_type, 'custom-fields' ) && - post_type_supports( $post_type, 'revisions' ) - ) { - register_post_meta( - $post_type, - 'footnotes', - array( - 'show_in_rest' => true, - 'single' => true, - 'type' => 'string', - 'revisions_enabled' => true, - ) - ); - } - } -} -/* - * Most post types are registered at priority 10, so use priority 20 here in - * order to catch them. -*/ -add_action( 'init', 'register_block_core_footnotes_post_meta', 20 ); - -/** - * Adds the footnotes field to the revisions display. - * - * @since 6.3.0 - * - * @param array $fields The revision fields. - * @return array The revision fields. - */ -function wp_add_footnotes_to_revision( $fields ) { - $fields['footnotes'] = __( 'Footnotes' ); - return $fields; -} -add_filter( '_wp_post_revision_fields', 'wp_add_footnotes_to_revision' ); - -/** - * Gets the footnotes field from the revision for the revisions screen. - * - * @since 6.3.0 - * - * @param string $revision_field The field value, but $revision->$field - * (footnotes) does not exist. - * @param string $field The field name, in this case "footnotes". - * @param object $revision The revision object to compare against. - * @return string The field value. - */ -function wp_get_footnotes_from_revision( $revision_field, $field, $revision ) { - return get_metadata( 'post', $revision->ID, $field, true ); -} -add_filter( '_wp_post_revision_field_footnotes', 'wp_get_footnotes_from_revision', 10, 3 ); diff --git a/src/wp-includes/blocks/footnotes/block.json b/src/wp-includes/blocks/footnotes/block.json deleted file mode 100644 index 1fe74abb471ee..0000000000000 --- a/src/wp-includes/blocks/footnotes/block.json +++ /dev/null @@ -1,64 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/footnotes", - "title": "Footnotes", - "category": "text", - "description": "Display footnotes added to the page.", - "keywords": [ "references" ], - "textdomain": "default", - "usesContext": [ "postId", "postType" ], - "supports": { - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": false, - "color": false, - "width": false, - "style": false - } - }, - "color": { - "background": true, - "link": true, - "text": true, - "__experimentalDefaultControls": { - "link": true, - "text": true - } - }, - "html": false, - "multiple": false, - "reusable": false, - "inserter": false, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalTextDecoration": true, - "__experimentalFontStyle": true, - "__experimentalFontWeight": true, - "__experimentalLetterSpacing": true, - "__experimentalTextTransform": true, - "__experimentalWritingMode": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "style": "wp-block-footnotes" -} diff --git a/src/wp-includes/blocks/freeform/block.json b/src/wp-includes/blocks/freeform/block.json deleted file mode 100644 index 35d8295e4669d..0000000000000 --- a/src/wp-includes/blocks/freeform/block.json +++ /dev/null @@ -1,25 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/freeform", - "title": "Classic", - "category": "text", - "description": "Use the classic WordPress editor.", - "textdomain": "default", - "attributes": { - "content": { - "type": "string", - "source": "raw" - } - }, - "supports": { - "html": false, - "className": false, - "customClassName": false, - "lock": false, - "reusable": false, - "renaming": false, - "blockVisibility": false - }, - "editorStyle": "wp-block-freeform-editor" -} diff --git a/src/wp-includes/blocks/gallery.php b/src/wp-includes/blocks/gallery.php deleted file mode 100644 index 8671a130fb038..0000000000000 --- a/src/wp-includes/blocks/gallery.php +++ /dev/null @@ -1,183 +0,0 @@ - $inner_block ) { - if ( 'core/image' === $inner_block['blockName'] ) { - if ( ! isset( $parsed_block['innerBlocks'][ $key ]['attrs']['data-id'] ) && isset( $inner_block['attrs']['id'] ) ) { - $parsed_block['innerBlocks'][ $key ]['attrs']['data-id'] = esc_attr( $inner_block['attrs']['id'] ); - } - } - } - } - - return $parsed_block; -} - -add_filter( 'render_block_data', 'block_core_gallery_data_id_backcompatibility' ); - -/** - * Renders the `core/gallery` block on the server. - * - * @since 6.0.0 - * - * @param array $attributes Attributes of the block being rendered. - * @param string $content Content of the block being rendered. - * @return string The content of the block being rendered. - */ -function block_core_gallery_render( $attributes, $content ) { - // Adds a style tag for the --wp--style--unstable-gallery-gap var. - // The Gallery block needs to recalculate Image block width based on - // the current gap setting in order to maintain the number of flex columns - // so a css var is added to allow this. - - $gap = $attributes['style']['spacing']['blockGap'] ?? null; - // Skip if gap value contains unsupported characters. - // Regex for CSS value borrowed from `safecss_filter_attr`, and used here - // because we only want to match against the value, not the CSS attribute. - if ( is_array( $gap ) ) { - foreach ( $gap as $key => $value ) { - // Make sure $value is a string to avoid PHP 8.1 deprecation error in preg_match() when the value is null. - $value = is_string( $value ) ? $value : ''; - $value = $value && preg_match( '%[\\\(&=}]|/\*%', $value ) ? null : $value; - - // Get spacing CSS variable from preset value if provided. - if ( is_string( $value ) && str_contains( $value, 'var:preset|spacing|' ) ) { - $index_to_splice = strrpos( $value, '|' ) + 1; - $slug = _wp_to_kebab_case( substr( $value, $index_to_splice ) ); - $value = "var(--wp--preset--spacing--$slug)"; - } - - $gap[ $key ] = $value; - } - } else { - // Make sure $gap is a string to avoid PHP 8.1 deprecation error in preg_match() when the value is null. - $gap = is_string( $gap ) ? $gap : ''; - $gap = $gap && preg_match( '%[\\\(&=}]|/\*%', $gap ) ? null : $gap; - - // Get spacing CSS variable from preset value if provided. - if ( is_string( $gap ) && str_contains( $gap, 'var:preset|spacing|' ) ) { - $index_to_splice = strrpos( $gap, '|' ) + 1; - $slug = _wp_to_kebab_case( substr( $gap, $index_to_splice ) ); - $gap = "var(--wp--preset--spacing--$slug)"; - } - } - - $unique_gallery_classname = wp_unique_id( 'wp-block-gallery-' ); - $processed_content = new WP_HTML_Tag_Processor( $content ); - $processed_content->next_tag(); - $processed_content->add_class( $unique_gallery_classname ); - - // --gallery-block--gutter-size is deprecated. --wp--style--gallery-gap-default should be used by themes that want to set a default - // gap on the gallery. - $fallback_gap = 'var( --wp--style--gallery-gap-default, var( --gallery-block--gutter-size, var( --wp--style--block-gap, 0.5em ) ) )'; - $gap_value = $gap ? $gap : $fallback_gap; - $gap_column = $gap_value; - - if ( is_array( $gap_value ) ) { - $gap_row = isset( $gap_value['top'] ) ? $gap_value['top'] : $fallback_gap; - $gap_column = isset( $gap_value['left'] ) ? $gap_value['left'] : $fallback_gap; - $gap_value = $gap_row === $gap_column ? $gap_row : $gap_row . ' ' . $gap_column; - } - - // The unstable gallery gap calculation requires a real value (such as `0px`) and not `0`. - if ( '0' === $gap_column ) { - $gap_column = '0px'; - } - - // Set the CSS variable to the column value, and the `gap` property to the combined gap value. - $gallery_styles = array( - array( - 'selector' => ".wp-block-gallery.{$unique_gallery_classname}", - 'declarations' => array( - '--wp--style--unstable-gallery-gap' => $gap_column, - 'gap' => $gap_value, - ), - ), - ); - - wp_style_engine_get_stylesheet_from_css_rules( - $gallery_styles, - array( - 'context' => 'block-supports', - ) - ); - - // The WP_HTML_Tag_Processor class calls get_updated_html() internally - // when the instance is treated as a string, but here we explicitly - // convert it to a string. - $updated_content = $processed_content->get_updated_html(); - - /* - * Randomize the order of image blocks. Ideally we should shuffle - * the `$parsed_block['innerBlocks']` via the `render_block_data` hook. - * However, this hook doesn't apply inner block updates when blocks are - * nested. - * @todo In the future, if this hook supports updating innerBlocks in - * nested blocks, it should be refactored. - * - * @see: https://github.com/WordPress/gutenberg/pull/58733 - */ - if ( empty( $attributes['randomOrder'] ) ) { - return $updated_content; - } - - // This pattern matches figure elements with the `wp-block-image` class to - // avoid the gallery's wrapping `figure` element and extract images only. - $pattern = '/]*\bwp-block-image\b[^>]*>.*?<\/figure>/s'; - - // Find all Image blocks. - preg_match_all( $pattern, $updated_content, $matches ); - if ( ! $matches ) { - return $updated_content; - } - $image_blocks = $matches[0]; - - // Randomize the order of Image blocks. - shuffle( $image_blocks ); - $i = 0; - $content = preg_replace_callback( - $pattern, - static function () use ( $image_blocks, &$i ) { - $new_image_block = $image_blocks[ $i ]; - ++$i; - return $new_image_block; - }, - $updated_content - ); - - return $content; -} -/** - * Registers the `core/gallery` block on server. - * - * @since 5.9.0 - */ -function register_block_core_gallery() { - register_block_type_from_metadata( - __DIR__ . '/gallery', - array( - 'render_callback' => 'block_core_gallery_render', - ) - ); -} - -add_action( 'init', 'register_block_core_gallery' ); diff --git a/src/wp-includes/blocks/gallery/block.json b/src/wp-includes/blocks/gallery/block.json deleted file mode 100644 index 02dbb05cb78b4..0000000000000 --- a/src/wp-includes/blocks/gallery/block.json +++ /dev/null @@ -1,162 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/gallery", - "title": "Gallery", - "category": "media", - "allowedBlocks": [ "core/image" ], - "description": "Display multiple images in a rich gallery.", - "keywords": [ "images", "photos" ], - "textdomain": "default", - "attributes": { - "images": { - "type": "array", - "default": [], - "source": "query", - "selector": ".blocks-gallery-item", - "query": { - "url": { - "type": "string", - "source": "attribute", - "selector": "img", - "attribute": "src" - }, - "fullUrl": { - "type": "string", - "source": "attribute", - "selector": "img", - "attribute": "data-full-url" - }, - "link": { - "type": "string", - "source": "attribute", - "selector": "img", - "attribute": "data-link" - }, - "alt": { - "type": "string", - "source": "attribute", - "selector": "img", - "attribute": "alt", - "default": "" - }, - "id": { - "type": "string", - "source": "attribute", - "selector": "img", - "attribute": "data-id" - }, - "caption": { - "type": "rich-text", - "source": "rich-text", - "selector": ".blocks-gallery-item__caption" - } - } - }, - "ids": { - "type": "array", - "items": { - "type": "number" - }, - "default": [] - }, - "shortCodeTransforms": { - "type": "array", - "items": { - "type": "object" - }, - "default": [] - }, - "columns": { - "type": "number", - "minimum": 1, - "maximum": 8 - }, - "caption": { - "type": "rich-text", - "source": "rich-text", - "selector": ".blocks-gallery-caption", - "role": "content" - }, - "imageCrop": { - "type": "boolean", - "default": true - }, - "randomOrder": { - "type": "boolean", - "default": false - }, - "fixedHeight": { - "type": "boolean", - "default": true - }, - "linkTarget": { - "type": "string" - }, - "linkTo": { - "type": "string" - }, - "sizeSlug": { - "type": "string", - "default": "large" - }, - "allowResize": { - "type": "boolean", - "default": false - }, - "aspectRatio": { - "type": "string", - "default": "auto" - } - }, - "providesContext": { - "allowResize": "allowResize", - "imageCrop": "imageCrop", - "fixedHeight": "fixedHeight" - }, - "supports": { - "anchor": true, - "align": true, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "color": true, - "radius": true - } - }, - "html": false, - "units": [ "px", "em", "rem", "vh", "vw" ], - "spacing": { - "margin": true, - "padding": true, - "blockGap": [ "horizontal", "vertical" ], - "__experimentalSkipSerialization": [ "blockGap" ], - "__experimentalDefaultControls": { - "blockGap": true, - "margin": false, - "padding": false - } - }, - "color": { - "text": false, - "background": true, - "gradients": true - }, - "layout": { - "allowSwitching": false, - "allowInheriting": false, - "allowEditing": false, - "default": { - "type": "flex" - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-gallery-editor", - "style": "wp-block-gallery" -} diff --git a/src/wp-includes/blocks/group/block.json b/src/wp-includes/blocks/group/block.json deleted file mode 100644 index e83fb60d31fc7..0000000000000 --- a/src/wp-includes/blocks/group/block.json +++ /dev/null @@ -1,96 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/group", - "title": "Group", - "category": "design", - "description": "Gather blocks in a layout container.", - "keywords": [ "container", "wrapper", "row", "section" ], - "textdomain": "default", - "attributes": { - "tagName": { - "type": "string", - "default": "div" - }, - "templateLock": { - "type": [ "string", "boolean" ], - "enum": [ "all", "insert", "contentOnly", false ] - } - }, - "supports": { - "__experimentalOnEnter": true, - "__experimentalOnMerge": true, - "__experimentalSettings": true, - "align": [ "wide", "full" ], - "anchor": true, - "ariaLabel": true, - "html": false, - "background": { - "backgroundImage": true, - "backgroundSize": true, - "__experimentalDefaultControls": { - "backgroundImage": true - } - }, - "color": { - "gradients": true, - "heading": true, - "button": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "shadow": true, - "spacing": { - "margin": [ "top", "bottom" ], - "padding": true, - "blockGap": true, - "__experimentalDefaultControls": { - "padding": true, - "blockGap": true - } - }, - "dimensions": { - "minHeight": true - }, - "__experimentalBorder": { - "color": true, - "radius": true, - "style": true, - "width": true, - "__experimentalDefaultControls": { - "color": true, - "radius": true, - "style": true, - "width": true - } - }, - "position": { - "sticky": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "layout": { - "allowSizingOnChildren": true - }, - "interactivity": { - "clientNavigation": true - }, - "allowedBlocks": true - }, - "editorStyle": "wp-block-group-editor", - "style": "wp-block-group" -} diff --git a/src/wp-includes/blocks/heading.php b/src/wp-includes/blocks/heading.php deleted file mode 100644 index 471e31f19f2ee..0000000000000 --- a/src/wp-includes/blocks/heading.php +++ /dev/null @@ -1,56 +0,0 @@ -Hello World - * - * Would be transformed to: - *

    Hello World

    - * - * @since 6.2.0 - * - * @param array $attributes Attributes of the block being rendered. - * @param string $content Content of the block being rendered. - * - * @return string The content of the block being rendered. - */ -function block_core_heading_render( $attributes, $content ) { - if ( ! $content ) { - return $content; - } - - $p = new WP_HTML_Tag_Processor( $content ); - - $header_tags = array( 'H1', 'H2', 'H3', 'H4', 'H5', 'H6' ); - while ( $p->next_tag() ) { - if ( in_array( $p->get_tag(), $header_tags, true ) ) { - $p->add_class( 'wp-block-heading' ); - break; - } - } - - return $p->get_updated_html(); -} - -/** - * Registers the `core/heading` block on server. - * - * @since 6.2.0 - */ -function register_block_core_heading() { - register_block_type_from_metadata( - __DIR__ . '/heading', - array( - 'render_callback' => 'block_core_heading_render', - ) - ); -} - -add_action( 'init', 'register_block_core_heading' ); diff --git a/src/wp-includes/blocks/heading/block.json b/src/wp-includes/blocks/heading/block.json deleted file mode 100644 index d9488a3156528..0000000000000 --- a/src/wp-includes/blocks/heading/block.json +++ /dev/null @@ -1,81 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/heading", - "title": "Heading", - "category": "text", - "description": "Introduce new sections and organize content to help visitors (and search engines) understand the structure of your content.", - "keywords": [ "title", "subtitle" ], - "textdomain": "default", - "attributes": { - "textAlign": { - "type": "string" - }, - "content": { - "type": "rich-text", - "source": "rich-text", - "selector": "h1,h2,h3,h4,h5,h6", - "role": "content" - }, - "level": { - "type": "number", - "default": 2 - }, - "levelOptions": { - "type": "array" - }, - "placeholder": { - "type": "string" - } - }, - "supports": { - "align": [ "wide", "full" ], - "anchor": true, - "className": true, - "splitting": true, - "__experimentalBorder": { - "color": true, - "radius": true, - "style": true, - "width": true - }, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontStyle": true, - "__experimentalFontWeight": true, - "__experimentalLetterSpacing": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalWritingMode": true, - "fitText": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "__unstablePasteTextInline": true, - "__experimentalSlashInserter": true, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-heading-editor", - "style": "wp-block-heading" -} diff --git a/src/wp-includes/blocks/home-link.php b/src/wp-includes/blocks/home-link.php deleted file mode 100644 index d61aa0bc235e2..0000000000000 --- a/src/wp-includes/blocks/home-link.php +++ /dev/null @@ -1,176 +0,0 @@ - array(), - 'inline_styles' => '', - ); - - // Text color. - $has_named_text_color = array_key_exists( 'textColor', $context ); - $has_custom_text_color = isset( $context['style']['color']['text'] ); - - // If has text color. - if ( $has_custom_text_color || $has_named_text_color ) { - // Add has-text-color class. - $colors['css_classes'][] = 'has-text-color'; - } - - if ( $has_named_text_color ) { - // Add the color class. - $colors['css_classes'][] = sprintf( 'has-%s-color', $context['textColor'] ); - } elseif ( $has_custom_text_color ) { - // Add the custom color inline style. - $colors['inline_styles'] .= sprintf( 'color: %s;', $context['style']['color']['text'] ); - } - - // Background color. - $has_named_background_color = array_key_exists( 'backgroundColor', $context ); - $has_custom_background_color = isset( $context['style']['color']['background'] ); - - // If has background color. - if ( $has_custom_background_color || $has_named_background_color ) { - // Add has-background class. - $colors['css_classes'][] = 'has-background'; - } - - if ( $has_named_background_color ) { - // Add the background-color class. - $colors['css_classes'][] = sprintf( 'has-%s-background-color', $context['backgroundColor'] ); - } elseif ( $has_custom_background_color ) { - // Add the custom background-color inline style. - $colors['inline_styles'] .= sprintf( 'background-color: %s;', $context['style']['color']['background'] ); - } - - return $colors; -} - -/** - * Build an array with CSS classes and inline styles defining the font sizes - * which will be applied to the home link markup in the front-end. - * - * @since 6.0.0 - * - * @param array $context Home link block context. - * @return array Font size CSS classes and inline styles. - */ -function block_core_home_link_build_css_font_sizes( $context ) { - // CSS classes. - $font_sizes = array( - 'css_classes' => array(), - 'inline_styles' => '', - ); - - $has_named_font_size = array_key_exists( 'fontSize', $context ); - $has_custom_font_size = isset( $context['style']['typography']['fontSize'] ); - - if ( $has_named_font_size ) { - // Add the font size class. - $font_sizes['css_classes'][] = sprintf( 'has-%s-font-size', $context['fontSize'] ); - } elseif ( $has_custom_font_size ) { - // Add the custom font size inline style. - $font_sizes['inline_styles'] = sprintf( 'font-size: %s;', $context['style']['typography']['fontSize'] ); - } - - return $font_sizes; -} - -/** - * Builds an array with classes and style for the li wrapper - * - * @since 6.0.0 - * - * @param array $context Home link block context. - * @return string The li wrapper attributes. - */ -function block_core_home_link_build_li_wrapper_attributes( $context ) { - $colors = block_core_home_link_build_css_colors( $context ); - $font_sizes = block_core_home_link_build_css_font_sizes( $context ); - $classes = array_merge( - $colors['css_classes'], - $font_sizes['css_classes'] - ); - $style_attribute = ( $colors['inline_styles'] . $font_sizes['inline_styles'] ); - $classes[] = 'wp-block-navigation-item'; - - if ( is_front_page() ) { - $classes[] = 'current-menu-item'; - } elseif ( is_home() && ( (int) get_option( 'page_for_posts' ) !== get_queried_object_id() ) ) { - // Edge case where the Reading settings has a posts page set but not a static homepage. - $classes[] = 'current-menu-item'; - } - - $wrapper_attributes = get_block_wrapper_attributes( - array( - 'class' => implode( ' ', $classes ), - 'style' => $style_attribute, - ) - ); - - return $wrapper_attributes; -} - -/** - * Renders the `core/home-link` block. - * - * @since 6.0.0 - * - * @param array $attributes The block attributes. - * @param string $content The saved content. - * @param WP_Block $block The parsed block. - * - * @return string Returns the post content with the home url added. - */ -function render_block_core_home_link( $attributes, $content, $block ) { - if ( empty( $attributes['label'] ) ) { - $attributes['label'] = __( 'Home' ); - } - $aria_current = ''; - - if ( is_front_page() ) { - $aria_current = ' aria-current="page"'; - } elseif ( is_home() && ( (int) get_option( 'page_for_posts' ) !== get_queried_object_id() ) ) { - // Edge case where the Reading settings has a posts page set but not a static homepage. - $aria_current = ' aria-current="page"'; - } - - return sprintf( - '
  • %4$s
  • ', - block_core_home_link_build_li_wrapper_attributes( $block->context ), - esc_url( home_url() ), - $aria_current, - wp_kses_post( $attributes['label'] ) - ); -} - -/** - * Register the home block - * - * @since 6.0.0 - * - * @uses render_block_core_home_link() - * @throws WP_Error An WP_Error exception parsing the block definition. - */ -function register_block_core_home_link() { - register_block_type_from_metadata( - __DIR__ . '/home-link', - array( - 'render_callback' => 'render_block_core_home_link', - ) - ); -} -add_action( 'init', 'register_block_core_home_link' ); diff --git a/src/wp-includes/blocks/home-link/block.json b/src/wp-includes/blocks/home-link/block.json deleted file mode 100644 index 4b5103ec0c75a..0000000000000 --- a/src/wp-includes/blocks/home-link/block.json +++ /dev/null @@ -1,47 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/home-link", - "category": "design", - "parent": [ "core/navigation" ], - "title": "Home Link", - "description": "Create a link that always points to the homepage of the site. Usually not necessary if there is already a site title link present in the header.", - "textdomain": "default", - "attributes": { - "label": { - "type": "string", - "role": "content" - } - }, - "usesContext": [ - "textColor", - "customTextColor", - "backgroundColor", - "customBackgroundColor", - "fontSize", - "customFontSize", - "style" - ], - "supports": { - "reusable": false, - "html": false, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-home-link-editor", - "style": "wp-block-home-link" -} diff --git a/src/wp-includes/blocks/html/block.json b/src/wp-includes/blocks/html/block.json deleted file mode 100644 index 940cc5e8b253d..0000000000000 --- a/src/wp-includes/blocks/html/block.json +++ /dev/null @@ -1,26 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/html", - "title": "Custom HTML", - "category": "widgets", - "description": "Add custom HTML code and preview it as you edit.", - "keywords": [ "embed" ], - "textdomain": "default", - "attributes": { - "content": { - "type": "string", - "source": "raw", - "role": "content" - } - }, - "supports": { - "customClassName": false, - "className": false, - "html": false, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-html-editor" -} diff --git a/src/wp-includes/blocks/image.php b/src/wp-includes/blocks/image.php deleted file mode 100644 index 0db8c9d3f608e..0000000000000 --- a/src/wp-includes/blocks/image.php +++ /dev/null @@ -1,367 +0,0 @@ -set_bookmark( 'here' ); - $opener = $this->bookmarks['here']; - - // Allow comments within the definition of “empty.” - while ( $this->next_token() && '#comment' === $this->get_token_name() ) { - continue; - } - - if ( 'FIGCAPTION' !== $this->get_tag() || ! $this->is_tag_closer() ) { - return false; - } - - $this->set_bookmark( 'here' ); - $closer = $this->bookmarks['here']; - - return new WP_HTML_Span( $opener->start, $closer->start + $closer->length - $opener->start ); - } - }; - - if ( ! $processor->next_tag( 'img' ) || ! $processor->get_attribute( 'src' ) ) { - return ''; - } - - $has_id_binding = isset( $attributes['metadata']['bindings']['id'] ) && isset( $attributes['id'] ); - - // Ensure the `wp-image-id` classname on the image block supports block bindings. - if ( $has_id_binding ) { - // If there's a mismatch with the 'wp-image-' class and the actual id, the id was - // probably overridden by block bindings. Update it to the correct value. - // See https://github.com/WordPress/gutenberg/issues/62886 for why this is needed. - $id = $attributes['id']; - $image_classnames = $processor->get_attribute( 'class' ); - $class_with_binding_value = "wp-image-$id"; - if ( is_string( $image_classnames ) && ! str_contains( $image_classnames, $class_with_binding_value ) ) { - $image_classnames = preg_replace( '/wp-image-(\d+)/', $class_with_binding_value, $image_classnames ); - $processor->set_attribute( 'class', $image_classnames ); - } - } - - // For backwards compatibility, the data-id html attribute is only set for - // image blocks nested in a gallery. Detect if the image is in a gallery by - // checking the data-id attribute. - // See the `block_core_gallery_data_id_backcompatibility` function. - if ( isset( $attributes['data-id'] ) ) { - // If there's a binding for the `id`, the `id` attribute is used for the - // value, since `data-id` does not support block bindings. - // Else the `data-id` is used for backwards compatibility, since - // third parties may be filtering its value. - $data_id = $has_id_binding ? $attributes['id'] : $attributes['data-id']; - $processor->set_attribute( 'data-id', $data_id ); - } - - /* - * If the `caption` attribute is empty and we encounter a `
    ` element, - * we take note of its span so we can remove it later. - */ - if ( $processor->next_tag( 'FIGCAPTION' ) && empty( $attributes['caption'] ) ) { - $figcaption_span = $processor->block_core_image_extract_empty_figcaption_element(); - } - - $link_destination = isset( $attributes['linkDestination'] ) ? $attributes['linkDestination'] : 'none'; - $lightbox_settings = block_core_image_get_lightbox_settings( $block->parsed_block ); - - /* - * If the lightbox is enabled and the image is not linked, adds the filter and - * the JavaScript view file. - */ - if ( - isset( $lightbox_settings ) && - 'none' === $link_destination && - isset( $lightbox_settings['enabled'] ) && - true === $lightbox_settings['enabled'] - ) { - wp_enqueue_script_module( '@wordpress/block-library/image/view' ); - - /* - * This render needs to happen in a filter with priority 15 to ensure that - * it runs after the duotone filter and that duotone styles are applied to - * the image in the lightbox. Lightbox has to work with any plugins that - * might use filters as well. Removing this can be considered in the future - * if the way the blocks are rendered changes, or if a new kind of filter is - * introduced. - */ - add_filter( 'render_block_core/image', 'block_core_image_render_lightbox', 15, 2 ); - } else { - /* - * Remove the filter if previously added by other Image blocks. - */ - remove_filter( 'render_block_core/image', 'block_core_image_render_lightbox', 15 ); - } - - $output = $processor->get_updated_html(); - if ( ! empty( $figcaption_span ) ) { - return substr( $output, 0, $figcaption_span->start ) . substr( $output, $figcaption_span->start + $figcaption_span->length ); - } - return $output; -} - -/** - * Adds the lightboxEnabled flag to the block data. - * - * This is used to determine whether the lightbox should be rendered or not. - * - * @since 6.4.0 - * - * @param array $block Block data. - * - * @return array|null Filtered block data. - */ -function block_core_image_get_lightbox_settings( $block ) { - // Gets the lightbox setting from the block attributes. - if ( isset( $block['attrs']['lightbox'] ) ) { - $lightbox_settings = $block['attrs']['lightbox']; - } - - if ( ! isset( $lightbox_settings ) ) { - $lightbox_settings = wp_get_global_settings( array( 'lightbox' ), array( 'block_name' => 'core/image' ) ); - - // If not present in global settings, check the top-level global settings. - // - // NOTE: If no block-level settings are found, the previous call to - // `wp_get_global_settings` will return the whole `theme.json` structure in - // which case we can check if the "lightbox" key is present at the top-level - // of the global settings and use its value. - if ( isset( $lightbox_settings['lightbox'] ) ) { - $lightbox_settings = wp_get_global_settings( array( 'lightbox' ) ); - } - } - - return $lightbox_settings ?? null; -} - -/** - * Adds the directives and layout needed for the lightbox behavior. - * - * @since 6.4.0 - * - * @param string $block_content Rendered block content. - * @param array $block Block object. - * - * @return string Filtered block content. - */ -function block_core_image_render_lightbox( $block_content, $block ) { - /* - * If there's no IMG tag in the block then return the given block content - * as-is. There's nothing that this code can knowingly modify to add the - * lightbox behavior. - */ - $processor = new WP_HTML_Tag_Processor( $block_content ); - if ( $processor->next_tag( 'figure' ) ) { - $processor->set_bookmark( 'figure' ); - } - if ( ! $processor->next_tag( 'img' ) ) { - return $block_content; - } - - $alt = $processor->get_attribute( 'alt' ); - $img_uploaded_src = $processor->get_attribute( 'src' ); - $img_class_names = $processor->get_attribute( 'class' ); - $img_styles = $processor->get_attribute( 'style' ); - $img_width = 'none'; - $img_height = 'none'; - $aria_label = __( 'Enlarge' ); - $dialog_aria_label = __( 'Enlarged image' ); - - if ( isset( $block['attrs']['id'] ) ) { - $img_uploaded_src = wp_get_attachment_url( $block['attrs']['id'] ); - $img_metadata = wp_get_attachment_metadata( $block['attrs']['id'] ); - $img_width = $img_metadata['width'] ?? 'none'; - $img_height = $img_metadata['height'] ?? 'none'; - } - - // Figure. - $processor->seek( 'figure' ); - $figure_class_names = $processor->get_attribute( 'class' ); - $figure_styles = $processor->get_attribute( 'style' ); - - // Create unique id and set the image metadata in the state. - $unique_image_id = uniqid(); - - wp_interactivity_state( - 'core/image', - array( - 'metadata' => array( - $unique_image_id => array( - 'uploadedSrc' => $img_uploaded_src, - 'figureClassNames' => $figure_class_names, - 'figureStyles' => $figure_styles, - 'imgClassNames' => $img_class_names, - 'imgStyles' => $img_styles, - 'targetWidth' => $img_width, - 'targetHeight' => $img_height, - 'scaleAttr' => $block['attrs']['scale'] ?? false, - 'ariaLabel' => $dialog_aria_label, - 'alt' => $alt, - ), - ), - ) - ); - - $processor->add_class( 'wp-lightbox-container' ); - $processor->set_attribute( 'data-wp-interactive', 'core/image' ); - $processor->set_attribute( - 'data-wp-context', - wp_json_encode( - array( - 'imageId' => $unique_image_id, - ), - JSON_HEX_TAG | JSON_HEX_APOS | JSON_HEX_QUOT | JSON_HEX_AMP - ) - ); - $processor->set_attribute( 'data-wp-key', $unique_image_id ); - - // Image. - $processor->next_tag( 'img' ); - $processor->set_attribute( 'data-wp-init', 'callbacks.setButtonStyles' ); - $processor->set_attribute( 'data-wp-on--load', 'callbacks.setButtonStyles' ); - $processor->set_attribute( 'data-wp-on-window--resize', 'callbacks.setButtonStyles' ); - // Sets an event callback on the `img` because the `figure` element can also - // contain a caption, and we don't want to trigger the lightbox when the - // caption is clicked. - $processor->set_attribute( 'data-wp-on--click', 'actions.showLightbox' ); - $processor->set_attribute( 'data-wp-class--hide', 'state.isContentHidden' ); - $processor->set_attribute( 'data-wp-class--show', 'state.isContentVisible' ); - - $body_content = $processor->get_updated_html(); - - // Adds a button alongside image in the body content. - $img = null; - preg_match( '/]+>/', $body_content, $img ); - - $button = - $img[0] - . ''; - - $body_content = preg_replace( '/]+>/', $button, $body_content ); - - add_action( 'wp_footer', 'block_core_image_print_lightbox_overlay' ); - - return $body_content; -} - -/** - * @since 6.5.0 - */ -function block_core_image_print_lightbox_overlay() { - $close_button_label = esc_attr__( 'Close' ); - - // If the current theme does NOT have a `theme.json`, or the colors are not - // defined, it needs to set the background color & close button color to some - // default values because it can't get them from the Global Styles. - $background_color = '#fff'; - $close_button_color = '#000'; - if ( wp_theme_has_theme_json() ) { - $global_styles_color = wp_get_global_styles( array( 'color' ) ); - if ( ! empty( $global_styles_color['background'] ) ) { - $background_color = esc_attr( $global_styles_color['background'] ); - } - if ( ! empty( $global_styles_color['text'] ) ) { - $close_button_color = esc_attr( $global_styles_color['text'] ); - } - } - - echo << - - - - -
    -HTML; -} - -/** - * Registers the `core/image` block on server. - * - * @since 5.9.0 - */ -function register_block_core_image() { - register_block_type_from_metadata( - __DIR__ . '/image', - array( - 'render_callback' => 'render_block_core_image', - ) - ); -} -add_action( 'init', 'register_block_core_image' ); diff --git a/src/wp-includes/blocks/image/block.json b/src/wp-includes/blocks/image/block.json deleted file mode 100644 index 26835df9e856c..0000000000000 --- a/src/wp-includes/blocks/image/block.json +++ /dev/null @@ -1,151 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/image", - "title": "Image", - "category": "media", - "usesContext": [ - "allowResize", - "imageCrop", - "fixedHeight", - "postId", - "postType", - "queryId" - ], - "description": "Insert an image to make a visual statement.", - "keywords": [ "img", "photo", "picture" ], - "textdomain": "default", - "attributes": { - "blob": { - "type": "string", - "role": "local" - }, - "url": { - "type": "string", - "source": "attribute", - "selector": "img", - "attribute": "src", - "role": "content" - }, - "alt": { - "type": "string", - "source": "attribute", - "selector": "img", - "attribute": "alt", - "default": "", - "role": "content" - }, - "caption": { - "type": "rich-text", - "source": "rich-text", - "selector": "figcaption", - "role": "content" - }, - "lightbox": { - "type": "object", - "enabled": { - "type": "boolean" - } - }, - "title": { - "type": "string", - "source": "attribute", - "selector": "img", - "attribute": "title", - "role": "content" - }, - "href": { - "type": "string", - "source": "attribute", - "selector": "figure > a", - "attribute": "href", - "role": "content" - }, - "rel": { - "type": "string", - "source": "attribute", - "selector": "figure > a", - "attribute": "rel" - }, - "linkClass": { - "type": "string", - "source": "attribute", - "selector": "figure > a", - "attribute": "class" - }, - "id": { - "type": "number", - "role": "content" - }, - "width": { - "type": "string" - }, - "height": { - "type": "string" - }, - "aspectRatio": { - "type": "string" - }, - "scale": { - "type": "string" - }, - "sizeSlug": { - "type": "string" - }, - "linkDestination": { - "type": "string" - }, - "linkTarget": { - "type": "string", - "source": "attribute", - "selector": "figure > a", - "attribute": "target" - } - }, - "supports": { - "interactivity": true, - "align": [ "left", "center", "right", "wide", "full" ], - "anchor": true, - "color": { - "text": false, - "background": false - }, - "filter": { - "duotone": true - }, - "spacing": { - "margin": true - }, - "__experimentalBorder": { - "color": true, - "radius": true, - "width": true, - "__experimentalSkipSerialization": true, - "__experimentalDefaultControls": { - "color": true, - "radius": true, - "width": true - } - }, - "shadow": { - "__experimentalSkipSerialization": true - } - }, - "selectors": { - "border": ".wp-block-image img, .wp-block-image .wp-block-image__crop-area, .wp-block-image .components-placeholder", - "shadow": ".wp-block-image img, .wp-block-image .wp-block-image__crop-area, .wp-block-image .components-placeholder", - "filter": { - "duotone": ".wp-block-image img, .wp-block-image .components-placeholder" - } - }, - "styles": [ - { - "name": "default", - "label": "Default", - "isDefault": true - }, - { "name": "rounded", "label": "Rounded" } - ], - "editorStyle": "wp-block-image-editor", - "style": "wp-block-image" -} diff --git a/src/wp-includes/blocks/image/view.asset.php b/src/wp-includes/blocks/image/view.asset.php deleted file mode 100644 index 58058b1408c81..0000000000000 --- a/src/wp-includes/blocks/image/view.asset.php +++ /dev/null @@ -1 +0,0 @@ - array(), 'version' => '7500eb032759d407a71d'); diff --git a/src/wp-includes/blocks/image/view.min.asset.php b/src/wp-includes/blocks/image/view.min.asset.php deleted file mode 100644 index 5b46fcb7d531e..0000000000000 --- a/src/wp-includes/blocks/image/view.min.asset.php +++ /dev/null @@ -1 +0,0 @@ - array(), 'version' => 'ff354d5368d64857fef0'); diff --git a/src/wp-includes/blocks/latest-comments.php b/src/wp-includes/blocks/latest-comments.php deleted file mode 100644 index bbe82b8b18f9a..0000000000000 --- a/src/wp-includes/blocks/latest-comments.php +++ /dev/null @@ -1,162 +0,0 @@ - $attributes['commentsToShow'], - 'status' => 'approve', - 'post_status' => 'publish', - ), - array() - ) - ); - - $list_items_markup = ''; - if ( ! empty( $comments ) ) { - // Prime the cache for associated posts. This is copied from \WP_Widget_Recent_Comments::widget(). - $post_ids = array_unique( wp_list_pluck( $comments, 'comment_post_ID' ) ); - _prime_post_caches( $post_ids, strpos( get_option( 'permalink_structure' ), '%category%' ), false ); - - foreach ( $comments as $comment ) { - $list_items_markup .= '
  • '; - if ( $attributes['displayAvatar'] ) { - $avatar = get_avatar( - $comment, - 48, - '', - '', - array( - 'class' => 'wp-block-latest-comments__comment-avatar', - ) - ); - if ( $avatar ) { - $list_items_markup .= $avatar; - } - } - - $list_items_markup .= '
    '; - $list_items_markup .= ''; - if ( $attributes['displayExcerpt'] ) { - $list_items_markup .= '
    ' . wpautop( get_comment_excerpt( $comment ) ) . '
    '; - } - $list_items_markup .= '
  • '; - } - } - - $classnames = array(); - if ( $attributes['displayAvatar'] ) { - $classnames[] = 'has-avatars'; - } - if ( $attributes['displayDate'] ) { - $classnames[] = 'has-dates'; - } - if ( $attributes['displayExcerpt'] ) { - $classnames[] = 'has-excerpts'; - } - if ( empty( $comments ) ) { - $classnames[] = 'no-comments'; - } - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classnames ) ) ); - - return ! empty( $comments ) ? sprintf( - '
      %2$s
    ', - $wrapper_attributes, - $list_items_markup - ) : sprintf( - '
    %2$s
    ', - $wrapper_attributes, - __( 'No comments to show.' ) - ); -} - -/** - * Registers the `core/latest-comments` block. - * - * @since 5.3.0 - */ -function register_block_core_latest_comments() { - register_block_type_from_metadata( - __DIR__ . '/latest-comments', - array( - 'render_callback' => 'render_block_core_latest_comments', - ) - ); -} - -add_action( 'init', 'register_block_core_latest_comments' ); diff --git a/src/wp-includes/blocks/latest-comments/block.json b/src/wp-includes/blocks/latest-comments/block.json deleted file mode 100644 index 543512ddf3ce7..0000000000000 --- a/src/wp-includes/blocks/latest-comments/block.json +++ /dev/null @@ -1,65 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/latest-comments", - "title": "Latest Comments", - "category": "widgets", - "description": "Display a list of your most recent comments.", - "keywords": [ "recent comments" ], - "textdomain": "default", - "attributes": { - "commentsToShow": { - "type": "number", - "default": 5, - "minimum": 1, - "maximum": 100 - }, - "displayAvatar": { - "type": "boolean", - "default": true - }, - "displayDate": { - "type": "boolean", - "default": true - }, - "displayExcerpt": { - "type": "boolean", - "default": true - } - }, - "supports": { - "align": true, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "html": false, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-latest-comments-editor", - "style": "wp-block-latest-comments" -} diff --git a/src/wp-includes/blocks/latest-posts.php b/src/wp-includes/blocks/latest-posts.php deleted file mode 100644 index b970f486bb6a1..0000000000000 --- a/src/wp-includes/blocks/latest-posts.php +++ /dev/null @@ -1,273 +0,0 @@ - $attributes['postsToShow'], - 'post_status' => 'publish', - 'order' => $attributes['order'], - 'orderby' => $attributes['orderBy'], - 'ignore_sticky_posts' => true, - 'no_found_rows' => true, - ); - - $block_core_latest_posts_excerpt_length = $attributes['excerptLength']; - add_filter( 'excerpt_length', 'block_core_latest_posts_get_excerpt_length', 20 ); - - if ( ! empty( $attributes['categories'] ) ) { - $args['category__in'] = array_column( $attributes['categories'], 'id' ); - } - if ( isset( $attributes['selectedAuthor'] ) ) { - $args['author'] = $attributes['selectedAuthor']; - } - - $query = new WP_Query(); - $recent_posts = $query->query( $args ); - - if ( isset( $attributes['displayFeaturedImage'] ) && $attributes['displayFeaturedImage'] ) { - update_post_thumbnail_cache( $query ); - } - - $list_items_markup = ''; - - foreach ( $recent_posts as $post ) { - $post_link = esc_url( get_permalink( $post ) ); - $title = get_the_title( $post ); - - if ( ! $title ) { - $title = __( '(no title)' ); - } - - $list_items_markup .= '
  • '; - - if ( $attributes['displayFeaturedImage'] && has_post_thumbnail( $post ) ) { - $image_style = ''; - if ( isset( $attributes['featuredImageSizeWidth'] ) ) { - $image_style .= sprintf( 'max-width:%spx;', $attributes['featuredImageSizeWidth'] ); - } - if ( isset( $attributes['featuredImageSizeHeight'] ) ) { - $image_style .= sprintf( 'max-height:%spx;', $attributes['featuredImageSizeHeight'] ); - } - - $image_classes = 'wp-block-latest-posts__featured-image'; - if ( isset( $attributes['featuredImageAlign'] ) ) { - $image_classes .= ' align' . $attributes['featuredImageAlign']; - } - - $featured_image = get_the_post_thumbnail( - $post, - $attributes['featuredImageSizeSlug'], - array( - 'style' => esc_attr( $image_style ), - ) - ); - if ( $attributes['addLinkToFeaturedImage'] ) { - $featured_image = sprintf( - '%3$s', - esc_url( $post_link ), - esc_attr( $title ), - $featured_image - ); - } - $list_items_markup .= sprintf( - '
    %2$s
    ', - esc_attr( $image_classes ), - $featured_image - ); - } - - $list_items_markup .= sprintf( - '%2$s', - esc_url( $post_link ), - $title - ); - - if ( isset( $attributes['displayAuthor'] ) && $attributes['displayAuthor'] ) { - $author_display_name = get_the_author_meta( 'display_name', $post->post_author ); - - /* translators: byline. %s: author. */ - $byline = sprintf( __( 'by %s' ), $author_display_name ); - - if ( ! empty( $author_display_name ) ) { - $list_items_markup .= sprintf( - '', - $byline - ); - } - } - - if ( isset( $attributes['displayPostDate'] ) && $attributes['displayPostDate'] ) { - $list_items_markup .= sprintf( - '', - esc_attr( get_the_date( 'c', $post ) ), - get_the_date( '', $post ) - ); - } - - if ( isset( $attributes['displayPostContent'] ) && $attributes['displayPostContent'] - && isset( $attributes['displayPostContentRadio'] ) && 'excerpt' === $attributes['displayPostContentRadio'] ) { - - $trimmed_excerpt = get_the_excerpt( $post ); - - /* - * Adds a "Read more" link with screen reader text. - * […] is the default excerpt ending from wp_trim_excerpt() in Core. - */ - if ( str_ends_with( $trimmed_excerpt, ' […]' ) ) { - /** This filter is documented in wp-includes/formatting.php */ - $excerpt_length = (int) apply_filters( 'excerpt_length', $block_core_latest_posts_excerpt_length ); - if ( $excerpt_length <= $block_core_latest_posts_excerpt_length ) { - $trimmed_excerpt = substr( $trimmed_excerpt, 0, -11 ); - $trimmed_excerpt .= sprintf( - /* translators: 1: A URL to a post, 2: Hidden accessibility text: Post title */ - __( '… Read more: %2$s' ), - esc_url( $post_link ), - esc_html( $title ) - ); - } - } - - if ( post_password_required( $post ) ) { - $trimmed_excerpt = __( 'This content is password protected.' ); - } - - $list_items_markup .= sprintf( - '
    %1$s
    ', - $trimmed_excerpt - ); - } - - if ( isset( $attributes['displayPostContent'] ) && $attributes['displayPostContent'] - && isset( $attributes['displayPostContentRadio'] ) && 'full_post' === $attributes['displayPostContentRadio'] ) { - - $post_content = html_entity_decode( $post->post_content, ENT_QUOTES, get_option( 'blog_charset' ) ); - - if ( post_password_required( $post ) ) { - $post_content = __( 'This content is password protected.' ); - } - - $list_items_markup .= sprintf( - '
    %1$s
    ', - wp_kses_post( $post_content ) - ); - } - - $list_items_markup .= "
  • \n"; - } - - remove_filter( 'excerpt_length', 'block_core_latest_posts_get_excerpt_length', 20 ); - - $classes = array( 'wp-block-latest-posts__list' ); - if ( isset( $attributes['postLayout'] ) && 'grid' === $attributes['postLayout'] ) { - $classes[] = 'is-grid'; - } - if ( isset( $attributes['columns'] ) && 'grid' === $attributes['postLayout'] ) { - $classes[] = 'columns-' . $attributes['columns']; - } - if ( isset( $attributes['displayPostDate'] ) && $attributes['displayPostDate'] ) { - $classes[] = 'has-dates'; - } - if ( isset( $attributes['displayAuthor'] ) && $attributes['displayAuthor'] ) { - $classes[] = 'has-author'; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - - return sprintf( - '', - $wrapper_attributes, - $list_items_markup - ); -} - -/** - * Registers the `core/latest-posts` block on server. - * - * @since 5.0.0 - */ -function register_block_core_latest_posts() { - register_block_type_from_metadata( - __DIR__ . '/latest-posts', - array( - 'render_callback' => 'render_block_core_latest_posts', - ) - ); -} -add_action( 'init', 'register_block_core_latest_posts' ); - -/** - * Handles outdated versions of the `core/latest-posts` block by converting - * attribute `categories` from a numeric string to an array with key `id`. - * - * This is done to accommodate the changes introduced in #20781 that sought to - * add support for multiple categories to the block. However, given that this - * block is dynamic, the usual provisions for block migration are insufficient, - * as they only act when a block is loaded in the editor. - * - * TODO: Remove when and if the bottom client-side deprecation for this block - * is removed. - * - * @since 5.5.0 - * - * @param array $block A single parsed block object. - * - * @return array The migrated block object. - */ -function block_core_latest_posts_migrate_categories( $block ) { - if ( - 'core/latest-posts' === $block['blockName'] && - ! empty( $block['attrs']['categories'] ) && - is_string( $block['attrs']['categories'] ) - ) { - $block['attrs']['categories'] = array( - array( 'id' => absint( $block['attrs']['categories'] ) ), - ); - } - - return $block; -} -add_filter( 'render_block_data', 'block_core_latest_posts_migrate_categories' ); diff --git a/src/wp-includes/blocks/latest-posts/block.json b/src/wp-includes/blocks/latest-posts/block.json deleted file mode 100644 index 58b1c6da81ca3..0000000000000 --- a/src/wp-includes/blocks/latest-posts/block.json +++ /dev/null @@ -1,132 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/latest-posts", - "title": "Latest Posts", - "category": "widgets", - "description": "Display a list of your most recent posts.", - "keywords": [ "recent posts" ], - "textdomain": "default", - "attributes": { - "categories": { - "type": "array", - "items": { - "type": "object" - } - }, - "selectedAuthor": { - "type": "number" - }, - "postsToShow": { - "type": "number", - "default": 5 - }, - "displayPostContent": { - "type": "boolean", - "default": false - }, - "displayPostContentRadio": { - "type": "string", - "default": "excerpt" - }, - "excerptLength": { - "type": "number", - "default": 55 - }, - "displayAuthor": { - "type": "boolean", - "default": false - }, - "displayPostDate": { - "type": "boolean", - "default": false - }, - "postLayout": { - "type": "string", - "default": "list" - }, - "columns": { - "type": "number", - "default": 3 - }, - "order": { - "type": "string", - "default": "desc" - }, - "orderBy": { - "type": "string", - "default": "date" - }, - "displayFeaturedImage": { - "type": "boolean", - "default": false - }, - "featuredImageAlign": { - "type": "string", - "enum": [ "left", "center", "right" ] - }, - "featuredImageSizeSlug": { - "type": "string", - "default": "thumbnail" - }, - "featuredImageSizeWidth": { - "type": "number", - "default": null - }, - "featuredImageSizeHeight": { - "type": "number", - "default": null - }, - "addLinkToFeaturedImage": { - "type": "boolean", - "default": false - } - }, - "supports": { - "align": true, - "html": false, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-latest-posts-editor", - "style": "wp-block-latest-posts" -} diff --git a/src/wp-includes/blocks/legacy-widget.php b/src/wp-includes/blocks/legacy-widget.php deleted file mode 100644 index bec1b16b6ba8c..0000000000000 --- a/src/wp-includes/blocks/legacy-widget.php +++ /dev/null @@ -1,157 +0,0 @@ -get_widget_key( $id_base ); - $widget_object = $wp_widget_factory->get_widget_object( $id_base ); - - if ( ! $widget_key || ! $widget_object ) { - return ''; - } - - if ( isset( $attributes['instance']['encoded'], $attributes['instance']['hash'] ) ) { - $serialized_instance = base64_decode( $attributes['instance']['encoded'] ); - if ( ! hash_equals( wp_hash( $serialized_instance ), (string) $attributes['instance']['hash'] ) ) { - return ''; - } - $instance = unserialize( $serialized_instance ); - } else { - $instance = array(); - } - - $args = array( - 'widget_id' => $widget_object->id, - 'widget_name' => $widget_object->name, - ); - - ob_start(); - the_widget( $widget_key, $instance, $args ); - return ob_get_clean(); -} - -/** - * Registers the 'core/legacy-widget' block. - * - * @since 5.8.0 - */ -function register_block_core_legacy_widget() { - register_block_type_from_metadata( - __DIR__ . '/legacy-widget', - array( - 'render_callback' => 'render_block_core_legacy_widget', - ) - ); -} - -add_action( 'init', 'register_block_core_legacy_widget' ); - -/** - * Intercepts any request with legacy-widget-preview in the query param and, if - * set, renders a page containing a preview of the requested Legacy Widget - * block. - * - * @since 5.8.0 - */ -function handle_legacy_widget_preview_iframe() { - if ( empty( $_GET['legacy-widget-preview'] ) ) { - return; - } - - if ( ! current_user_can( 'edit_theme_options' ) ) { - return; - } - - define( 'IFRAME_REQUEST', true ); - - ?> - - > - - - - - - - - > -
    -
    - get_registered( 'core/legacy-widget' ); - echo $block->render( $_GET['legacy-widget-preview'] ); - ?> -
    -
    - - - - li", - "border": ".wp-block-list:not(.wp-block-list .wp-block-list) > li" - } -} diff --git a/src/wp-includes/blocks/list.php b/src/wp-includes/blocks/list.php deleted file mode 100644 index 1bffd81324857..0000000000000 --- a/src/wp-includes/blocks/list.php +++ /dev/null @@ -1,54 +0,0 @@ - is transformed to
      . - * - * @since 6.6.0 - * - * @see https://github.com/WordPress/gutenberg/issues/12420 - * - * @param array $attributes Attributes of the block being rendered. - * @param string $content Content of the block being rendered. - * - * @return string The content of the block being rendered. - */ -function block_core_list_render( $attributes, $content ) { - if ( ! $content ) { - return $content; - } - - $processor = new WP_HTML_Tag_Processor( $content ); - - $list_tags = array( 'OL', 'UL' ); - while ( $processor->next_tag() ) { - if ( in_array( $processor->get_tag(), $list_tags, true ) ) { - $processor->add_class( 'wp-block-list' ); - break; - } - } - - return $processor->get_updated_html(); -} - -/** - * Registers the `core/list` block on server. - * - * @since 6.6.0 - */ -function register_block_core_list() { - register_block_type_from_metadata( - __DIR__ . '/list', - array( - 'render_callback' => 'block_core_list_render', - ) - ); -} - -add_action( 'init', 'register_block_core_list' ); diff --git a/src/wp-includes/blocks/list/block.json b/src/wp-includes/blocks/list/block.json deleted file mode 100644 index bd696c30c334c..0000000000000 --- a/src/wp-includes/blocks/list/block.json +++ /dev/null @@ -1,88 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/list", - "title": "List", - "category": "text", - "allowedBlocks": [ "core/list-item" ], - "description": "An organized collection of items displayed in a specific order.", - "keywords": [ "bullet list", "ordered list", "numbered list" ], - "textdomain": "default", - "attributes": { - "ordered": { - "type": "boolean", - "default": false, - "role": "content" - }, - "values": { - "type": "string", - "source": "html", - "selector": "ol,ul", - "multiline": "li", - "default": "", - "role": "content" - }, - "type": { - "type": "string" - }, - "start": { - "type": "number" - }, - "reversed": { - "type": "boolean" - }, - "placeholder": { - "type": "string" - } - }, - "supports": { - "anchor": true, - "html": false, - "__experimentalBorder": { - "color": true, - "radius": true, - "style": true, - "width": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "__unstablePasteTextInline": true, - "__experimentalOnMerge": true, - "__experimentalSlashInserter": true, - "interactivity": { - "clientNavigation": true - } - }, - "selectors": { - "border": ".wp-block-list:not(.wp-block-list .wp-block-list)" - }, - "editorStyle": "wp-block-list-editor", - "style": "wp-block-list" -} diff --git a/src/wp-includes/blocks/loginout.php b/src/wp-includes/blocks/loginout.php deleted file mode 100644 index f83d8be424ece..0000000000000 --- a/src/wp-includes/blocks/loginout.php +++ /dev/null @@ -1,61 +0,0 @@ - false ) ); - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => $classes ) ); - - return '
      ' . $contents . '
      '; -} - -/** - * Registers the `core/loginout` block on server. - * - * @since 5.8.0 - */ -function register_block_core_loginout() { - register_block_type_from_metadata( - __DIR__ . '/loginout', - array( - 'render_callback' => 'render_block_core_loginout', - ) - ); -} -add_action( 'init', 'register_block_core_loginout' ); diff --git a/src/wp-includes/blocks/loginout/block.json b/src/wp-includes/blocks/loginout/block.json deleted file mode 100644 index f2aaafd60fde0..0000000000000 --- a/src/wp-includes/blocks/loginout/block.json +++ /dev/null @@ -1,63 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/loginout", - "title": "Login/out", - "category": "theme", - "description": "Show login & logout links.", - "keywords": [ "login", "logout", "form" ], - "textdomain": "default", - "attributes": { - "displayLoginAsForm": { - "type": "boolean", - "default": false - }, - "redirectToCurrent": { - "type": "boolean", - "default": true - } - }, - "example": { - "viewportWidth": 350 - }, - "supports": { - "className": true, - "color": { - "background": true, - "text": false, - "gradients": true, - "link": true - }, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true - }, - "interactivity": { - "clientNavigation": true - } - }, - "style": "wp-block-loginout" -} diff --git a/src/wp-includes/blocks/math/block.json b/src/wp-includes/blocks/math/block.json deleted file mode 100644 index 4b47761307c4c..0000000000000 --- a/src/wp-includes/blocks/math/block.json +++ /dev/null @@ -1,24 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/math", - "title": "Math", - "category": "text", - "description": "Display mathematical notation using LaTeX.", - "keywords": [ "equation", "formula", "latex", "mathematics" ], - "textdomain": "default", - "supports": { - "html": false - }, - "attributes": { - "latex": { - "type": "string", - "role": "content" - }, - "mathML": { - "type": "string", - "source": "html", - "selector": "math" - } - } -} diff --git a/src/wp-includes/blocks/media-text.php b/src/wp-includes/blocks/media-text.php deleted file mode 100644 index b65137b150ba5..0000000000000 --- a/src/wp-includes/blocks/media-text.php +++ /dev/null @@ -1,131 +0,0 @@ - 'div', - 'class_name' => 'wp-block-media-text', - ); - - while ( $block_tag_processor->next_tag( $block_query ) ) { - if ( $image_fill ) { - // The markup below does not work with the deprecated `is-image-fill` class. - $block_tag_processor->remove_class( 'is-image-fill' ); - $block_tag_processor->add_class( 'is-image-fill-element' ); - } - } - - $content = $block_tag_processor->get_updated_html(); - - $media_tag_processor = new WP_HTML_Tag_Processor( $content ); - $wrapping_figure_query = array( - 'tag_name' => 'figure', - 'class_name' => 'wp-block-media-text__media', - ); - - if ( $has_media_on_right ) { - // Loop through all the figure tags and set a bookmark on the last figure tag. - while ( $media_tag_processor->next_tag( $wrapping_figure_query ) ) { - $media_tag_processor->set_bookmark( 'last_figure' ); - } - if ( $media_tag_processor->has_bookmark( 'last_figure' ) ) { - $media_tag_processor->seek( 'last_figure' ); - // Insert a unique ID to identify the figure tag. - $media_tag_processor->set_attribute( 'id', $unique_id ); - } - } else { - if ( $media_tag_processor->next_tag( $wrapping_figure_query ) ) { - // Insert a unique ID to identify the figure tag. - $media_tag_processor->set_attribute( 'id', $unique_id ); - } - } - - $content = $media_tag_processor->get_updated_html(); - - // Add the image tag inside the figure tag, and update the image attributes - // in order to display the featured image. - $media_size_slug = isset( $attributes['mediaSizeSlug'] ) ? $attributes['mediaSizeSlug'] : 'full'; - $image_tag = ''; - $content = preg_replace( - '/()/', - '$1' . $image_tag, - $content - ); - - $image_tag_processor = new WP_HTML_Tag_Processor( $content ); - if ( $image_tag_processor->next_tag( - array( - 'tag_name' => 'figure', - 'id' => $unique_id, - ) - ) ) { - // The ID is only used to ensure that the correct figure tag is selected, - // and can now be removed. - $image_tag_processor->remove_attribute( 'id' ); - if ( $image_tag_processor->next_tag( - array( - 'tag_name' => 'img', - 'class_name' => 'wp-block-media-text__featured_image', - ) - ) ) { - $image_tag_processor->set_attribute( 'src', esc_url( $current_featured_image ) ); - $image_tag_processor->set_attribute( 'class', 'wp-image-' . get_post_thumbnail_id() . ' size-' . $media_size_slug ); - $image_tag_processor->set_attribute( 'alt', trim( strip_tags( get_post_meta( get_post_thumbnail_id(), '_wp_attachment_image_alt', true ) ) ) ); - if ( $image_fill ) { - $image_tag_processor->set_attribute( 'style', 'object-position:' . $focal_point . ';' ); - } - - $content = $image_tag_processor->get_updated_html(); - } - } - - return $content; -} - -/** - * Registers the `core/media-text` block renderer on server. - * - * @since 6.6.0 - */ -function register_block_core_media_text() { - register_block_type_from_metadata( - __DIR__ . '/media-text', - array( - 'render_callback' => 'render_block_core_media_text', - ) - ); -} -add_action( 'init', 'register_block_core_media_text' ); diff --git a/src/wp-includes/blocks/media-text/block.json b/src/wp-includes/blocks/media-text/block.json deleted file mode 100644 index 249a5d43032c8..0000000000000 --- a/src/wp-includes/blocks/media-text/block.json +++ /dev/null @@ -1,148 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/media-text", - "title": "Media & Text", - "category": "media", - "description": "Set media and words side-by-side for a richer layout.", - "keywords": [ "image", "video" ], - "textdomain": "default", - "attributes": { - "align": { - "type": "string", - "default": "none" - }, - "mediaAlt": { - "type": "string", - "source": "attribute", - "selector": "figure img", - "attribute": "alt", - "default": "", - "role": "content" - }, - "mediaPosition": { - "type": "string", - "default": "left" - }, - "mediaId": { - "type": "number", - "role": "content" - }, - "mediaUrl": { - "type": "string", - "source": "attribute", - "selector": "figure video,figure img", - "attribute": "src", - "role": "content" - }, - "mediaLink": { - "type": "string" - }, - "linkDestination": { - "type": "string" - }, - "linkTarget": { - "type": "string", - "source": "attribute", - "selector": "figure a", - "attribute": "target" - }, - "href": { - "type": "string", - "source": "attribute", - "selector": "figure a", - "attribute": "href", - "role": "content" - }, - "rel": { - "type": "string", - "source": "attribute", - "selector": "figure a", - "attribute": "rel" - }, - "linkClass": { - "type": "string", - "source": "attribute", - "selector": "figure a", - "attribute": "class" - }, - "mediaType": { - "type": "string", - "role": "content" - }, - "mediaWidth": { - "type": "number", - "default": 50 - }, - "mediaSizeSlug": { - "type": "string" - }, - "isStackedOnMobile": { - "type": "boolean", - "default": true - }, - "verticalAlignment": { - "type": "string" - }, - "imageFill": { - "type": "boolean" - }, - "focalPoint": { - "type": "object" - }, - "useFeaturedImage": { - "type": "boolean", - "default": false - } - }, - "usesContext": [ "postId", "postType" ], - "supports": { - "anchor": true, - "align": [ "wide", "full" ], - "html": false, - "__experimentalBorder": { - "color": true, - "radius": true, - "style": true, - "width": true, - "__experimentalDefaultControls": { - "color": true, - "radius": true, - "style": true, - "width": true - } - }, - "color": { - "gradients": true, - "heading": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "allowedBlocks": true - }, - "editorStyle": "wp-block-media-text-editor", - "style": "wp-block-media-text" -} diff --git a/src/wp-includes/blocks/missing/block.json b/src/wp-includes/blocks/missing/block.json deleted file mode 100644 index 94051f20be7e5..0000000000000 --- a/src/wp-includes/blocks/missing/block.json +++ /dev/null @@ -1,34 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/missing", - "title": "Unsupported", - "category": "text", - "description": "Your site doesn’t include support for this block.", - "textdomain": "default", - "attributes": { - "originalName": { - "type": "string" - }, - "originalUndelimitedContent": { - "type": "string" - }, - "originalContent": { - "type": "string", - "source": "raw" - } - }, - "supports": { - "className": false, - "customClassName": false, - "inserter": false, - "html": false, - "lock": false, - "reusable": false, - "renaming": false, - "blockVisibility": false, - "interactivity": { - "clientNavigation": true - } - } -} diff --git a/src/wp-includes/blocks/more/block.json b/src/wp-includes/blocks/more/block.json deleted file mode 100644 index 01c4b3ce961e5..0000000000000 --- a/src/wp-includes/blocks/more/block.json +++ /dev/null @@ -1,31 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/more", - "title": "More", - "category": "design", - "description": "Content before this block will be shown in the excerpt on your archives page.", - "keywords": [ "read more" ], - "textdomain": "default", - "attributes": { - "customText": { - "type": "string", - "default": "", - "role": "content" - }, - "noTeaser": { - "type": "boolean", - "default": false - } - }, - "supports": { - "customClassName": false, - "className": false, - "html": false, - "multiple": false, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-more-editor" -} diff --git a/src/wp-includes/blocks/navigation-link.php b/src/wp-includes/blocks/navigation-link.php deleted file mode 100644 index 111598ea4c486..0000000000000 --- a/src/wp-includes/blocks/navigation-link.php +++ /dev/null @@ -1,446 +0,0 @@ - array(), - 'inline_styles' => '', - ); - - // Text color. - $named_text_color = null; - $custom_text_color = null; - - if ( $is_sub_menu && array_key_exists( 'customOverlayTextColor', $context ) ) { - $custom_text_color = $context['customOverlayTextColor']; - } elseif ( $is_sub_menu && array_key_exists( 'overlayTextColor', $context ) ) { - $named_text_color = $context['overlayTextColor']; - } elseif ( array_key_exists( 'customTextColor', $context ) ) { - $custom_text_color = $context['customTextColor']; - } elseif ( array_key_exists( 'textColor', $context ) ) { - $named_text_color = $context['textColor']; - } elseif ( isset( $context['style']['color']['text'] ) ) { - $custom_text_color = $context['style']['color']['text']; - } - - // If has text color. - if ( ! is_null( $named_text_color ) ) { - // Add the color class. - array_push( $colors['css_classes'], 'has-text-color', sprintf( 'has-%s-color', $named_text_color ) ); - } elseif ( ! is_null( $custom_text_color ) ) { - // Add the custom color inline style. - $colors['css_classes'][] = 'has-text-color'; - $colors['inline_styles'] .= sprintf( 'color: %s;', $custom_text_color ); - } - - // Background color. - $named_background_color = null; - $custom_background_color = null; - - if ( $is_sub_menu && array_key_exists( 'customOverlayBackgroundColor', $context ) ) { - $custom_background_color = $context['customOverlayBackgroundColor']; - } elseif ( $is_sub_menu && array_key_exists( 'overlayBackgroundColor', $context ) ) { - $named_background_color = $context['overlayBackgroundColor']; - } elseif ( array_key_exists( 'customBackgroundColor', $context ) ) { - $custom_background_color = $context['customBackgroundColor']; - } elseif ( array_key_exists( 'backgroundColor', $context ) ) { - $named_background_color = $context['backgroundColor']; - } elseif ( isset( $context['style']['color']['background'] ) ) { - $custom_background_color = $context['style']['color']['background']; - } - - // If has background color. - if ( ! is_null( $named_background_color ) ) { - // Add the background-color class. - array_push( $colors['css_classes'], 'has-background', sprintf( 'has-%s-background-color', $named_background_color ) ); - } elseif ( ! is_null( $custom_background_color ) ) { - // Add the custom background-color inline style. - $colors['css_classes'][] = 'has-background'; - $colors['inline_styles'] .= sprintf( 'background-color: %s;', $custom_background_color ); - } - - return $colors; -} - -/** - * Build an array with CSS classes and inline styles defining the font sizes - * which will be applied to the navigation markup in the front-end. - * - * @since 5.9.0 - * - * @param array $context Navigation block context. - * @return array Font size CSS classes and inline styles. - */ -function block_core_navigation_link_build_css_font_sizes( $context ) { - // CSS classes. - $font_sizes = array( - 'css_classes' => array(), - 'inline_styles' => '', - ); - - $has_named_font_size = array_key_exists( 'fontSize', $context ); - $has_custom_font_size = isset( $context['style']['typography']['fontSize'] ); - - if ( $has_named_font_size ) { - // Add the font size class. - $font_sizes['css_classes'][] = sprintf( 'has-%s-font-size', $context['fontSize'] ); - } elseif ( $has_custom_font_size ) { - // Add the custom font size inline style. - $font_sizes['inline_styles'] = sprintf( - 'font-size: %s;', - wp_get_typography_font_size_value( - array( - 'size' => $context['style']['typography']['fontSize'], - ) - ) - ); - } - - return $font_sizes; -} - -/** - * Returns the top-level submenu SVG chevron icon. - * - * @since 5.9.0 - * - * @return string - */ -function block_core_navigation_link_render_submenu_icon() { - return ''; -} - -/** - * Decodes a url if it's encoded, returning the same url if not. - * - * @since 6.2.0 - * - * @param string $url The url to decode. - * - * @return string $url Returns the decoded url. - */ -function block_core_navigation_link_maybe_urldecode( $url ) { - $is_url_encoded = false; - $query = parse_url( $url, PHP_URL_QUERY ); - $query_params = wp_parse_args( $query ); - - foreach ( $query_params as $query_param ) { - $can_query_param_be_encoded = is_string( $query_param ) && ! empty( $query_param ); - if ( ! $can_query_param_be_encoded ) { - continue; - } - if ( rawurldecode( $query_param ) !== $query_param ) { - $is_url_encoded = true; - break; - } - } - - if ( $is_url_encoded ) { - return rawurldecode( $url ); - } - - return $url; -} - - -/** - * Renders the `core/navigation-link` block. - * - * @since 5.9.0 - * - * @param array $attributes The block attributes. - * @param string $content The saved content. - * @param WP_Block $block The parsed block. - * - * @return string Returns the post content with the legacy widget added. - */ -function render_block_core_navigation_link( $attributes, $content, $block ) { - $navigation_link_has_id = isset( $attributes['id'] ) && is_numeric( $attributes['id'] ); - $is_post_type = isset( $attributes['kind'] ) && 'post-type' === $attributes['kind']; - $is_post_type = $is_post_type || isset( $attributes['type'] ) && ( 'post' === $attributes['type'] || 'page' === $attributes['type'] ); - - // Don't render the block's subtree if it is a draft or if the ID does not exist. - if ( $is_post_type && $navigation_link_has_id ) { - $post = get_post( $attributes['id'] ); - /** - * Filter allowed post_status for navigation link block to render. - * - * @since 6.8.0 - * - * @param array $post_status - * @param array $attributes - * @param WP_Block $block - */ - $allowed_post_status = (array) apply_filters( - 'render_block_core_navigation_link_allowed_post_status', - array( 'publish' ), - $attributes, - $block - ); - if ( ! $post || ! in_array( $post->post_status, $allowed_post_status, true ) ) { - return ''; - } - } - - // Don't render the block's subtree if it has no label. - if ( empty( $attributes['label'] ) ) { - return ''; - } - - $font_sizes = block_core_navigation_link_build_css_font_sizes( $block->context ); - $classes = array_merge( - $font_sizes['css_classes'] - ); - $style_attribute = $font_sizes['inline_styles']; - - $css_classes = trim( implode( ' ', $classes ) ); - $has_submenu = count( $block->inner_blocks ) > 0; - $kind = empty( $attributes['kind'] ) ? 'post_type' : str_replace( '-', '_', $attributes['kind'] ); - $is_active = ! empty( $attributes['id'] ) && get_queried_object_id() === (int) $attributes['id'] && ! empty( get_queried_object()->$kind ); - - if ( is_post_type_archive() && ! empty( $attributes['url'] ) ) { - $queried_archive_link = get_post_type_archive_link( get_queried_object()->name ); - if ( $attributes['url'] === $queried_archive_link ) { - $is_active = true; - } - } - - $wrapper_attributes = get_block_wrapper_attributes( - array( - 'class' => $css_classes . ' wp-block-navigation-item' . ( $has_submenu ? ' has-child' : '' ) . - ( $is_active ? ' current-menu-item' : '' ), - 'style' => $style_attribute, - ) - ); - $html = '
    1. ' . - ''; - - if ( isset( $attributes['label'] ) ) { - $html .= wp_kses_post( $attributes['label'] ); - } - - $html .= ''; - - // Add description if available. - if ( ! empty( $attributes['description'] ) ) { - $html .= ''; - $html .= wp_kses_post( $attributes['description'] ); - $html .= ''; - } - - $html .= ''; - // End anchor tag content. - - if ( isset( $block->context['showSubmenuIcon'] ) && $block->context['showSubmenuIcon'] && $has_submenu ) { - // The submenu icon can be hidden by a CSS rule on the Navigation Block. - $html .= '' . block_core_navigation_link_render_submenu_icon() . ''; - } - - if ( $has_submenu ) { - $inner_blocks_html = ''; - foreach ( $block->inner_blocks as $inner_block ) { - $inner_blocks_html .= $inner_block->render(); - } - - $html .= sprintf( - '
        %s
      ', - $inner_blocks_html - ); - } - - $html .= '
    2. '; - - return $html; -} - -/** - * Returns a navigation link variation - * - * @since 5.9.0 - * - * @param WP_Taxonomy|WP_Post_Type $entity post type or taxonomy entity. - * @param string $kind string of value 'taxonomy' or 'post-type'. - * - * @return array - */ -function build_variation_for_navigation_link( $entity, $kind ) { - $title = ''; - $description = ''; - - if ( property_exists( $entity->labels, 'item_link' ) ) { - $title = $entity->labels->item_link; - } - if ( property_exists( $entity->labels, 'item_link_description' ) ) { - $description = $entity->labels->item_link_description; - } - - $variation = array( - 'name' => $entity->name, - 'title' => $title, - 'description' => $description, - 'attributes' => array( - 'type' => $entity->name, - 'kind' => $kind, - ), - ); - - // Tweak some value for the variations. - $variation_overrides = array( - 'post_tag' => array( - 'name' => 'tag', - 'attributes' => array( - 'type' => 'tag', - 'kind' => $kind, - ), - ), - 'post_format' => array( - // The item_link and item_link_description for post formats is the - // same as for tags, so need to be overridden. - 'title' => __( 'Post Format Link' ), - 'description' => __( 'A link to a post format' ), - 'attributes' => array( - 'type' => 'post_format', - 'kind' => $kind, - ), - ), - ); - - if ( array_key_exists( $entity->name, $variation_overrides ) ) { - $variation = array_merge( - $variation, - $variation_overrides[ $entity->name ] - ); - } - - return $variation; -} - -/** - * Filters the registered variations for a block type. - * Returns the dynamically built variations for all post-types and taxonomies. - * - * @since 6.5.0 - * - * @param array $variations Array of registered variations for a block type. - * @param WP_Block_Type $block_type The full block type object. - */ -function block_core_navigation_link_filter_variations( $variations, $block_type ) { - if ( 'core/navigation-link' !== $block_type->name ) { - return $variations; - } - - $generated_variations = block_core_navigation_link_build_variations(); - return array_merge( $variations, $generated_variations ); -} - -/** - * Returns an array of variations for the navigation link block. - * - * @since 6.5.0 - * - * @return array - */ -function block_core_navigation_link_build_variations() { - $post_types = get_post_types( array( 'show_in_nav_menus' => true ), 'objects' ); - $taxonomies = get_taxonomies( array( 'show_in_nav_menus' => true ), 'objects' ); - - /* - * Use two separate arrays as a way to order the variations in the UI. - * Known variations (like Post Link and Page Link) are added to the - * `built_ins` array. Variations for custom post types and taxonomies are - * added to the `variations` array and will always appear after `built-ins. - */ - $built_ins = array(); - $variations = array(); - - if ( $post_types ) { - foreach ( $post_types as $post_type ) { - $variation = build_variation_for_navigation_link( $post_type, 'post-type' ); - if ( $post_type->_builtin ) { - $built_ins[] = $variation; - } else { - $variations[] = $variation; - } - } - } - if ( $taxonomies ) { - foreach ( $taxonomies as $taxonomy ) { - $variation = build_variation_for_navigation_link( $taxonomy, 'taxonomy' ); - if ( $taxonomy->_builtin ) { - $built_ins[] = $variation; - } else { - $variations[] = $variation; - } - } - } - - return array_merge( $built_ins, $variations ); -} - -/** - * Registers the navigation link block. - * - * @since 5.9.0 - * - * @uses render_block_core_navigation_link() - * @throws WP_Error An WP_Error exception parsing the block definition. - */ -function register_block_core_navigation_link() { - register_block_type_from_metadata( - __DIR__ . '/navigation-link', - array( - 'render_callback' => 'render_block_core_navigation_link', - ) - ); -} -add_action( 'init', 'register_block_core_navigation_link' ); -/** - * Creates all variations for post types / taxonomies dynamically (= each time when variations are requested). - * Do not use variation_callback, to also account for unregistering post types/taxonomies later on. - */ -add_action( 'get_block_type_variations', 'block_core_navigation_link_filter_variations', 10, 2 ); diff --git a/src/wp-includes/blocks/navigation-link/block.json b/src/wp-includes/blocks/navigation-link/block.json deleted file mode 100644 index 5f2d10b97dabe..0000000000000 --- a/src/wp-includes/blocks/navigation-link/block.json +++ /dev/null @@ -1,88 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/navigation-link", - "title": "Custom Link", - "category": "design", - "parent": [ "core/navigation" ], - "allowedBlocks": [ - "core/navigation-link", - "core/navigation-submenu", - "core/page-list" - ], - "description": "Add a page, link, or another item to your navigation.", - "textdomain": "default", - "attributes": { - "label": { - "type": "string", - "role": "content" - }, - "type": { - "type": "string" - }, - "description": { - "type": "string" - }, - "rel": { - "type": "string" - }, - "id": { - "type": "number" - }, - "opensInNewTab": { - "type": "boolean", - "default": false - }, - "url": { - "type": "string" - }, - "title": { - "type": "string" - }, - "kind": { - "type": "string" - }, - "isTopLevelLink": { - "type": "boolean" - } - }, - "usesContext": [ - "textColor", - "customTextColor", - "backgroundColor", - "customBackgroundColor", - "overlayTextColor", - "customOverlayTextColor", - "overlayBackgroundColor", - "customOverlayBackgroundColor", - "fontSize", - "customFontSize", - "showSubmenuIcon", - "maxNestingLevel", - "style" - ], - "supports": { - "reusable": false, - "html": false, - "__experimentalSlashInserter": true, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "renaming": false, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-navigation-link-editor", - "style": "wp-block-navigation-link" -} diff --git a/src/wp-includes/blocks/navigation-submenu.php b/src/wp-includes/blocks/navigation-submenu.php deleted file mode 100644 index 77f2c1fa635fc..0000000000000 --- a/src/wp-includes/blocks/navigation-submenu.php +++ /dev/null @@ -1,300 +0,0 @@ - array(), - 'inline_styles' => '', - ); - - $has_named_font_size = array_key_exists( 'fontSize', $context ); - $has_custom_font_size = isset( $context['style']['typography']['fontSize'] ); - - if ( $has_named_font_size ) { - // Add the font size class. - $font_sizes['css_classes'][] = sprintf( 'has-%s-font-size', $context['fontSize'] ); - } elseif ( $has_custom_font_size ) { - // Add the custom font size inline style. - $font_sizes['inline_styles'] = sprintf( - 'font-size: %s;', - wp_get_typography_font_size_value( - array( - 'size' => $context['style']['typography']['fontSize'], - ) - ) - ); - } - - return $font_sizes; -} - -/** - * Returns the top-level submenu SVG chevron icon. - * - * @since 5.9.0 - * - * @return string - */ -function block_core_navigation_submenu_render_submenu_icon() { - return ''; -} - -/** - * Renders the `core/navigation-submenu` block. - * - * @since 5.9.0 - * - * @param array $attributes The block attributes. - * @param string $content The saved content. - * @param WP_Block $block The parsed block. - * - * @return string Returns the post content with the legacy widget added. - */ -function render_block_core_navigation_submenu( $attributes, $content, $block ) { - $navigation_link_has_id = isset( $attributes['id'] ) && is_numeric( $attributes['id'] ); - $is_post_type = isset( $attributes['kind'] ) && 'post-type' === $attributes['kind']; - $is_post_type = $is_post_type || isset( $attributes['type'] ) && ( 'post' === $attributes['type'] || 'page' === $attributes['type'] ); - - // Don't render the block's subtree if it is a draft. - if ( $is_post_type && $navigation_link_has_id && 'publish' !== get_post_status( $attributes['id'] ) ) { - return ''; - } - - // Don't render the block's subtree if it has no label. - if ( empty( $attributes['label'] ) ) { - return ''; - } - - $font_sizes = block_core_navigation_submenu_build_css_font_sizes( $block->context ); - $style_attribute = $font_sizes['inline_styles']; - - $has_submenu = count( $block->inner_blocks ) > 0; - $kind = empty( $attributes['kind'] ) ? 'post_type' : str_replace( '-', '_', $attributes['kind'] ); - $is_active = ! empty( $attributes['id'] ) && get_queried_object_id() === (int) $attributes['id'] && ! empty( get_queried_object()->$kind ); - - if ( is_post_type_archive() && ! empty( $attributes['url'] ) ) { - $queried_archive_link = get_post_type_archive_link( get_queried_object()->name ); - if ( $attributes['url'] === $queried_archive_link ) { - $is_active = true; - } - } - - $show_submenu_indicators = isset( $block->context['showSubmenuIcon'] ) && $block->context['showSubmenuIcon']; - $open_on_click = isset( $block->context['openSubmenusOnClick'] ) && $block->context['openSubmenusOnClick']; - $open_on_hover_and_click = isset( $block->context['openSubmenusOnClick'] ) && ! $block->context['openSubmenusOnClick'] && - $show_submenu_indicators; - - $classes = array( - 'wp-block-navigation-item', - ); - $classes = array_merge( - $classes, - $font_sizes['css_classes'] - ); - if ( $has_submenu ) { - $classes[] = 'has-child'; - } - if ( $open_on_click ) { - $classes[] = 'open-on-click'; - } - if ( $open_on_hover_and_click ) { - $classes[] = 'open-on-hover-click'; - } - if ( $is_active ) { - $classes[] = 'current-menu-item'; - } - - $wrapper_attributes = get_block_wrapper_attributes( - array( - 'class' => implode( ' ', $classes ), - 'style' => $style_attribute, - ) - ); - - $label = ''; - - if ( isset( $attributes['label'] ) ) { - $label .= wp_kses_post( $attributes['label'] ); - } - - $aria_label = sprintf( - /* translators: Accessibility text. %s: Parent page title. */ - __( '%s submenu' ), - wp_strip_all_tags( $label ) - ); - - $html = '
    3. '; - - // If Submenus open on hover, we render an anchor tag with attributes. - // If submenu icons are set to show, we also render a submenu button, so the submenu can be opened on click. - if ( ! $open_on_click ) { - $item_url = isset( $attributes['url'] ) ? $attributes['url'] : ''; - // Start appending HTML attributes to anchor tag. - $html .= '
    4. ' . $title . ''; - } - - if ( isset( $page['children'] ) ) { - if ( $is_navigation_child && $show_submenu_icons && ! $open_submenus_on_click ) { - $markup .= ''; - } - $markup .= '
        '; - $markup .= block_core_page_list_render_nested_page_list( $open_submenus_on_click, $show_submenu_icons, $is_navigation_child, $page['children'], $is_nested, $active_page_ancestor_ids, $colors, $depth + 1 ); - $markup .= '
      '; - } - $markup .= '
    5. '; - } - return $markup; -} - -/** - * Outputs nested array of pages - * - * @since 5.8.0 - * - * @param array $current_level The level being iterated through. - * @param array $children The children grouped by parent post ID. - * - * @return array The nested array of pages. - */ -function block_core_page_list_nest_pages( $current_level, $children ) { - if ( empty( $current_level ) ) { - return; - } - foreach ( (array) $current_level as $key => $current ) { - if ( isset( $children[ $key ] ) ) { - $current_level[ $key ]['children'] = block_core_page_list_nest_pages( $children[ $key ], $children ); - } - } - return $current_level; -} - -/** - * Renders the `core/page-list` block on server. - * - * @since 5.8.0 - * - * @param array $attributes The block attributes. - * @param string $content The saved content. - * @param WP_Block $block The parsed block. - * - * @return string Returns the page list markup. - */ -function render_block_core_page_list( $attributes, $content, $block ) { - static $block_id = 0; - ++$block_id; - - $parent_page_id = $attributes['parentPageID']; - $is_nested = $attributes['isNested']; - - $all_pages = get_pages( - array( - 'sort_column' => 'menu_order,post_title', - 'order' => 'asc', - ) - ); - - // If there are no pages, there is nothing to show. - if ( empty( $all_pages ) ) { - return; - } - - $top_level_pages = array(); - - $pages_with_children = array(); - - $active_page_ancestor_ids = array(); - - foreach ( (array) $all_pages as $page ) { - $is_active = ! empty( $page->ID ) && ( get_queried_object_id() === $page->ID ); - - if ( $is_active ) { - $active_page_ancestor_ids = get_post_ancestors( $page->ID ); - } - - if ( $page->post_parent ) { - $pages_with_children[ $page->post_parent ][ $page->ID ] = array( - 'page_id' => $page->ID, - 'title' => $page->post_title, - 'link' => get_permalink( $page ), - 'is_active' => $is_active, - ); - } else { - $top_level_pages[ $page->ID ] = array( - 'page_id' => $page->ID, - 'title' => $page->post_title, - 'link' => get_permalink( $page ), - 'is_active' => $is_active, - ); - - } - } - - $colors = block_core_page_list_build_css_colors( $attributes, $block->context ); - $font_sizes = block_core_page_list_build_css_font_sizes( $block->context ); - $classes = array_merge( - $colors['css_classes'], - $font_sizes['css_classes'] - ); - $style_attribute = ( $colors['inline_styles'] . $font_sizes['inline_styles'] ); - $css_classes = trim( implode( ' ', $classes ) ); - - $nested_pages = block_core_page_list_nest_pages( $top_level_pages, $pages_with_children ); - - if ( 0 !== $parent_page_id ) { - // If the parent page has no child pages, there is nothing to show. - if ( ! array_key_exists( $parent_page_id, $pages_with_children ) ) { - return; - } - - $nested_pages = block_core_page_list_nest_pages( - $pages_with_children[ $parent_page_id ], - $pages_with_children - ); - } - - $is_navigation_child = array_key_exists( 'showSubmenuIcon', $block->context ); - - $open_submenus_on_click = array_key_exists( 'openSubmenusOnClick', $block->context ) ? $block->context['openSubmenusOnClick'] : false; - - $show_submenu_icons = array_key_exists( 'showSubmenuIcon', $block->context ) ? $block->context['showSubmenuIcon'] : false; - - $wrapper_markup = $is_nested ? '%2$s' : '
        %2$s
      '; - - $items_markup = block_core_page_list_render_nested_page_list( $open_submenus_on_click, $show_submenu_icons, $is_navigation_child, $nested_pages, $is_nested, $active_page_ancestor_ids, $colors ); - - $wrapper_attributes = get_block_wrapper_attributes( - array( - 'class' => $css_classes, - 'style' => $style_attribute, - ) - ); - - return sprintf( - $wrapper_markup, - $wrapper_attributes, - $items_markup - ); -} - -/** - * Registers the `core/pages` block on server. - * - * @since 5.8.0 - */ -function register_block_core_page_list() { - register_block_type_from_metadata( - __DIR__ . '/page-list', - array( - 'render_callback' => 'render_block_core_page_list', - ) - ); -} -add_action( 'init', 'register_block_core_page_list' ); diff --git a/src/wp-includes/blocks/page-list/block.json b/src/wp-includes/blocks/page-list/block.json deleted file mode 100644 index 317502b1200b4..0000000000000 --- a/src/wp-includes/blocks/page-list/block.json +++ /dev/null @@ -1,84 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/page-list", - "title": "Page List", - "category": "widgets", - "allowedBlocks": [ "core/page-list-item" ], - "description": "Display a list of all pages.", - "keywords": [ "menu", "navigation" ], - "textdomain": "default", - "attributes": { - "parentPageID": { - "type": "integer", - "default": 0 - }, - "isNested": { - "type": "boolean", - "default": false - } - }, - "usesContext": [ - "textColor", - "customTextColor", - "backgroundColor", - "customBackgroundColor", - "overlayTextColor", - "customOverlayTextColor", - "overlayBackgroundColor", - "customOverlayBackgroundColor", - "fontSize", - "customFontSize", - "showSubmenuIcon", - "style", - "openSubmenusOnClick" - ], - "supports": { - "reusable": false, - "html": false, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "color": { - "text": true, - "background": true, - "link": true, - "gradients": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true - }, - "spacing": { - "padding": true, - "margin": true, - "__experimentalDefaultControls": { - "padding": false, - "margin": false - } - }, - "contentRole": true - }, - "editorStyle": "wp-block-page-list-editor", - "style": "wp-block-page-list" -} diff --git a/src/wp-includes/blocks/paragraph/block.json b/src/wp-includes/blocks/paragraph/block.json deleted file mode 100644 index 9617627ef5d0d..0000000000000 --- a/src/wp-includes/blocks/paragraph/block.json +++ /dev/null @@ -1,81 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/paragraph", - "title": "Paragraph", - "category": "text", - "description": "Start with the basic building block of all narrative.", - "keywords": [ "text" ], - "textdomain": "default", - "attributes": { - "align": { - "type": "string" - }, - "content": { - "type": "rich-text", - "source": "rich-text", - "selector": "p", - "role": "content" - }, - "dropCap": { - "type": "boolean", - "default": false - }, - "placeholder": { - "type": "string" - }, - "direction": { - "type": "string", - "enum": [ "ltr", "rtl" ] - } - }, - "supports": { - "splitting": true, - "anchor": true, - "className": false, - "__experimentalBorder": { - "color": true, - "radius": true, - "style": true, - "width": true - }, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalTextDecoration": true, - "__experimentalFontStyle": true, - "__experimentalFontWeight": true, - "__experimentalLetterSpacing": true, - "__experimentalTextTransform": true, - "__experimentalWritingMode": true, - "fitText": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "__experimentalSelector": "p", - "__unstablePasteTextInline": true, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-paragraph-editor", - "style": "wp-block-paragraph" -} diff --git a/src/wp-includes/blocks/pattern.php b/src/wp-includes/blocks/pattern.php deleted file mode 100644 index 870313eb5e86d..0000000000000 --- a/src/wp-includes/blocks/pattern.php +++ /dev/null @@ -1,72 +0,0 @@ - 'render_block_core_pattern', - ) - ); -} - -/** - * Renders the `core/pattern` block on the server. - * - * @since 6.3.0 Backwards compatibility: blocks with no `syncStatus` attribute do not receive block wrapper. - * - * @global WP_Embed $wp_embed Used to process embedded content within patterns - * - * @param array $attributes Block attributes. - * - * @return string Returns the output of the pattern. - */ -function render_block_core_pattern( $attributes ) { - static $seen_refs = array(); - - if ( empty( $attributes['slug'] ) ) { - return ''; - } - - $slug = $attributes['slug']; - $registry = WP_Block_Patterns_Registry::get_instance(); - - if ( ! $registry->is_registered( $slug ) ) { - return ''; - } - - if ( isset( $seen_refs[ $attributes['slug'] ] ) ) { - // WP_DEBUG_DISPLAY must only be honored when WP_DEBUG. This precedent - // is set in `wp_debug_mode()`. - $is_debug = WP_DEBUG && WP_DEBUG_DISPLAY; - - return $is_debug ? - // translators: Visible only in the front end, this warning takes the place of a faulty block. %s represents a pattern's slug. - sprintf( __( '[block rendering halted for pattern "%s"]' ), $slug ) : - ''; - } - - $pattern = $registry->get_registered( $slug ); - $content = $pattern['content']; - - $seen_refs[ $attributes['slug'] ] = true; - - $content = do_blocks( $content ); - - global $wp_embed; - $content = $wp_embed->autoembed( $content ); - - unset( $seen_refs[ $attributes['slug'] ] ); - return $content; -} - -add_action( 'init', 'register_block_core_pattern' ); diff --git a/src/wp-includes/blocks/pattern/block.json b/src/wp-includes/blocks/pattern/block.json deleted file mode 100644 index 2a761dfd643ba..0000000000000 --- a/src/wp-includes/blocks/pattern/block.json +++ /dev/null @@ -1,23 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/pattern", - "title": "Pattern Placeholder", - "category": "theme", - "description": "Show a block pattern.", - "supports": { - "html": false, - "inserter": false, - "renaming": false, - "blockVisibility": false, - "interactivity": { - "clientNavigation": true - } - }, - "textdomain": "default", - "attributes": { - "slug": { - "type": "string" - } - } -} diff --git a/src/wp-includes/blocks/post-author-biography.php b/src/wp-includes/blocks/post-author-biography.php deleted file mode 100644 index bd983f79e7609..0000000000000 --- a/src/wp-includes/blocks/post-author-biography.php +++ /dev/null @@ -1,53 +0,0 @@ -context['postId'] ) ) { - $author_id = get_post_field( 'post_author', $block->context['postId'] ); - } else { - $author_id = get_query_var( 'author' ); - } - - if ( empty( $author_id ) ) { - return ''; - } - - $author_biography = get_the_author_meta( 'description', $author_id ); - if ( empty( $author_biography ) ) { - return ''; - } - - $align_class_name = empty( $attributes['textAlign'] ) ? '' : "has-text-align-{$attributes['textAlign']}"; - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => $align_class_name ) ); - - return sprintf( '
      ', $wrapper_attributes ) . $author_biography . '
      '; -} - -/** - * Registers the `core/post-author-biography` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_post_author_biography() { - register_block_type_from_metadata( - __DIR__ . '/post-author-biography', - array( - 'render_callback' => 'render_block_core_post_author_biography', - ) - ); -} -add_action( 'init', 'register_block_core_post_author_biography' ); diff --git a/src/wp-includes/blocks/post-author-biography/block.json b/src/wp-includes/blocks/post-author-biography/block.json deleted file mode 100644 index c6e27bc484dfd..0000000000000 --- a/src/wp-includes/blocks/post-author-biography/block.json +++ /dev/null @@ -1,61 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-author-biography", - "title": "Author Biography", - "category": "theme", - "description": "The author biography.", - "textdomain": "default", - "attributes": { - "textAlign": { - "type": "string" - } - }, - "usesContext": [ "postType", "postId" ], - "example": { - "viewportWidth": 350 - }, - "supports": { - "spacing": { - "margin": true, - "padding": true - }, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "style": "wp-block-post-author-biography" -} diff --git a/src/wp-includes/blocks/post-author-name.php b/src/wp-includes/blocks/post-author-name.php deleted file mode 100644 index ac514401f5cc2..0000000000000 --- a/src/wp-includes/blocks/post-author-name.php +++ /dev/null @@ -1,63 +0,0 @@ -context['postId'] ) ) { - $author_id = get_post_field( 'post_author', $block->context['postId'] ); - } else { - $author_id = get_query_var( 'author' ); - } - - if ( empty( $author_id ) ) { - return ''; - } - - if ( isset( $block->context['postType'] ) && ! post_type_supports( $block->context['postType'], 'author' ) ) { - return ''; - } - - $author_name = get_the_author_meta( 'display_name', $author_id ); - if ( isset( $attributes['isLink'] ) && $attributes['isLink'] ) { - $author_name = sprintf( '', get_author_posts_url( $author_id ), esc_attr( $attributes['linkTarget'] ), $author_name ); - } - - $classes = array(); - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - - return sprintf( '
      %2$s
      ', $wrapper_attributes, $author_name ); -} - -/** - * Registers the `core/post-author-name` block on the server. - * - * @since 6.2.0 - */ -function register_block_core_post_author_name() { - register_block_type_from_metadata( - __DIR__ . '/post-author-name', - array( - 'render_callback' => 'render_block_core_post_author_name', - ) - ); -} -add_action( 'init', 'register_block_core_post_author_name' ); diff --git a/src/wp-includes/blocks/post-author-name/block.json b/src/wp-includes/blocks/post-author-name/block.json deleted file mode 100644 index 23211f0bf5bf4..0000000000000 --- a/src/wp-includes/blocks/post-author-name/block.json +++ /dev/null @@ -1,73 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-author-name", - "title": "Author Name", - "category": "theme", - "description": "The author name.", - "textdomain": "default", - "attributes": { - "textAlign": { - "type": "string" - }, - "isLink": { - "type": "boolean", - "default": false, - "role": "content" - }, - "linkTarget": { - "type": "string", - "default": "_self", - "role": "content" - } - }, - "usesContext": [ "postType", "postId" ], - "example": { - "viewportWidth": 350 - }, - "supports": { - "html": false, - "spacing": { - "margin": true, - "padding": true - }, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "style": "wp-block-post-author-name" -} diff --git a/src/wp-includes/blocks/post-author.php b/src/wp-includes/blocks/post-author.php deleted file mode 100644 index a4880f8a9e744..0000000000000 --- a/src/wp-includes/blocks/post-author.php +++ /dev/null @@ -1,81 +0,0 @@ -context['postId'] ) ) { - $author_id = get_query_var( 'author' ); - } else { - $author_id = get_post_field( 'post_author', $block->context['postId'] ); - } - - if ( empty( $author_id ) ) { - return ''; - } - - if ( isset( $block->context['postType'] ) && ! post_type_supports( $block->context['postType'], 'author' ) ) { - return ''; - } - - $avatar = ! empty( $attributes['avatarSize'] ) ? get_avatar( - $author_id, - $attributes['avatarSize'] - ) : null; - - $link = get_author_posts_url( $author_id ); - $author_name = get_the_author_meta( 'display_name', $author_id ); - if ( ! empty( $attributes['isLink'] && ! empty( $attributes['linkTarget'] ) ) ) { - $author_name = sprintf( '%3$s', esc_url( $link ), esc_attr( $attributes['linkTarget'] ), $author_name ); - } - - $byline = ! empty( $attributes['byline'] ) ? $attributes['byline'] : false; - $classes = array(); - if ( isset( $attributes['itemsJustification'] ) ) { - $classes[] = 'items-justified-' . $attributes['itemsJustification']; - } - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - - return sprintf( '
      ', $wrapper_attributes ) . - ( ! empty( $attributes['showAvatar'] ) ? '' : '' ) . - '' . - '
      '; -} - -/** - * Registers the `core/post-author` block on the server. - * - * @since 5.9.0 - */ -function register_block_core_post_author() { - register_block_type_from_metadata( - __DIR__ . '/post-author', - array( - 'render_callback' => 'render_block_core_post_author', - ) - ); -} -add_action( 'init', 'register_block_core_post_author' ); diff --git a/src/wp-includes/blocks/post-author/block.json b/src/wp-includes/blocks/post-author/block.json deleted file mode 100644 index a83bb48bd840a..0000000000000 --- a/src/wp-includes/blocks/post-author/block.json +++ /dev/null @@ -1,92 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-author", - "title": "Author", - "category": "theme", - "description": "Display post author details such as name, avatar, and bio.", - "textdomain": "default", - "attributes": { - "textAlign": { - "type": "string" - }, - "avatarSize": { - "type": "number", - "default": 48 - }, - "showAvatar": { - "type": "boolean", - "default": true - }, - "showBio": { - "type": "boolean" - }, - "byline": { - "type": "string" - }, - "isLink": { - "type": "boolean", - "default": false, - "role": "content" - }, - "linkTarget": { - "type": "string", - "default": "_self", - "role": "content" - } - }, - "usesContext": [ "postType", "postId", "queryId" ], - "supports": { - "html": false, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - }, - "filter": { - "duotone": true - } - }, - "selectors": { - "filter": { - "duotone": ".wp-block-post-author .wp-block-post-author__avatar img" - } - }, - "editorStyle": "wp-block-post-author-editor", - "style": "wp-block-post-author" -} diff --git a/src/wp-includes/blocks/post-comments-count.php b/src/wp-includes/blocks/post-comments-count.php deleted file mode 100644 index bf12d6f0f9c4c..0000000000000 --- a/src/wp-includes/blocks/post-comments-count.php +++ /dev/null @@ -1,49 +0,0 @@ -context['postId'] ) ) { - return ''; - } - - $classes = ''; - if ( isset( $attributes['textAlign'] ) ) { - $classes .= 'has-text-align-' . $attributes['textAlign']; - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => $classes ) ); - return sprintf( - '
      %2$s
      ', - $wrapper_attributes, - get_comments_number( $block->context['postId'] ) - ); -} - -/** - * Registers the `core/post-comments-count` block on the server. - * - * @since 6.9.0 - */ -function register_block_core_post_comments_count() { - register_block_type_from_metadata( - __DIR__ . '/post-comments-count', - array( - 'render_callback' => 'render_block_core_post_comments_count', - ) - ); -} -add_action( 'init', 'register_block_core_post_comments_count' ); diff --git a/src/wp-includes/blocks/post-comments-count/block.json b/src/wp-includes/blocks/post-comments-count/block.json deleted file mode 100644 index fa8ade2f2c12f..0000000000000 --- a/src/wp-includes/blocks/post-comments-count/block.json +++ /dev/null @@ -1,55 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-comments-count", - "title": "Comments Count", - "category": "theme", - "description": "Display a post's comments count.", - "textdomain": "default", - "attributes": { - "textAlign": { - "type": "string" - } - }, - "usesContext": [ "postId" ], - "example": { - "viewportWidth": 350 - }, - "supports": { - "html": false, - "color": { - "gradients": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true - }, - "interactivity": { - "clientNavigation": true - } - }, - "style": "wp-block-post-comments-count" -} diff --git a/src/wp-includes/blocks/post-comments-form.php b/src/wp-includes/blocks/post-comments-form.php deleted file mode 100644 index dfbf4c59f264a..0000000000000 --- a/src/wp-includes/blocks/post-comments-form.php +++ /dev/null @@ -1,88 +0,0 @@ -context['postId'] ) ) { - return ''; - } - - if ( post_password_required( $block->context['postId'] ) ) { - return; - } - - $classes = array( 'comment-respond' ); // See comment further below. - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - - add_filter( 'comment_form_defaults', 'post_comments_form_block_form_defaults' ); - - ob_start(); - comment_form( array(), $block->context['postId'] ); - $form = ob_get_clean(); - - remove_filter( 'comment_form_defaults', 'post_comments_form_block_form_defaults' ); - - // We use the outermost wrapping `
      ` returned by `comment_form()` - // which is identified by its default classname `comment-respond` to inject - // our wrapper attributes. This way, it is guaranteed that all styling applied - // to the block is carried along when the comment form is moved to the location - // of the 'Reply' link that the user clicked by Core's `comment-reply.js` script. - $form = str_replace( 'class="comment-respond"', $wrapper_attributes, $form ); - - // Enqueue the comment-reply script. - wp_enqueue_script( 'comment-reply' ); - - return $form; -} - -/** - * Registers the `core/post-comments-form` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_post_comments_form() { - register_block_type_from_metadata( - __DIR__ . '/post-comments-form', - array( - 'render_callback' => 'render_block_core_post_comments_form', - ) - ); -} -add_action( 'init', 'register_block_core_post_comments_form' ); - -/** - * Use the button block classes for the form-submit button. - * - * @since 6.0.0 - * - * @param array $fields The default comment form arguments. - * - * @return array Returns the modified fields. - */ -function post_comments_form_block_form_defaults( $fields ) { - if ( wp_is_block_theme() ) { - $fields['submit_button'] = ''; - $fields['submit_field'] = '

      %1$s %2$s

      '; - } - - return $fields; -} diff --git a/src/wp-includes/blocks/post-comments-form/block.json b/src/wp-includes/blocks/post-comments-form/block.json deleted file mode 100644 index 4b6b333b75cfa..0000000000000 --- a/src/wp-includes/blocks/post-comments-form/block.json +++ /dev/null @@ -1,65 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-comments-form", - "title": "Comments Form", - "category": "theme", - "description": "Display a post's comments form.", - "textdomain": "default", - "attributes": { - "textAlign": { - "type": "string" - } - }, - "usesContext": [ "postId", "postType" ], - "supports": { - "html": false, - "color": { - "gradients": true, - "heading": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontStyle": true, - "__experimentalFontWeight": true, - "__experimentalLetterSpacing": true, - "__experimentalTextTransform": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "editorStyle": "wp-block-post-comments-form-editor", - "style": [ - "wp-block-post-comments-form", - "wp-block-buttons", - "wp-block-button" - ], - "example": { - "attributes": { - "textAlign": "center" - } - } -} diff --git a/src/wp-includes/blocks/post-comments-link.php b/src/wp-includes/blocks/post-comments-link.php deleted file mode 100644 index c6d33eb0cd65c..0000000000000 --- a/src/wp-includes/blocks/post-comments-link.php +++ /dev/null @@ -1,75 +0,0 @@ -context['postId'] ) || - isset( $block->context['postId'] ) && - ! comments_open( $block->context['postId'] ) - ) { - return ''; - } - - $classes = array(); - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - $comments_number = (int) get_comments_number( $block->context['postId'] ); - $comments_link = get_comments_link( $block->context['postId'] ); - $post_title = get_the_title( $block->context['postId'] ); - $comment_html = ''; - - if ( 0 === $comments_number ) { - $comment_html = sprintf( - /* translators: %s post title */ - __( 'No comments on %s' ), - $post_title - ); - } else { - $comment_html = sprintf( - /* translators: 1: Number of comments, 2: post title */ - _n( - '%1$s comment on %2$s', - '%1$s comments on %2$s', - $comments_number - ), - esc_html( number_format_i18n( $comments_number ) ), - $post_title - ); - } - - return ''; -} - -/** - * Registers the `core/post-comments-link` block on the server. - * - * @since 6.9.0 - */ -function register_block_core_post_comments_link() { - register_block_type_from_metadata( - __DIR__ . '/post-comments-link', - array( - 'render_callback' => 'render_block_core_post_comments_link', - ) - ); -} -add_action( 'init', 'register_block_core_post_comments_link' ); diff --git a/src/wp-includes/blocks/post-comments-link/block.json b/src/wp-includes/blocks/post-comments-link/block.json deleted file mode 100644 index e0dcdb9afa03d..0000000000000 --- a/src/wp-includes/blocks/post-comments-link/block.json +++ /dev/null @@ -1,62 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-comments-link", - "title": "Comments Link", - "category": "theme", - "description": "Displays the link to the current post comments.", - "textdomain": "default", - "usesContext": [ "postType", "postId" ], - "attributes": { - "textAlign": { - "type": "string" - } - }, - "example": { - "viewportWidth": 350 - }, - "supports": { - "html": false, - "color": { - "link": true, - "text": false, - "__experimentalDefaultControls": { - "background": true, - "link": true - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "style": "wp-block-post-comments-link" -} diff --git a/src/wp-includes/blocks/post-content.php b/src/wp-includes/blocks/post-content.php deleted file mode 100644 index 0be1a8730f605..0000000000000 --- a/src/wp-includes/blocks/post-content.php +++ /dev/null @@ -1,86 +0,0 @@ -context['postId'] ) ) { - return ''; - } - - $post_id = $block->context['postId']; - - if ( isset( $seen_ids[ $post_id ] ) ) { - // WP_DEBUG_DISPLAY must only be honored when WP_DEBUG. This precedent - // is set in `wp_debug_mode()`. - $is_debug = WP_DEBUG && WP_DEBUG_DISPLAY; - - return $is_debug ? - // translators: Visible only in the front end, this warning takes the place of a faulty block. - __( '[block rendering halted]' ) : - ''; - } - - $seen_ids[ $post_id ] = true; - - // When inside the main loop, we want to use queried object - // so that `the_preview` for the current post can apply. - // We force this behavior by omitting the third argument (post ID) from the `get_the_content`. - $content = get_the_content(); - // Check for nextpage to display page links for paginated posts. - if ( has_block( 'core/nextpage' ) ) { - $content .= wp_link_pages( array( 'echo' => 0 ) ); - } - - /** This filter is documented in wp-includes/post-template.php */ - $content = apply_filters( 'the_content', str_replace( ']]>', ']]>', $content ) ); - unset( $seen_ids[ $post_id ] ); - - if ( empty( $content ) ) { - return ''; - } - - $tag_name = 'div'; - - if ( ! empty( $attributes['tagName'] ) && tag_escape( $attributes['tagName'] ) === $attributes['tagName'] ) { - $tag_name = $attributes['tagName']; - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => 'entry-content' ) ); - - return sprintf( - '<%1$s %2$s>%3$s', - $tag_name, - $wrapper_attributes, - $content - ); -} - -/** - * Registers the `core/post-content` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_post_content() { - register_block_type_from_metadata( - __DIR__ . '/post-content', - array( - 'render_callback' => 'render_block_core_post_content', - ) - ); -} -add_action( 'init', 'register_block_core_post_content' ); diff --git a/src/wp-includes/blocks/post-content/block.json b/src/wp-includes/blocks/post-content/block.json deleted file mode 100644 index 264f6959304fe..0000000000000 --- a/src/wp-includes/blocks/post-content/block.json +++ /dev/null @@ -1,82 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-content", - "title": "Content", - "category": "theme", - "description": "Displays the contents of a post or page.", - "textdomain": "default", - "usesContext": [ "postId", "postType", "queryId" ], - "attributes": { - "tagName": { - "type": "string", - "default": "div" - } - }, - "example": { - "viewportWidth": 350 - }, - "supports": { - "align": [ "wide", "full" ], - "html": false, - "layout": true, - "background": { - "backgroundImage": true, - "backgroundSize": true, - "__experimentalDefaultControls": { - "backgroundImage": true - } - }, - "dimensions": { - "minHeight": true - }, - "spacing": { - "blockGap": true, - "padding": true, - "margin": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "color": { - "gradients": true, - "heading": true, - "link": true, - "__experimentalDefaultControls": { - "background": false, - "text": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "style": "wp-block-post-content", - "editorStyle": "wp-block-post-content-editor" -} diff --git a/src/wp-includes/blocks/post-date.php b/src/wp-includes/blocks/post-date.php deleted file mode 100644 index e12a26eda7c12..0000000000000 --- a/src/wp-includes/blocks/post-date.php +++ /dev/null @@ -1,109 +0,0 @@ - 'modified', - ); - } else { - $source_args = array( - 'field' => 'date', - ); - } - $attributes['datetime'] = $source->get_value( $source_args, $block, 'datetime' ); - } - - if ( isset( $source_args['field'] ) && 'modified' === $source_args['field'] ) { - $classes[] = 'wp-block-post-date__modified-date'; - } - - if ( empty( $attributes['datetime'] ) ) { - // If the `datetime` attribute is set but empty, it could be because Block Bindings - // set it that way. This can happen e.g. if the block is bound to the - // post's last modified date, and the latter lies before the publish date. - // (See https://github.com/WordPress/gutenberg/pull/46839 where this logic was originally - // implemented.) - // In this case, we have to respect and return the empty value. - return ''; - } - - $unformatted_date = $attributes['datetime']; - $post_timestamp = strtotime( $unformatted_date ); - - if ( isset( $attributes['format'] ) && 'human-diff' === $attributes['format'] ) { - if ( $post_timestamp > time() ) { - // translators: %s: human-readable time difference. - $formatted_date = sprintf( __( '%s from now' ), human_time_diff( $post_timestamp ) ); - } else { - // translators: %s: human-readable time difference. - $formatted_date = sprintf( __( '%s ago' ), human_time_diff( $post_timestamp ) ); - } - } else { - $format = empty( $attributes['format'] ) ? get_option( 'date_format' ) : $attributes['format']; - $formatted_date = wp_date( $format, $post_timestamp ); - } - - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - - if ( isset( $attributes['isLink'] ) && $attributes['isLink'] && isset( $block->context['postId'] ) ) { - $formatted_date = sprintf( '%2s', get_the_permalink( $block->context['postId'] ), $formatted_date ); - } - - return sprintf( - '
      ', - $wrapper_attributes, - $unformatted_date, - $formatted_date - ); -} - -/** - * Registers the `core/post-date` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_post_date() { - register_block_type_from_metadata( - __DIR__ . '/post-date', - array( - 'render_callback' => 'render_block_core_post_date', - ) - ); -} -add_action( 'init', 'register_block_core_post_date' ); diff --git a/src/wp-includes/blocks/post-date/block.json b/src/wp-includes/blocks/post-date/block.json deleted file mode 100644 index ea99f6ab5ff8d..0000000000000 --- a/src/wp-includes/blocks/post-date/block.json +++ /dev/null @@ -1,74 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-date", - "title": "Date", - "category": "theme", - "description": "Display a custom date.", - "textdomain": "default", - "attributes": { - "datetime": { - "type": "string", - "role": "content" - }, - "textAlign": { - "type": "string" - }, - "format": { - "type": "string" - }, - "isLink": { - "type": "boolean", - "default": false, - "role": "content" - } - }, - "usesContext": [ "postId", "postType", "queryId" ], - "example": { - "viewportWidth": 350 - }, - "supports": { - "html": false, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - } -} diff --git a/src/wp-includes/blocks/post-excerpt.php b/src/wp-includes/blocks/post-excerpt.php deleted file mode 100644 index 28aab46a01294..0000000000000 --- a/src/wp-includes/blocks/post-excerpt.php +++ /dev/null @@ -1,103 +0,0 @@ -context['postId'] ) ) { - return ''; - } - - $more_text = ! empty( $attributes['moreText'] ) ? '' . wp_kses_post( $attributes['moreText'] ) . '' : ''; - $filter_excerpt_more = static function ( $more ) use ( $more_text ) { - return empty( $more_text ) ? $more : ''; - }; - /** - * Some themes might use `excerpt_more` filter to handle the - * `more` link displayed after a trimmed excerpt. Since the - * block has a `more text` attribute we have to check and - * override if needed the return value from this filter. - * So if the block's attribute is not empty override the - * `excerpt_more` filter and return nothing. This will - * result in showing only one `read more` link at a time. - * - * This hook needs to be applied before the excerpt is retrieved with get_the_excerpt. - * Otherwise, the read more link filter from the theme is not removed. - */ - add_filter( 'excerpt_more', $filter_excerpt_more ); - - /* - * The purpose of the excerpt length setting is to limit the length of both - * automatically generated and user-created excerpts. - * Because the excerpt_length filter only applies to auto generated excerpts, - * wp_trim_words is used instead. - */ - $excerpt_length = $attributes['excerptLength']; - $excerpt = get_the_excerpt( $block->context['postId'] ); - if ( isset( $excerpt_length ) ) { - $excerpt = wp_trim_words( $excerpt, $excerpt_length ); - } - - $classes = array(); - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - - $content = '

      ' . $excerpt; - $show_more_on_new_line = ! isset( $attributes['showMoreOnNewLine'] ) || $attributes['showMoreOnNewLine']; - if ( $show_more_on_new_line && ! empty( $more_text ) ) { - $content .= '

      ' . $more_text . '

      '; - } else { - $content .= " $more_text

      "; - } - remove_filter( 'excerpt_more', $filter_excerpt_more ); - return sprintf( '
      %2$s
      ', $wrapper_attributes, $content ); -} - -/** - * Registers the `core/post-excerpt` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_post_excerpt() { - register_block_type_from_metadata( - __DIR__ . '/post-excerpt', - array( - 'render_callback' => 'render_block_core_post_excerpt', - ) - ); -} -add_action( 'init', 'register_block_core_post_excerpt' ); - -/** - * If themes or plugins filter the excerpt_length, we need to - * override the filter in the editor, otherwise - * the excerpt length block setting has no effect. - * Returns 100 because 100 is the max length in the setting. - */ -if ( is_admin() || - defined( 'REST_REQUEST' ) && REST_REQUEST ) { - add_filter( - 'excerpt_length', - static function () { - return 100; - }, - PHP_INT_MAX - ); -} diff --git a/src/wp-includes/blocks/post-excerpt/block.json b/src/wp-includes/blocks/post-excerpt/block.json deleted file mode 100644 index c0037b0e5b39c..0000000000000 --- a/src/wp-includes/blocks/post-excerpt/block.json +++ /dev/null @@ -1,76 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-excerpt", - "title": "Excerpt", - "category": "theme", - "description": "Display the excerpt.", - "textdomain": "default", - "attributes": { - "textAlign": { - "type": "string" - }, - "moreText": { - "type": "string", - "role": "content" - }, - "showMoreOnNewLine": { - "type": "boolean", - "default": true - }, - "excerptLength": { - "type": "number", - "default": 55 - } - }, - "usesContext": [ "postId", "postType", "queryId" ], - "example": { - "viewportWidth": 350 - }, - "supports": { - "html": false, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "editorStyle": "wp-block-post-excerpt-editor", - "style": "wp-block-post-excerpt" -} diff --git a/src/wp-includes/blocks/post-featured-image.php b/src/wp-includes/blocks/post-featured-image.php deleted file mode 100644 index dc8bcba194a79..0000000000000 --- a/src/wp-includes/blocks/post-featured-image.php +++ /dev/null @@ -1,269 +0,0 @@ -context['postId'] ) ) { - return ''; - } - $post_ID = $block->context['postId']; - - $is_link = isset( $attributes['isLink'] ) && $attributes['isLink']; - $size_slug = isset( $attributes['sizeSlug'] ) ? $attributes['sizeSlug'] : 'post-thumbnail'; - $attr = get_block_core_post_featured_image_border_attributes( $attributes ); - $overlay_markup = get_block_core_post_featured_image_overlay_element_markup( $attributes ); - - if ( $is_link ) { - $title = get_the_title( $post_ID ); - if ( $title ) { - $attr['alt'] = trim( strip_tags( $title ) ); - } else { - $attr['alt'] = sprintf( - // translators: %d is the post ID. - __( 'Untitled post %d' ), - $post_ID - ); - } - } - - $extra_styles = ''; - - // Aspect ratio with a height set needs to override the default width/height. - if ( ! empty( $attributes['aspectRatio'] ) ) { - $extra_styles .= 'width:100%;height:100%;'; - } elseif ( ! empty( $attributes['height'] ) ) { - $extra_styles .= "height:{$attributes['height']};"; - } - - if ( ! empty( $attributes['scale'] ) ) { - $extra_styles .= "object-fit:{$attributes['scale']};"; - } - if ( ! empty( $attributes['style']['shadow'] ) ) { - $shadow_styles = wp_style_engine_get_styles( array( 'shadow' => $attributes['style']['shadow'] ) ); - - if ( ! empty( $shadow_styles['css'] ) ) { - $extra_styles .= $shadow_styles['css']; - } - } - - if ( ! empty( $extra_styles ) ) { - $attr['style'] = empty( $attr['style'] ) ? $extra_styles : $attr['style'] . $extra_styles; - } - - $featured_image = get_the_post_thumbnail( $post_ID, $size_slug, $attr ); - - // Get the first image from the post. - if ( $attributes['useFirstImageFromPost'] && ! $featured_image ) { - $content_post = get_post( $post_ID ); - $content = $content_post->post_content; - $processor = new WP_HTML_Tag_Processor( $content ); - - /* - * Transfer the image tag from the post into a new text snippet. - * Because the HTML API doesn't currently expose a way to extract - * HTML substrings this is necessary as a workaround. Of note, this - * is different than directly extracting the IMG tag: - * - If there are duplicate attributes in the source there will only be one in the output. - * - If there are single-quoted or unquoted attributes they will be double-quoted in the output. - * - If there are named character references in the attribute values they may be replaced with their direct code points. E.g. `…` becomes `…`. - * In the future there will likely be a mechanism to copy snippets of HTML from - * one document into another, via the HTML Processor's `get_outer_html()` or - * equivalent. When that happens it would be appropriate to replace this custom - * code with that canonical code. - */ - if ( $processor->next_tag( 'img' ) ) { - $tag_html = new WP_HTML_Tag_Processor( '' ); - $tag_html->next_tag(); - foreach ( $processor->get_attribute_names_with_prefix( '' ) as $name ) { - $tag_html->set_attribute( $name, $processor->get_attribute( $name ) ); - } - $featured_image = $tag_html->get_updated_html(); - } - } - - if ( ! $featured_image ) { - return ''; - } - - if ( $is_link ) { - $link_target = $attributes['linkTarget']; - $rel = ! empty( $attributes['rel'] ) ? 'rel="' . esc_attr( $attributes['rel'] ) . '"' : ''; - $height = ! empty( $attributes['height'] ) ? 'style="' . esc_attr( safecss_filter_attr( 'height:' . $attributes['height'] ) ) . '"' : ''; - $featured_image = sprintf( - '%5$s%6$s', - get_the_permalink( $post_ID ), - esc_attr( $link_target ), - $rel, - $height, - $featured_image, - $overlay_markup - ); - } else { - $featured_image = $featured_image . $overlay_markup; - } - - $aspect_ratio = ! empty( $attributes['aspectRatio'] ) - ? esc_attr( safecss_filter_attr( 'aspect-ratio:' . $attributes['aspectRatio'] ) ) . ';' - : ''; - $width = ! empty( $attributes['width'] ) - ? esc_attr( safecss_filter_attr( 'width:' . $attributes['width'] ) ) . ';' - : ''; - $height = ! empty( $attributes['height'] ) - ? esc_attr( safecss_filter_attr( 'height:' . $attributes['height'] ) ) . ';' - : ''; - if ( ! $height && ! $width && ! $aspect_ratio ) { - $wrapper_attributes = get_block_wrapper_attributes(); - } else { - $wrapper_attributes = get_block_wrapper_attributes( array( 'style' => $aspect_ratio . $width . $height ) ); - } - return "
      {$featured_image}
      "; -} - -/** - * Generate markup for the HTML element that will be used for the overlay. - * - * @since 6.1.0 - * - * @param array $attributes Block attributes. - * - * @return string HTML markup in string format. - */ -function get_block_core_post_featured_image_overlay_element_markup( $attributes ) { - $has_dim_background = isset( $attributes['dimRatio'] ) && $attributes['dimRatio']; - $has_gradient = isset( $attributes['gradient'] ) && $attributes['gradient']; - $has_custom_gradient = isset( $attributes['customGradient'] ) && $attributes['customGradient']; - $has_solid_overlay = isset( $attributes['overlayColor'] ) && $attributes['overlayColor']; - $has_custom_overlay = isset( $attributes['customOverlayColor'] ) && $attributes['customOverlayColor']; - $class_names = array( 'wp-block-post-featured-image__overlay' ); - $styles = array(); - - if ( ! $has_dim_background ) { - return ''; - } - - // Apply border classes and styles. - $border_attributes = get_block_core_post_featured_image_border_attributes( $attributes ); - - if ( ! empty( $border_attributes['class'] ) ) { - $class_names[] = $border_attributes['class']; - } - - if ( ! empty( $border_attributes['style'] ) ) { - $styles[] = $border_attributes['style']; - } - - // Apply overlay and gradient classes. - if ( $has_dim_background ) { - $class_names[] = 'has-background-dim'; - $class_names[] = "has-background-dim-{$attributes['dimRatio']}"; - } - - if ( $has_solid_overlay ) { - $class_names[] = "has-{$attributes['overlayColor']}-background-color"; - } - - if ( $has_gradient || $has_custom_gradient ) { - $class_names[] = 'has-background-gradient'; - } - - if ( $has_gradient ) { - $class_names[] = "has-{$attributes['gradient']}-gradient-background"; - } - - // Apply background styles. - if ( $has_custom_gradient ) { - $styles[] = sprintf( 'background-image: %s;', $attributes['customGradient'] ); - } - - if ( $has_custom_overlay ) { - $styles[] = sprintf( 'background-color: %s;', $attributes['customOverlayColor'] ); - } - - return sprintf( - '', - esc_attr( implode( ' ', $class_names ) ), - esc_attr( safecss_filter_attr( implode( ' ', $styles ) ) ) - ); -} - -/** - * Generates class names and styles to apply the border support styles for - * the Post Featured Image block. - * - * @since 6.1.0 - * - * @param array $attributes The block attributes. - * @return array The border-related classnames and styles for the block. - */ -function get_block_core_post_featured_image_border_attributes( $attributes ) { - $border_styles = array(); - $sides = array( 'top', 'right', 'bottom', 'left' ); - - // Border radius. - if ( isset( $attributes['style']['border']['radius'] ) ) { - $border_styles['radius'] = $attributes['style']['border']['radius']; - } - - // Border style. - if ( isset( $attributes['style']['border']['style'] ) ) { - $border_styles['style'] = $attributes['style']['border']['style']; - } - - // Border width. - if ( isset( $attributes['style']['border']['width'] ) ) { - $border_styles['width'] = $attributes['style']['border']['width']; - } - - // Border color. - $preset_color = array_key_exists( 'borderColor', $attributes ) ? "var:preset|color|{$attributes['borderColor']}" : null; - $custom_color = $attributes['style']['border']['color'] ?? null; - $border_styles['color'] = $preset_color ? $preset_color : $custom_color; - - // Individual border styles e.g. top, left etc. - foreach ( $sides as $side ) { - $border = $attributes['style']['border'][ $side ] ?? null; - $border_styles[ $side ] = array( - 'color' => isset( $border['color'] ) ? $border['color'] : null, - 'style' => isset( $border['style'] ) ? $border['style'] : null, - 'width' => isset( $border['width'] ) ? $border['width'] : null, - ); - } - - $styles = wp_style_engine_get_styles( array( 'border' => $border_styles ) ); - $attributes = array(); - if ( ! empty( $styles['classnames'] ) ) { - $attributes['class'] = $styles['classnames']; - } - if ( ! empty( $styles['css'] ) ) { - $attributes['style'] = $styles['css']; - } - return $attributes; -} - -/** - * Registers the `core/post-featured-image` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_post_featured_image() { - register_block_type_from_metadata( - __DIR__ . '/post-featured-image', - array( - 'render_callback' => 'render_block_core_post_featured_image', - ) - ); -} -add_action( 'init', 'register_block_core_post_featured_image' ); diff --git a/src/wp-includes/blocks/post-featured-image/block.json b/src/wp-includes/blocks/post-featured-image/block.json deleted file mode 100644 index 3cd144caa0cf4..0000000000000 --- a/src/wp-includes/blocks/post-featured-image/block.json +++ /dev/null @@ -1,108 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-featured-image", - "title": "Featured Image", - "category": "theme", - "description": "Display a post's featured image.", - "textdomain": "default", - "attributes": { - "isLink": { - "type": "boolean", - "default": false, - "role": "content" - }, - "aspectRatio": { - "type": "string" - }, - "width": { - "type": "string" - }, - "height": { - "type": "string" - }, - "scale": { - "type": "string", - "default": "cover" - }, - "sizeSlug": { - "type": "string" - }, - "rel": { - "type": "string", - "attribute": "rel", - "default": "", - "role": "content" - }, - "linkTarget": { - "type": "string", - "default": "_self", - "role": "content" - }, - "overlayColor": { - "type": "string" - }, - "customOverlayColor": { - "type": "string" - }, - "dimRatio": { - "type": "number", - "default": 0 - }, - "gradient": { - "type": "string" - }, - "customGradient": { - "type": "string" - }, - "useFirstImageFromPost": { - "type": "boolean", - "default": false - } - }, - "usesContext": [ "postId", "postType", "queryId" ], - "example": { - "viewportWidth": 350 - }, - "supports": { - "align": [ "left", "right", "center", "wide", "full" ], - "color": { - "text": false, - "background": false - }, - "__experimentalBorder": { - "color": true, - "radius": true, - "width": true, - "__experimentalSkipSerialization": true, - "__experimentalDefaultControls": { - "color": true, - "radius": true, - "width": true - } - }, - "filter": { - "duotone": true - }, - "shadow": { - "__experimentalSkipSerialization": true - }, - "html": false, - "spacing": { - "margin": true, - "padding": true - }, - "interactivity": { - "clientNavigation": true - } - }, - "selectors": { - "border": ".wp-block-post-featured-image img, .wp-block-post-featured-image .block-editor-media-placeholder, .wp-block-post-featured-image .wp-block-post-featured-image__overlay", - "shadow": ".wp-block-post-featured-image img, .wp-block-post-featured-image .components-placeholder", - "filter": { - "duotone": ".wp-block-post-featured-image img, .wp-block-post-featured-image .wp-block-post-featured-image__placeholder, .wp-block-post-featured-image .components-placeholder__illustration, .wp-block-post-featured-image .components-placeholder::before" - } - }, - "editorStyle": "wp-block-post-featured-image-editor", - "style": "wp-block-post-featured-image" -} diff --git a/src/wp-includes/blocks/post-navigation-link.php b/src/wp-includes/blocks/post-navigation-link.php deleted file mode 100644 index 8162b74d8af17..0000000000000 --- a/src/wp-includes/blocks/post-navigation-link.php +++ /dev/null @@ -1,139 +0,0 @@ - $classes, - ) - ); - // Set default values. - $format = '%link'; - $link = 'next' === $navigation_type ? _x( 'Next', 'label for next post link' ) : _x( 'Previous', 'label for previous post link' ); - $label = ''; - - // Only use hardcoded values here, otherwise we need to add escaping where these values are used. - $arrow_map = array( - 'none' => '', - 'arrow' => array( - 'next' => '→', - 'previous' => '←', - ), - 'chevron' => array( - 'next' => '»', - 'previous' => '«', - ), - ); - - // If a custom label is provided, make this a link. - // `$label` is used to prepend the provided label, if we want to show the page title as well. - if ( isset( $attributes['label'] ) && ! empty( $attributes['label'] ) ) { - $label = "{$attributes['label']}"; - $link = $label; - } - - // If we want to also show the page title, make the page title a link and prepend the label. - if ( isset( $attributes['showTitle'] ) && $attributes['showTitle'] ) { - /* - * If the label link option is not enabled but there is a custom label, - * display the custom label as text before the linked title. - */ - if ( ! $attributes['linkLabel'] ) { - if ( $label ) { - $format = '' . wp_kses_post( $label ) . ' %link'; - } - $link = '%title'; - } elseif ( isset( $attributes['linkLabel'] ) && $attributes['linkLabel'] ) { - // If the label link option is enabled and there is a custom label, display it before the title. - if ( $label ) { - $link = '' . wp_kses_post( $label ) . ' %title'; - } else { - /* - * If the label link option is enabled and there is no custom label, - * add a colon between the label and the post title. - */ - $label = 'next' === $navigation_type ? _x( 'Next:', 'label before the title of the next post' ) : _x( 'Previous:', 'label before the title of the previous post' ); - $link = sprintf( - '%1$s %2$s', - wp_kses_post( $label ), - '%title' - ); - } - } - } - - // Display arrows. - if ( isset( $attributes['arrow'] ) && 'none' !== $attributes['arrow'] && isset( $arrow_map[ $attributes['arrow'] ] ) ) { - $arrow = $arrow_map[ $attributes['arrow'] ][ $navigation_type ]; - - if ( 'next' === $navigation_type ) { - $format = '%link'; - } else { - $format = '%link'; - } - } - - /* - * The dynamic portion of the function name, `$navigation_type`, - * Refers to the type of adjacency, 'next' or 'previous'. - * - * @see https://developer.wordpress.org/reference/functions/get_previous_post_link/ - * @see https://developer.wordpress.org/reference/functions/get_next_post_link/ - */ - $get_link_function = "get_{$navigation_type}_post_link"; - - if ( ! empty( $attributes['taxonomy'] ) ) { - $content = $get_link_function( $format, $link, true, '', $attributes['taxonomy'] ); - } else { - $content = $get_link_function( $format, $link ); - } - - return sprintf( - '
      %2$s
      ', - $wrapper_attributes, - $content - ); -} - -/** - * Registers the `core/post-navigation-link` block on the server. - * - * @since 5.9.0 - */ -function register_block_core_post_navigation_link() { - register_block_type_from_metadata( - __DIR__ . '/post-navigation-link', - array( - 'render_callback' => 'render_block_core_post_navigation_link', - ) - ); -} -add_action( 'init', 'register_block_core_post_navigation_link' ); diff --git a/src/wp-includes/blocks/post-navigation-link/block.json b/src/wp-includes/blocks/post-navigation-link/block.json deleted file mode 100644 index 2fda6a01cf516..0000000000000 --- a/src/wp-includes/blocks/post-navigation-link/block.json +++ /dev/null @@ -1,64 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-navigation-link", - "title": "Post Navigation Link", - "category": "theme", - "description": "Displays the next or previous post link that is adjacent to the current post.", - "textdomain": "default", - "attributes": { - "textAlign": { - "type": "string" - }, - "type": { - "type": "string", - "default": "next" - }, - "label": { - "type": "string", - "role": "content" - }, - "showTitle": { - "type": "boolean", - "default": false - }, - "linkLabel": { - "type": "boolean", - "default": false - }, - "arrow": { - "type": "string", - "default": "none" - }, - "taxonomy": { - "type": "string", - "default": "" - } - }, - "usesContext": [ "postType" ], - "supports": { - "reusable": false, - "html": false, - "color": { - "link": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalWritingMode": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "style": "wp-block-post-navigation-link" -} diff --git a/src/wp-includes/blocks/post-template.php b/src/wp-includes/blocks/post-template.php deleted file mode 100644 index 9126355c096a5..0000000000000 --- a/src/wp-includes/blocks/post-template.php +++ /dev/null @@ -1,162 +0,0 @@ -name ) { - return true; - } - if ( - 'core/cover' === $block->name && - ! empty( $block->attributes['useFeaturedImage'] ) - ) { - return true; - } - if ( $block->inner_blocks && block_core_post_template_uses_featured_image( $block->inner_blocks ) ) { - return true; - } - } - - return false; -} - -/** - * Renders the `core/post-template` block on the server. - * - * @since 6.3.0 Changed render_block_context priority to `1`. - * - * @global WP_Query $wp_query WordPress Query object. - * - * @param array $attributes Block attributes. - * @param string $content Block default content. - * @param WP_Block $block Block instance. - * - * @return string Returns the output of the query, structured using the layout defined by the block's inner blocks. - */ -function render_block_core_post_template( $attributes, $content, $block ) { - $page_key = isset( $block->context['queryId'] ) ? 'query-' . $block->context['queryId'] . '-page' : 'query-page'; - $enhanced_pagination = isset( $block->context['enhancedPagination'] ) && $block->context['enhancedPagination']; - $page = empty( $_GET[ $page_key ] ) ? 1 : (int) $_GET[ $page_key ]; - - // Use global query if needed. - $use_global_query = ( isset( $block->context['query']['inherit'] ) && $block->context['query']['inherit'] ); - if ( $use_global_query ) { - global $wp_query; - - /* - * If already in the main query loop, duplicate the query instance to not tamper with the main instance. - * Since this is a nested query, it should start at the beginning, therefore rewind posts. - * Otherwise, the main query loop has not started yet and this block is responsible for doing so. - */ - if ( in_the_loop() ) { - $query = clone $wp_query; - $query->rewind_posts(); - } else { - $query = $wp_query; - } - } else { - $query_args = build_query_vars_from_query_block( $block, $page ); - $query = new WP_Query( $query_args ); - } - - if ( ! $query->have_posts() ) { - return ''; - } - - if ( block_core_post_template_uses_featured_image( $block->inner_blocks ) ) { - update_post_thumbnail_cache( $query ); - } - - $classnames = ''; - if ( isset( $block->context['displayLayout'] ) && isset( $block->context['query'] ) ) { - if ( isset( $block->context['displayLayout']['type'] ) && 'flex' === $block->context['displayLayout']['type'] ) { - $classnames = "is-flex-container columns-{$block->context['displayLayout']['columns']}"; - } - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classnames .= ' has-link-color'; - } - - // Ensure backwards compatibility by flagging the number of columns via classname when using grid layout. - if ( isset( $attributes['layout']['type'] ) && 'grid' === $attributes['layout']['type'] && ! empty( $attributes['layout']['columnCount'] ) ) { - $classnames .= ' ' . sanitize_title( 'columns-' . $attributes['layout']['columnCount'] ); - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => trim( $classnames ) ) ); - - $content = ''; - while ( $query->have_posts() ) { - $query->the_post(); - - // Get an instance of the current Post Template block. - $block_instance = $block->parsed_block; - - // Set the block name to one that does not correspond to an existing registered block. - // This ensures that for the inner instances of the Post Template block, we do not render any block supports. - $block_instance['blockName'] = 'core/null'; - - $post_id = get_the_ID(); - $post_type = get_post_type(); - $filter_block_context = static function ( $context ) use ( $post_id, $post_type ) { - $context['postType'] = $post_type; - $context['postId'] = $post_id; - return $context; - }; - - // Use an early priority to so that other 'render_block_context' filters have access to the values. - add_filter( 'render_block_context', $filter_block_context, 1 ); - // Render the inner blocks of the Post Template block with `dynamic` set to `false` to prevent calling - // `render_callback` and ensure that no wrapper markup is included. - $block_content = ( new WP_Block( $block_instance ) )->render( array( 'dynamic' => false ) ); - remove_filter( 'render_block_context', $filter_block_context, 1 ); - - // Wrap the render inner blocks in a `li` element with the appropriate post classes. - $post_classes = implode( ' ', get_post_class( 'wp-block-post' ) ); - - $inner_block_directives = $enhanced_pagination ? ' data-wp-key="post-template-item-' . $post_id . '"' : ''; - - $content .= '' . $block_content . ''; - } - - /* - * Use this function to restore the context of the template tags - * from a secondary query loop back to the main query loop. - * Since we use two custom loops, it's safest to always restore. - */ - wp_reset_postdata(); - - return sprintf( - '
        %2$s
      ', - $wrapper_attributes, - $content - ); -} - -/** - * Registers the `core/post-template` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_post_template() { - register_block_type_from_metadata( - __DIR__ . '/post-template', - array( - 'render_callback' => 'render_block_core_post_template', - 'skip_inner_blocks' => true, - ) - ); -} -add_action( 'init', 'register_block_core_post_template' ); diff --git a/src/wp-includes/blocks/post-template/block.json b/src/wp-includes/blocks/post-template/block.json deleted file mode 100644 index d379a46d3142f..0000000000000 --- a/src/wp-includes/blocks/post-template/block.json +++ /dev/null @@ -1,69 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-template", - "title": "Post Template", - "category": "theme", - "ancestor": [ "core/query" ], - "description": "Contains the block elements used to render a post, like the title, date, featured image, content or excerpt, and more.", - "textdomain": "default", - "usesContext": [ - "queryId", - "query", - "displayLayout", - "templateSlug", - "previewPostType", - "enhancedPagination", - "postType" - ], - "supports": { - "reusable": false, - "html": false, - "align": [ "wide", "full" ], - "layout": true, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "spacing": { - "margin": true, - "padding": true, - "blockGap": { - "__experimentalDefault": "1.25em" - }, - "__experimentalDefaultControls": { - "blockGap": true, - "padding": false, - "margin": false - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true - } - }, - "style": "wp-block-post-template", - "editorStyle": "wp-block-post-template-editor" -} diff --git a/src/wp-includes/blocks/post-terms.php b/src/wp-includes/blocks/post-terms.php deleted file mode 100644 index 3e7a05f10117e..0000000000000 --- a/src/wp-includes/blocks/post-terms.php +++ /dev/null @@ -1,130 +0,0 @@ -context['postId'] ) || ! isset( $attributes['term'] ) ) { - return ''; - } - - if ( ! is_taxonomy_viewable( $attributes['term'] ) ) { - return ''; - } - - $classes = array( 'taxonomy-' . $attributes['term'] ); - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - - $separator = empty( $attributes['separator'] ) ? ' ' : $attributes['separator']; - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - - $prefix = "
      "; - if ( isset( $attributes['prefix'] ) && $attributes['prefix'] ) { - $prefix .= '' . $attributes['prefix'] . ''; - } - - $suffix = '
      '; - if ( isset( $attributes['suffix'] ) && $attributes['suffix'] ) { - $suffix = '' . $attributes['suffix'] . '' . $suffix; - } - - $post_terms = get_the_term_list( - $block->context['postId'], - $attributes['term'], - wp_kses_post( $prefix ), - '' . esc_html( $separator ) . '', - wp_kses_post( $suffix ) - ); - - if ( is_wp_error( $post_terms ) || empty( $post_terms ) ) { - return ''; - } - - return $post_terms; -} - -/** - * Returns the available variations for the `core/post-terms` block. - * - * @since 6.5.0 - * - * @return array The available variations for the block. - */ -function block_core_post_terms_build_variations() { - $taxonomies = get_taxonomies( - array( - 'publicly_queryable' => true, - 'show_in_rest' => true, - ), - 'objects' - ); - - // Split the available taxonomies to `built_in` and custom ones, - // in order to prioritize the `built_in` taxonomies at the - // search results. - $built_ins = array(); - $custom_variations = array(); - - // Create and register the eligible taxonomies variations. - foreach ( $taxonomies as $taxonomy ) { - $variation = array( - 'name' => $taxonomy->name, - 'title' => $taxonomy->label, - 'description' => sprintf( - /* translators: %s: taxonomy's label */ - __( 'Display a list of assigned terms from the taxonomy: %s' ), - $taxonomy->label - ), - 'attributes' => array( - 'term' => $taxonomy->name, - ), - 'isActive' => array( 'term' ), - 'scope' => array( 'inserter', 'transform' ), - ); - // Set the category variation as the default one. - if ( 'category' === $taxonomy->name ) { - $variation['isDefault'] = true; - } - if ( $taxonomy->_builtin ) { - $built_ins[] = $variation; - } else { - $custom_variations[] = $variation; - } - } - - return array_merge( $built_ins, $custom_variations ); -} - -/** - * Registers the `core/post-terms` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_post_terms() { - register_block_type_from_metadata( - __DIR__ . '/post-terms', - array( - 'render_callback' => 'render_block_core_post_terms', - 'variation_callback' => 'block_core_post_terms_build_variations', - ) - ); -} -add_action( 'init', 'register_block_core_post_terms' ); diff --git a/src/wp-includes/blocks/post-terms/block.json b/src/wp-includes/blocks/post-terms/block.json deleted file mode 100644 index e7567ba657c3b..0000000000000 --- a/src/wp-includes/blocks/post-terms/block.json +++ /dev/null @@ -1,80 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-terms", - "title": "Post Terms", - "category": "theme", - "description": "Post terms.", - "textdomain": "default", - "attributes": { - "term": { - "type": "string" - }, - "textAlign": { - "type": "string" - }, - "separator": { - "type": "string", - "default": ", " - }, - "prefix": { - "type": "string", - "default": "", - "role": "content" - }, - "suffix": { - "type": "string", - "default": "", - "role": "content" - } - }, - "usesContext": [ "postId", "postType" ], - "example": { - "viewportWidth": 350 - }, - "supports": { - "html": false, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "style": "wp-block-post-terms" -} diff --git a/src/wp-includes/blocks/post-time-to-read.php b/src/wp-includes/blocks/post-time-to-read.php deleted file mode 100644 index bce545a2927d2..0000000000000 --- a/src/wp-includes/blocks/post-time-to-read.php +++ /dev/null @@ -1,185 +0,0 @@ - '/<\/?[a-z][^>]*?>/i', - 'html_comment_regexp' => '//', - 'space_regexp' => '/ | /i', - 'html_entity_regexp' => '/&\S+?;/', - 'connector_regexp' => "/--|\x{2014}/u", - 'remove_regexp' => "/[\x{0021}-\x{0040}\x{005B}-\x{0060}\x{007B}-\x{007E}\x{0080}-\x{00BF}\x{00D7}\x{00F7}\x{2000}-\x{2BFF}\x{2E00}-\x{2E7F}]/u", - 'astral_regexp' => "/[\x{010000}-\x{10FFFF}]/u", - 'words_regexp' => '/\S\s+/u', - 'characters_excluding_spaces_regexp' => '/\S/u', - 'characters_including_spaces_regexp' => "/[^\f\n\r\t\v\x{00AD}\x{2028}\x{2029}]/u", - ); - - $count = 0; - - if ( '' === trim( $text ) ) { - return $count; - } - - // Sanitize type to one of three possibilities: 'words', 'characters_excluding_spaces' or 'characters_including_spaces'. - if ( 'characters_excluding_spaces' !== $type && 'characters_including_spaces' !== $type ) { - $type = 'words'; - } - - $text .= "\n"; - - // Replace all HTML with a new-line. - $text = preg_replace( $settings['html_regexp'], "\n", $text ); - - // Remove all HTML comments. - $text = preg_replace( $settings['html_comment_regexp'], '', $text ); - - // If a shortcode regular expression has been provided use it to remove shortcodes. - if ( ! empty( $settings['shortcodes_regexp'] ) ) { - $text = preg_replace( $settings['shortcodes_regexp'], "\n", $text ); - } - - // Normalize non-breaking space to a normal space. - $text = preg_replace( $settings['space_regexp'], ' ', $text ); - - if ( 'words' === $type ) { - // Remove HTML Entities. - $text = preg_replace( $settings['html_entity_regexp'], '', $text ); - - // Convert connectors to spaces to count attached text as words. - $text = preg_replace( $settings['connector_regexp'], ' ', $text ); - - // Remove unwanted characters. - $text = preg_replace( $settings['remove_regexp'], '', $text ); - } else { - // Convert HTML Entities to "a". - $text = preg_replace( $settings['html_entity_regexp'], 'a', $text ); - - // Remove surrogate points. - $text = preg_replace( $settings['astral_regexp'], 'a', $text ); - } - - // Match with the selected type regular expression to count the items. - return (int) preg_match_all( $settings[ $type . '_regexp' ], $text ); -} - -/** - * Renders the `core/post-time-to-read` block on the server. - * - * @since 6.9.0 - * - * @param array $attributes Block attributes. - * @param string $content Block default content. - * @param WP_Block $block Block instance. - * @return string Returns the rendered post author name block. - */ -function render_block_core_post_time_to_read( $attributes, $content, $block ) { - if ( ! isset( $block->context['postId'] ) ) { - return ''; - } - - $content = get_the_content(); - $average_reading_rate = isset( $attributes['averageReadingSpeed'] ) ? $attributes['averageReadingSpeed'] : 189; - - $display_mode = isset( $attributes['displayMode'] ) ? $attributes['displayMode'] : 'time'; - - $word_count_type = wp_get_word_count_type(); - $total_words = block_core_post_time_to_read_word_count( $content, $word_count_type ); - - $parts = array(); - - // Add "time to read" part, if enabled. - if ( 'time' === $display_mode ) { - if ( ! empty( $attributes['displayAsRange'] ) ) { - // Calculate faster reading rate with 20% speed = lower minutes, - // and slower reading rate with 20% speed = higher minutes. - $min_minutes = max( 1, (int) round( $total_words / $average_reading_rate * 0.8 ) ); - $max_minutes = max( 1, (int) round( $total_words / $average_reading_rate * 1.2 ) ); - if ( $min_minutes === $max_minutes ) { - $max_minutes = $min_minutes + 1; - } - /* translators: 1: minimum minutes, 2: maximum minutes to read the post. */ - $time_string = sprintf( - /* translators: 1: minimum minutes, 2: maximum minutes to read the post. */ - _x( '%1$s–%2$s minutes', 'Range of minutes to read' ), - $min_minutes, - $max_minutes - ); - } else { - $minutes_to_read = max( 1, (int) round( $total_words / $average_reading_rate ) ); - $time_string = sprintf( - /* translators: %s: the number of minutes to read the post. */ - _n( '%s minute', '%s minutes', $minutes_to_read ), - $minutes_to_read - ); - } - $parts[] = $time_string; - } - - // Add "word count" part, if enabled. - if ( 'words' === $display_mode ) { - $word_count_string = 'words' === $word_count_type ? sprintf( - /* translators: %s: the number of words in the post. */ - _n( '%s word', '%s words', $total_words ), - number_format_i18n( $total_words ) - ) : sprintf( - /* translators: %s: the number of characters in the post. */ - _n( '%s character', '%s characters', $total_words ), - number_format_i18n( $total_words ) - ); - $parts[] = $word_count_string; - } - - $display_string = implode( '
      ', $parts ); - - $align_class_name = empty( $attributes['textAlign'] ) ? '' : "has-text-align-{$attributes['textAlign']}"; - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => $align_class_name ) ); - - return sprintf( - '
      %2$s
      ', - $wrapper_attributes, - $display_string - ); -} - - -/** - * Registers the `core/post-time-to-read` block on the server. - * - * @since 6.9.0 - */ -function register_block_core_post_time_to_read() { - register_block_type_from_metadata( - __DIR__ . '/post-time-to-read', - array( - 'render_callback' => 'render_block_core_post_time_to_read', - ) - ); -} - -add_action( 'init', 'register_block_core_post_time_to_read' ); diff --git a/src/wp-includes/blocks/post-time-to-read/block.json b/src/wp-includes/blocks/post-time-to-read/block.json deleted file mode 100644 index 386312e00434e..0000000000000 --- a/src/wp-includes/blocks/post-time-to-read/block.json +++ /dev/null @@ -1,67 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-time-to-read", - "title": "Time to Read", - "category": "theme", - "description": "Show minutes required to finish reading the post. Can also show a word count.", - "textdomain": "default", - "usesContext": [ "postId", "postType" ], - "attributes": { - "textAlign": { - "type": "string" - }, - "displayAsRange": { - "type": "boolean", - "default": true - }, - "displayMode": { - "type": "string", - "default": "time" - }, - "averageReadingSpeed": { - "type": "number", - "default": 189 - } - }, - "supports": { - "color": { - "gradients": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "html": false, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } -} diff --git a/src/wp-includes/blocks/post-title.php b/src/wp-includes/blocks/post-title.php deleted file mode 100644 index ed27f2e4158eb..0000000000000 --- a/src/wp-includes/blocks/post-title.php +++ /dev/null @@ -1,74 +0,0 @@ -context['postId'] ) ) { - return ''; - } - - /** - * The `$post` argument is intentionally omitted so that changes are reflected when previewing a post. - * See: https://github.com/WordPress/gutenberg/pull/37622#issuecomment-1000932816. - */ - $title = get_the_title(); - - if ( ! $title ) { - return ''; - } - - $tag_name = 'h2'; - if ( isset( $attributes['level'] ) ) { - $tag_name = 0 === $attributes['level'] ? 'p' : 'h' . (int) $attributes['level']; - } - - if ( isset( $attributes['isLink'] ) && $attributes['isLink'] ) { - $rel = ! empty( $attributes['rel'] ) ? 'rel="' . esc_attr( $attributes['rel'] ) . '"' : ''; - $title = sprintf( '%4$s', esc_url( get_the_permalink( $block->context['postId'] ) ), esc_attr( $attributes['linkTarget'] ), $rel, $title ); - } - - $classes = array(); - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - - return sprintf( - '<%1$s %2$s>%3$s', - $tag_name, - $wrapper_attributes, - $title - ); -} - -/** - * Registers the `core/post-title` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_post_title() { - register_block_type_from_metadata( - __DIR__ . '/post-title', - array( - 'render_callback' => 'render_block_core_post_title', - ) - ); -} -add_action( 'init', 'register_block_core_post_title' ); diff --git a/src/wp-includes/blocks/post-title/block.json b/src/wp-includes/blocks/post-title/block.json deleted file mode 100644 index 5587d71b148d0..0000000000000 --- a/src/wp-includes/blocks/post-title/block.json +++ /dev/null @@ -1,87 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/post-title", - "title": "Title", - "category": "theme", - "description": "Displays the title of a post, page, or any other content-type.", - "textdomain": "default", - "usesContext": [ "postId", "postType", "queryId" ], - "attributes": { - "textAlign": { - "type": "string" - }, - "level": { - "type": "number", - "default": 2 - }, - "levelOptions": { - "type": "array" - }, - "isLink": { - "type": "boolean", - "default": false, - "role": "content" - }, - "rel": { - "type": "string", - "attribute": "rel", - "default": "", - "role": "content" - }, - "linkTarget": { - "type": "string", - "default": "_self", - "role": "content" - } - }, - "example": { - "viewportWidth": 350 - }, - "supports": { - "align": [ "wide", "full" ], - "html": false, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "style": "wp-block-post-title" -} diff --git a/src/wp-includes/blocks/preformatted/block.json b/src/wp-includes/blocks/preformatted/block.json deleted file mode 100644 index c25b8ce37093a..0000000000000 --- a/src/wp-includes/blocks/preformatted/block.json +++ /dev/null @@ -1,61 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/preformatted", - "title": "Preformatted", - "category": "text", - "description": "Add text that respects your spacing and tabs, and also allows styling.", - "textdomain": "default", - "attributes": { - "content": { - "type": "rich-text", - "source": "rich-text", - "selector": "pre", - "__unstablePreserveWhiteSpace": true, - "role": "content" - } - }, - "supports": { - "anchor": true, - "color": { - "gradients": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "spacing": { - "padding": true, - "margin": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "style": "wp-block-preformatted" -} diff --git a/src/wp-includes/blocks/pullquote/block.json b/src/wp-includes/blocks/pullquote/block.json deleted file mode 100644 index 271bba74d0252..0000000000000 --- a/src/wp-includes/blocks/pullquote/block.json +++ /dev/null @@ -1,92 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/pullquote", - "title": "Pullquote", - "category": "text", - "description": "Give special visual emphasis to a quote from your text.", - "textdomain": "default", - "attributes": { - "value": { - "type": "rich-text", - "source": "rich-text", - "selector": "p", - "role": "content" - }, - "citation": { - "type": "rich-text", - "source": "rich-text", - "selector": "cite", - "role": "content" - }, - "textAlign": { - "type": "string" - } - }, - "supports": { - "anchor": true, - "align": [ "left", "right", "wide", "full" ], - "background": { - "backgroundImage": true, - "backgroundSize": true, - "__experimentalDefaultControls": { - "backgroundImage": true - } - }, - "color": { - "gradients": true, - "background": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "dimensions": { - "minHeight": true, - "__experimentalDefaultControls": { - "minHeight": false - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "__experimentalBorder": { - "color": true, - "radius": true, - "style": true, - "width": true, - "__experimentalDefaultControls": { - "color": true, - "radius": true, - "style": true, - "width": true - } - }, - "__experimentalStyle": { - "typography": { - "fontSize": "1.5em", - "lineHeight": "1.6" - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-pullquote-editor", - "style": "wp-block-pullquote" -} diff --git a/src/wp-includes/blocks/query-no-results.php b/src/wp-includes/blocks/query-no-results.php deleted file mode 100644 index 34d6b321cbd6b..0000000000000 --- a/src/wp-includes/blocks/query-no-results.php +++ /dev/null @@ -1,65 +0,0 @@ -context['queryId'] ) ? 'query-' . $block->context['queryId'] . '-page' : 'query-page'; - $page = empty( $_GET[ $page_key ] ) ? 1 : (int) $_GET[ $page_key ]; - - // Override the custom query with the global query if needed. - $use_global_query = ( isset( $block->context['query']['inherit'] ) && $block->context['query']['inherit'] ); - if ( $use_global_query ) { - global $wp_query; - $query = $wp_query; - } else { - $query_args = build_query_vars_from_query_block( $block, $page ); - $query = new WP_Query( $query_args ); - } - - if ( $query->post_count > 0 ) { - return ''; - } - - $classes = ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) ? 'has-link-color' : ''; - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => $classes ) ); - return sprintf( - '
      %2$s
      ', - $wrapper_attributes, - $content - ); -} - -/** - * Registers the `core/query-no-results` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_query_no_results() { - register_block_type_from_metadata( - __DIR__ . '/query-no-results', - array( - 'render_callback' => 'render_block_core_query_no_results', - ) - ); -} -add_action( 'init', 'register_block_core_query_no_results' ); diff --git a/src/wp-includes/blocks/query-no-results/block.json b/src/wp-includes/blocks/query-no-results/block.json deleted file mode 100644 index 44d2ceef987e2..0000000000000 --- a/src/wp-includes/blocks/query-no-results/block.json +++ /dev/null @@ -1,36 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/query-no-results", - "title": "No Results", - "category": "theme", - "description": "Contains the block elements used to render content when no query results are found.", - "ancestor": [ "core/query" ], - "textdomain": "default", - "usesContext": [ "queryId", "query" ], - "supports": { - "align": true, - "reusable": false, - "html": false, - "color": { - "gradients": true, - "link": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - } -} diff --git a/src/wp-includes/blocks/query-pagination-next.php b/src/wp-includes/blocks/query-pagination-next.php deleted file mode 100644 index d574f94093846..0000000000000 --- a/src/wp-includes/blocks/query-pagination-next.php +++ /dev/null @@ -1,102 +0,0 @@ -context['queryId'] ) ? 'query-' . $block->context['queryId'] . '-page' : 'query-page'; - $enhanced_pagination = isset( $block->context['enhancedPagination'] ) && $block->context['enhancedPagination']; - $page = empty( $_GET[ $page_key ] ) ? 1 : (int) $_GET[ $page_key ]; - $max_page = isset( $block->context['query']['pages'] ) ? (int) $block->context['query']['pages'] : 0; - - $wrapper_attributes = get_block_wrapper_attributes(); - $show_label = isset( $block->context['showLabel'] ) ? (bool) $block->context['showLabel'] : true; - $default_label = __( 'Next Page' ); - $label_text = isset( $attributes['label'] ) && ! empty( $attributes['label'] ) ? esc_html( $attributes['label'] ) : $default_label; - $label = $show_label ? $label_text : ''; - $pagination_arrow = get_query_pagination_arrow( $block, true ); - - if ( ! $label ) { - $wrapper_attributes .= ' aria-label="' . $label_text . '"'; - } - if ( $pagination_arrow ) { - $label .= $pagination_arrow; - } - $content = ''; - - // Check if the pagination is for Query that inherits the global context. - if ( isset( $block->context['query']['inherit'] ) && $block->context['query']['inherit'] ) { - $filter_link_attributes = static function () use ( $wrapper_attributes ) { - return $wrapper_attributes; - }; - add_filter( 'next_posts_link_attributes', $filter_link_attributes ); - // Take into account if we have set a bigger `max page` - // than what the query has. - global $wp_query; - if ( $max_page > $wp_query->max_num_pages ) { - $max_page = $wp_query->max_num_pages; - } - $content = get_next_posts_link( $label, $max_page ); - remove_filter( 'next_posts_link_attributes', $filter_link_attributes ); - } elseif ( ! $max_page || $max_page > $page ) { - $custom_query = new WP_Query( build_query_vars_from_query_block( $block, $page ) ); - $custom_query_max_pages = (int) $custom_query->max_num_pages; - if ( $custom_query_max_pages && $custom_query_max_pages !== $page ) { - $content = sprintf( - '%3$s', - esc_url( add_query_arg( $page_key, $page + 1 ) ), - $wrapper_attributes, - $label - ); - } - wp_reset_postdata(); // Restore original Post Data. - } - - if ( $enhanced_pagination && isset( $content ) ) { - $p = new WP_HTML_Tag_Processor( $content ); - if ( $p->next_tag( - array( - 'tag_name' => 'a', - 'class_name' => 'wp-block-query-pagination-next', - ) - ) ) { - $p->set_attribute( 'data-wp-key', 'query-pagination-next' ); - $p->set_attribute( 'data-wp-on--click', 'core/query::actions.navigate' ); - $p->set_attribute( 'data-wp-on--mouseenter', 'core/query::actions.prefetch' ); - $p->set_attribute( 'data-wp-watch', 'core/query::callbacks.prefetch' ); - $content = $p->get_updated_html(); - } - } - - return $content; -} - -/** - * Registers the `core/query-pagination-next` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_query_pagination_next() { - register_block_type_from_metadata( - __DIR__ . '/query-pagination-next', - array( - 'render_callback' => 'render_block_core_query_pagination_next', - ) - ); -} -add_action( 'init', 'register_block_core_query_pagination_next' ); diff --git a/src/wp-includes/blocks/query-pagination-next/block.json b/src/wp-includes/blocks/query-pagination-next/block.json deleted file mode 100644 index ec56125ee3b76..0000000000000 --- a/src/wp-includes/blocks/query-pagination-next/block.json +++ /dev/null @@ -1,49 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/query-pagination-next", - "title": "Next Page", - "category": "theme", - "parent": [ "core/query-pagination" ], - "description": "Displays the next posts page link.", - "textdomain": "default", - "attributes": { - "label": { - "type": "string" - } - }, - "usesContext": [ - "queryId", - "query", - "paginationArrow", - "showLabel", - "enhancedPagination" - ], - "supports": { - "reusable": false, - "html": false, - "color": { - "gradients": true, - "text": false, - "__experimentalDefaultControls": { - "background": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - } -} diff --git a/src/wp-includes/blocks/query-pagination-numbers.php b/src/wp-includes/blocks/query-pagination-numbers.php deleted file mode 100644 index fddf28660fe4f..0000000000000 --- a/src/wp-includes/blocks/query-pagination-numbers.php +++ /dev/null @@ -1,133 +0,0 @@ -context['queryId'] ) ? 'query-' . $block->context['queryId'] . '-page' : 'query-page'; - $enhanced_pagination = isset( $block->context['enhancedPagination'] ) && $block->context['enhancedPagination']; - $page = empty( $_GET[ $page_key ] ) ? 1 : (int) $_GET[ $page_key ]; - $max_page = isset( $block->context['query']['pages'] ) ? (int) $block->context['query']['pages'] : 0; - - $wrapper_attributes = get_block_wrapper_attributes(); - $content = ''; - global $wp_query; - $mid_size = isset( $block->attributes['midSize'] ) ? (int) $block->attributes['midSize'] : null; - if ( isset( $block->context['query']['inherit'] ) && $block->context['query']['inherit'] ) { - // Take into account if we have set a bigger `max page` - // than what the query has. - $total = ! $max_page || $max_page > $wp_query->max_num_pages ? $wp_query->max_num_pages : $max_page; - $paginate_args = array( - 'prev_next' => false, - 'total' => $total, - ); - if ( null !== $mid_size ) { - $paginate_args['mid_size'] = $mid_size; - } - $content = paginate_links( $paginate_args ); - } else { - $block_query = new WP_Query( build_query_vars_from_query_block( $block, $page ) ); - // `paginate_links` works with the global $wp_query, so we have to - // temporarily switch it with our custom query. - $prev_wp_query = $wp_query; - $wp_query = $block_query; - $total = ! $max_page || $max_page > $wp_query->max_num_pages ? $wp_query->max_num_pages : $max_page; - $paginate_args = array( - 'base' => '%_%', - 'format' => "?$page_key=%#%", - 'current' => max( 1, $page ), - 'total' => $total, - 'prev_next' => false, - ); - if ( null !== $mid_size ) { - $paginate_args['mid_size'] = $mid_size; - } - if ( 1 !== $page ) { - /** - * `paginate_links` doesn't use the provided `format` when the page is `1`. - * This is great for the main query as it removes the extra query params - * making the URL shorter, but in the case of multiple custom queries is - * problematic. It results in returning an empty link which ends up with - * a link to the current page. - * - * A way to address this is to add a `fake` query arg with no value that - * is the same for all custom queries. This way the link is not empty and - * preserves all the other existent query args. - * - * @see https://developer.wordpress.org/reference/functions/paginate_links/ - * - * The proper fix of this should be in core. Track Ticket: - * @see https://core.trac.wordpress.org/ticket/53868 - * - * TODO: After two WP versions (starting from the WP version the core patch landed), - * we should remove this and call `paginate_links` with the proper new arg. - */ - $paginate_args['add_args'] = array( 'cst' => '' ); - } - // We still need to preserve `paged` query param if exists, as is used - // for Queries that inherit from global context. - $paged = empty( $_GET['paged'] ) ? null : (int) $_GET['paged']; - if ( $paged ) { - $paginate_args['add_args'] = array( 'paged' => $paged ); - } - $content = paginate_links( $paginate_args ); - wp_reset_postdata(); // Restore original Post Data. - $wp_query = $prev_wp_query; - } - - if ( empty( $content ) ) { - return ''; - } - - if ( $enhanced_pagination ) { - $p = new WP_HTML_Tag_Processor( $content ); - $tag_index = 0; - while ( $p->next_tag( - array( 'class_name' => 'page-numbers' ) - ) ) { - if ( null === $p->get_attribute( 'data-wp-key' ) ) { - $p->set_attribute( 'data-wp-key', 'index-' . $tag_index++ ); - } - if ( 'A' === $p->get_tag() ) { - $p->set_attribute( 'data-wp-on--click', 'core/query::actions.navigate' ); - } - } - $content = $p->get_updated_html(); - } - - return sprintf( - '
      %2$s
      ', - $wrapper_attributes, - $content - ); -} - -/** - * Registers the `core/query-pagination-numbers` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_query_pagination_numbers() { - register_block_type_from_metadata( - __DIR__ . '/query-pagination-numbers', - array( - 'render_callback' => 'render_block_core_query_pagination_numbers', - ) - ); -} -add_action( 'init', 'register_block_core_query_pagination_numbers' ); diff --git a/src/wp-includes/blocks/query-pagination-numbers/block.json b/src/wp-includes/blocks/query-pagination-numbers/block.json deleted file mode 100644 index 8a9f0ee69f14e..0000000000000 --- a/src/wp-includes/blocks/query-pagination-numbers/block.json +++ /dev/null @@ -1,45 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/query-pagination-numbers", - "title": "Page Numbers", - "category": "theme", - "parent": [ "core/query-pagination" ], - "description": "Displays a list of page numbers for pagination.", - "textdomain": "default", - "attributes": { - "midSize": { - "type": "number", - "default": 2 - } - }, - "usesContext": [ "queryId", "query", "enhancedPagination" ], - "supports": { - "reusable": false, - "html": false, - "color": { - "gradients": true, - "text": false, - "__experimentalDefaultControls": { - "background": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-query-pagination-numbers-editor" -} diff --git a/src/wp-includes/blocks/query-pagination-previous.php b/src/wp-includes/blocks/query-pagination-previous.php deleted file mode 100644 index ec3de8921d519..0000000000000 --- a/src/wp-includes/blocks/query-pagination-previous.php +++ /dev/null @@ -1,95 +0,0 @@ -context['queryId'] ) ? 'query-' . $block->context['queryId'] . '-page' : 'query-page'; - $enhanced_pagination = isset( $block->context['enhancedPagination'] ) && $block->context['enhancedPagination']; - $max_page = isset( $block->context['query']['pages'] ) ? (int) $block->context['query']['pages'] : 0; - $page = empty( $_GET[ $page_key ] ) ? 1 : (int) $_GET[ $page_key ]; - $wrapper_attributes = get_block_wrapper_attributes(); - $show_label = isset( $block->context['showLabel'] ) ? (bool) $block->context['showLabel'] : true; - $default_label = __( 'Previous Page' ); - $label_text = isset( $attributes['label'] ) && ! empty( $attributes['label'] ) ? esc_html( $attributes['label'] ) : $default_label; - $label = $show_label ? $label_text : ''; - $pagination_arrow = get_query_pagination_arrow( $block, false ); - if ( ! $label ) { - $wrapper_attributes .= ' aria-label="' . $label_text . '"'; - } - if ( $pagination_arrow ) { - $label = $pagination_arrow . $label; - } - $content = ''; - // Check if the pagination is for Query that inherits the global context - // and handle appropriately. - if ( isset( $block->context['query']['inherit'] ) && $block->context['query']['inherit'] ) { - $filter_link_attributes = static function () use ( $wrapper_attributes ) { - return $wrapper_attributes; - }; - - add_filter( 'previous_posts_link_attributes', $filter_link_attributes ); - $content = get_previous_posts_link( $label ); - remove_filter( 'previous_posts_link_attributes', $filter_link_attributes ); - } else { - $block_query = new WP_Query( build_query_vars_from_query_block( $block, $page ) ); - $block_max_pages = $block_query->max_num_pages; - $total = ! $max_page || $max_page > $block_max_pages ? $block_max_pages : $max_page; - wp_reset_postdata(); - - if ( 1 < $page && $page <= $total ) { - $content = sprintf( - '%3$s', - esc_url( add_query_arg( $page_key, $page - 1 ) ), - $wrapper_attributes, - $label - ); - } - } - - if ( $enhanced_pagination && isset( $content ) ) { - $p = new WP_HTML_Tag_Processor( $content ); - if ( $p->next_tag( - array( - 'tag_name' => 'a', - 'class_name' => 'wp-block-query-pagination-previous', - ) - ) ) { - $p->set_attribute( 'data-wp-key', 'query-pagination-previous' ); - $p->set_attribute( 'data-wp-on--click', 'core/query::actions.navigate' ); - $p->set_attribute( 'data-wp-on--mouseenter', 'core/query::actions.prefetch' ); - $p->set_attribute( 'data-wp-watch', 'core/query::callbacks.prefetch' ); - $content = $p->get_updated_html(); - } - } - - return $content; -} - -/** - * Registers the `core/query-pagination-previous` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_query_pagination_previous() { - register_block_type_from_metadata( - __DIR__ . '/query-pagination-previous', - array( - 'render_callback' => 'render_block_core_query_pagination_previous', - ) - ); -} -add_action( 'init', 'register_block_core_query_pagination_previous' ); diff --git a/src/wp-includes/blocks/query-pagination-previous/block.json b/src/wp-includes/blocks/query-pagination-previous/block.json deleted file mode 100644 index d1e34c8630250..0000000000000 --- a/src/wp-includes/blocks/query-pagination-previous/block.json +++ /dev/null @@ -1,49 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/query-pagination-previous", - "title": "Previous Page", - "category": "theme", - "parent": [ "core/query-pagination" ], - "description": "Displays the previous posts page link.", - "textdomain": "default", - "attributes": { - "label": { - "type": "string" - } - }, - "usesContext": [ - "queryId", - "query", - "paginationArrow", - "showLabel", - "enhancedPagination" - ], - "supports": { - "reusable": false, - "html": false, - "color": { - "gradients": true, - "text": false, - "__experimentalDefaultControls": { - "background": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - } -} diff --git a/src/wp-includes/blocks/query-pagination.php b/src/wp-includes/blocks/query-pagination.php deleted file mode 100644 index acafe968c0bec..0000000000000 --- a/src/wp-includes/blocks/query-pagination.php +++ /dev/null @@ -1,51 +0,0 @@ - __( 'Pagination' ), - 'class' => $classes, - ) - ); - - return sprintf( - '', - $wrapper_attributes, - $content - ); -} - -/** - * Registers the `core/query-pagination` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_query_pagination() { - register_block_type_from_metadata( - __DIR__ . '/query-pagination', - array( - 'render_callback' => 'render_block_core_query_pagination', - ) - ); -} -add_action( 'init', 'register_block_core_query_pagination' ); diff --git a/src/wp-includes/blocks/query-pagination/block.json b/src/wp-includes/blocks/query-pagination/block.json deleted file mode 100644 index 355b188e442d8..0000000000000 --- a/src/wp-includes/blocks/query-pagination/block.json +++ /dev/null @@ -1,69 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/query-pagination", - "title": "Pagination", - "category": "theme", - "ancestor": [ "core/query" ], - "allowedBlocks": [ - "core/query-pagination-previous", - "core/query-pagination-numbers", - "core/query-pagination-next" - ], - "description": "Displays a paginated navigation to next/previous set of posts, when applicable.", - "textdomain": "default", - "attributes": { - "paginationArrow": { - "type": "string", - "default": "none" - }, - "showLabel": { - "type": "boolean", - "default": true - } - }, - "usesContext": [ "queryId", "query" ], - "providesContext": { - "paginationArrow": "paginationArrow", - "showLabel": "showLabel" - }, - "supports": { - "align": true, - "reusable": false, - "html": false, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "layout": { - "allowSwitching": false, - "allowInheriting": false, - "default": { - "type": "flex" - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-query-pagination-editor", - "style": "wp-block-query-pagination" -} diff --git a/src/wp-includes/blocks/query-title.php b/src/wp-includes/blocks/query-title.php deleted file mode 100644 index 980e1c5f58f44..0000000000000 --- a/src/wp-includes/blocks/query-title.php +++ /dev/null @@ -1,103 +0,0 @@ -context['query']['postType'] ) ? $block->context['query']['postType'] : get_post_type(); - - if ( ! $type || - ( 'archive' === $type && ! $is_archive ) || - ( 'search' === $type && ! $is_search ) || - ( 'post-type' === $type && ! $post_type ) - ) { - return ''; - } - $title = ''; - if ( $is_archive ) { - $show_prefix = isset( $attributes['showPrefix'] ) ? $attributes['showPrefix'] : true; - if ( ! $show_prefix ) { - add_filter( 'get_the_archive_title_prefix', '__return_empty_string', 1 ); - $title = get_the_archive_title(); - remove_filter( 'get_the_archive_title_prefix', '__return_empty_string', 1 ); - } else { - $title = get_the_archive_title(); - } - } - if ( $is_search ) { - $title = __( 'Search results' ); - - if ( isset( $attributes['showSearchTerm'] ) && $attributes['showSearchTerm'] ) { - $title = sprintf( - /* translators: %s is the search term. */ - __( 'Search results for: "%s"' ), - get_search_query() - ); - } - } - if ( 'post-type' === $type ) { - $post_type_object = get_post_type_object( $post_type ); - - if ( ! $post_type_object ) { - return ''; - } - - $post_type_name = $post_type_object->labels->singular_name; - $show_prefix = isset( $attributes['showPrefix'] ) ? $attributes['showPrefix'] : true; - - if ( $show_prefix ) { - $title = sprintf( - /* translators: %s is the post type name. */ - __( 'Post Type: "%s"' ), - $post_type_name - ); - } else { - $title = $post_type_name; - } - } - - $level = isset( $attributes['level'] ) ? (int) $attributes['level'] : 1; - $tag_name = 0 === $level ? 'p' : 'h' . (int) $attributes['level']; - - $align_class_name = empty( $attributes['textAlign'] ) ? '' : "has-text-align-{$attributes['textAlign']}"; - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => $align_class_name ) ); - return sprintf( - '<%1$s %2$s>%3$s', - $tag_name, - $wrapper_attributes, - $title - ); -} - -/** - * Registers the `core/query-title` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_query_title() { - register_block_type_from_metadata( - __DIR__ . '/query-title', - array( - 'render_callback' => 'render_block_core_query_title', - ) - ); -} -add_action( 'init', 'register_block_core_query_title' ); diff --git a/src/wp-includes/blocks/query-title/block.json b/src/wp-includes/blocks/query-title/block.json deleted file mode 100644 index 549451bbfc67b..0000000000000 --- a/src/wp-includes/blocks/query-title/block.json +++ /dev/null @@ -1,82 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/query-title", - "title": "Query Title", - "category": "theme", - "description": "Display the query title.", - "textdomain": "default", - "attributes": { - "type": { - "type": "string" - }, - "textAlign": { - "type": "string" - }, - "level": { - "type": "number", - "default": 1 - }, - "levelOptions": { - "type": "array" - }, - "showPrefix": { - "type": "boolean", - "default": true - }, - "showSearchTerm": { - "type": "boolean", - "default": true - } - }, - "example": { - "attributes": { - "type": "search" - } - }, - "usesContext": [ "query" ], - "supports": { - "align": [ "wide", "full" ], - "html": false, - "color": { - "gradients": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontStyle": true, - "__experimentalFontWeight": true, - "__experimentalLetterSpacing": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "style": "wp-block-query-title" -} diff --git a/src/wp-includes/blocks/query-total.php b/src/wp-includes/blocks/query-total.php deleted file mode 100644 index f63bb1b98eac0..0000000000000 --- a/src/wp-includes/blocks/query-total.php +++ /dev/null @@ -1,90 +0,0 @@ -context['query']['inherit'] ) && $block->context['query']['inherit'] ) { - $query_to_use = $wp_query; - $current_page = max( 1, (int) get_query_var( 'paged', 1 ) ); - } else { - $page_key = isset( $block->context['queryId'] ) ? 'query-' . $block->context['queryId'] . '-page' : 'query-page'; - $current_page = isset( $_GET[ $page_key ] ) ? (int) $_GET[ $page_key ] : 1; - $query_to_use = new WP_Query( build_query_vars_from_query_block( $block, $current_page ) ); - } - - $max_rows = $query_to_use->found_posts; - $posts_per_page = (int) $query_to_use->get( 'posts_per_page' ); - - // Calculate the range of posts being displayed. - $start = ( 0 === $max_rows ) ? 0 : ( ( $current_page - 1 ) * $posts_per_page + 1 ); - $end = min( $start + $posts_per_page - 1, $max_rows ); - - // Prepare the display based on the `displayType` attribute. - $output = ''; - switch ( $attributes['displayType'] ) { - case 'range-display': - if ( $start === $end ) { - $output = sprintf( - /* translators: 1: Start index of posts, 2: Total number of posts */ - __( 'Displaying %1$s of %2$s' ), - $start, - $max_rows - ); - } else { - $output = sprintf( - /* translators: 1: Start index of posts, 2: End index of posts, 3: Total number of posts */ - __( 'Displaying %1$s – %2$s of %3$s' ), - $start, - $end, - $max_rows - ); - } - - break; - - case 'total-results': - default: - // translators: %d: number of results. - $output = sprintf( _n( '%d result found', '%d results found', $max_rows ), $max_rows ); - break; - } - - return sprintf( - '
      %2$s
      ', - $wrapper_attributes, - $output - ); -} - -/** - * Registers the `query-total` block. - * - * @since 6.8.0 - */ -function register_block_core_query_total() { - register_block_type_from_metadata( - __DIR__ . '/query-total', - array( - 'render_callback' => 'render_block_core_query_total', - ) - ); -} -add_action( 'init', 'register_block_core_query_total' ); diff --git a/src/wp-includes/blocks/query-total/block.json b/src/wp-includes/blocks/query-total/block.json deleted file mode 100644 index 21f6ba0673903..0000000000000 --- a/src/wp-includes/blocks/query-total/block.json +++ /dev/null @@ -1,61 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/query-total", - "title": "Query Total", - "category": "theme", - "ancestor": [ "core/query" ], - "description": "Display the total number of results in a query.", - "textdomain": "default", - "attributes": { - "displayType": { - "type": "string", - "default": "total-results" - } - }, - "usesContext": [ "queryId", "query" ], - "supports": { - "align": [ "wide", "full" ], - "html": false, - "spacing": { - "margin": true, - "padding": true - }, - "color": { - "gradients": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "style": "wp-block-query-total" -} diff --git a/src/wp-includes/blocks/query.php b/src/wp-includes/blocks/query.php deleted file mode 100644 index 6b544cd99ae8c..0000000000000 --- a/src/wp-includes/blocks/query.php +++ /dev/null @@ -1,152 +0,0 @@ -next_tag() ) { - // Add the necessary directives. - $p->set_attribute( 'data-wp-interactive', 'core/query' ); - $p->set_attribute( 'data-wp-router-region', 'query-' . $attributes['queryId'] ); - $p->set_attribute( 'data-wp-context', '{}' ); - $p->set_attribute( 'data-wp-key', $attributes['queryId'] ); - $content = $p->get_updated_html(); - } - } - - // Add the styles to the block type if the block is interactive and remove - // them if it's not. - $style_asset = 'wp-block-query'; - if ( ! wp_style_is( $style_asset ) ) { - $style_handles = $block->block_type->style_handles; - // If the styles are not needed, and they are still in the `style_handles`, remove them. - if ( ! $is_interactive && in_array( $style_asset, $style_handles, true ) ) { - $block->block_type->style_handles = array_diff( $style_handles, array( $style_asset ) ); - } - // If the styles are needed, but they were previously removed, add them again. - if ( $is_interactive && ! in_array( $style_asset, $style_handles, true ) ) { - $block->block_type->style_handles = array_merge( $style_handles, array( $style_asset ) ); - } - } - - return $content; -} - -/** - * Registers the `core/query` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_query() { - register_block_type_from_metadata( - __DIR__ . '/query', - array( - 'render_callback' => 'render_block_core_query', - ) - ); -} -add_action( 'init', 'register_block_core_query' ); - -/** - * Traverse the tree of blocks looking for any plugin block (i.e., a block from - * an installed plugin) inside a Query block with the enhanced pagination - * enabled. If at least one is found, the enhanced pagination is effectively - * disabled to prevent any potential incompatibilities. - * - * @since 6.4.0 - * - * @param array $parsed_block The block being rendered. - * @return array Returns the parsed block, unmodified. - */ -function block_core_query_disable_enhanced_pagination( $parsed_block ) { - static $enhanced_query_stack = array(); - static $dirty_enhanced_queries = array(); - static $render_query_callback = null; - - $block_name = $parsed_block['blockName']; - $block_type = WP_Block_Type_Registry::get_instance()->get_registered( $block_name ); - $has_enhanced_pagination = isset( $parsed_block['attrs']['enhancedPagination'] ) && true === $parsed_block['attrs']['enhancedPagination'] && isset( $parsed_block['attrs']['queryId'] ); - /* - * Client side navigation can be true in two states: - * - supports.interactivity = true; - * - supports.interactivity.clientNavigation = true; - */ - $supports_client_navigation = ( isset( $block_type->supports['interactivity']['clientNavigation'] ) && true === $block_type->supports['interactivity']['clientNavigation'] ) - || ( isset( $block_type->supports['interactivity'] ) && true === $block_type->supports['interactivity'] ); - - if ( 'core/query' === $block_name && $has_enhanced_pagination ) { - $enhanced_query_stack[] = $parsed_block['attrs']['queryId']; - - if ( ! isset( $render_query_callback ) ) { - /** - * Filter that disables the enhanced pagination feature during block - * rendering when a plugin block has been found inside. It does so - * by adding an attribute called `data-wp-navigation-disabled` which - * is later handled by the front-end logic. - * - * @param string $content The block content. - * @param array $block The full block, including name and attributes. - * @return string Returns the modified output of the query block. - */ - $render_query_callback = static function ( $content, $block ) use ( &$enhanced_query_stack, &$dirty_enhanced_queries, &$render_query_callback ) { - $has_enhanced_pagination = isset( $block['attrs']['enhancedPagination'] ) && true === $block['attrs']['enhancedPagination'] && isset( $block['attrs']['queryId'] ); - - if ( ! $has_enhanced_pagination ) { - return $content; - } - - if ( isset( $dirty_enhanced_queries[ $block['attrs']['queryId'] ] ) ) { - // Disable navigation in the router store config. - wp_interactivity_config( 'core/router', array( 'clientNavigationDisabled' => true ) ); - $dirty_enhanced_queries[ $block['attrs']['queryId'] ] = null; - } - - array_pop( $enhanced_query_stack ); - - if ( empty( $enhanced_query_stack ) ) { - remove_filter( 'render_block_core/query', $render_query_callback ); - $render_query_callback = null; - } - - return $content; - }; - - add_filter( 'render_block_core/query', $render_query_callback, 10, 2 ); - } - } elseif ( - ! empty( $enhanced_query_stack ) && - isset( $block_name ) && - ( ! $supports_client_navigation ) - ) { - foreach ( $enhanced_query_stack as $query_id ) { - $dirty_enhanced_queries[ $query_id ] = true; - } - } - - return $parsed_block; -} - -add_filter( 'render_block_data', 'block_core_query_disable_enhanced_pagination', 10, 1 ); diff --git a/src/wp-includes/blocks/query/block.json b/src/wp-includes/blocks/query/block.json deleted file mode 100644 index 33ba8bfd925ca..0000000000000 --- a/src/wp-includes/blocks/query/block.json +++ /dev/null @@ -1,60 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/query", - "title": "Query Loop", - "category": "theme", - "description": "An advanced block that allows displaying post types based on different query parameters and visual configurations.", - "keywords": [ "posts", "list", "blog", "blogs", "custom post types" ], - "textdomain": "default", - "attributes": { - "queryId": { - "type": "number" - }, - "query": { - "type": "object", - "default": { - "perPage": null, - "pages": 0, - "offset": 0, - "postType": "post", - "order": "desc", - "orderBy": "date", - "author": "", - "search": "", - "exclude": [], - "sticky": "", - "inherit": true, - "taxQuery": null, - "parents": [], - "format": [] - } - }, - "tagName": { - "type": "string", - "default": "div" - }, - "namespace": { - "type": "string" - }, - "enhancedPagination": { - "type": "boolean", - "default": false - } - }, - "usesContext": [ "templateSlug" ], - "providesContext": { - "queryId": "queryId", - "query": "query", - "displayLayout": "displayLayout", - "enhancedPagination": "enhancedPagination" - }, - "supports": { - "align": [ "wide", "full" ], - "html": false, - "layout": true, - "interactivity": true, - "contentRole": true - }, - "editorStyle": "wp-block-query-editor" -} diff --git a/src/wp-includes/blocks/query/view.asset.php b/src/wp-includes/blocks/query/view.asset.php deleted file mode 100644 index 30c0410598e62..0000000000000 --- a/src/wp-includes/blocks/query/view.asset.php +++ /dev/null @@ -1 +0,0 @@ - array(), 'version' => 'ee101e08820687c9c07f'); diff --git a/src/wp-includes/blocks/query/view.min.asset.php b/src/wp-includes/blocks/query/view.min.asset.php deleted file mode 100644 index 305a626497b32..0000000000000 --- a/src/wp-includes/blocks/query/view.min.asset.php +++ /dev/null @@ -1 +0,0 @@ - array(), 'version' => '490915f92cc794ea16e1'); diff --git a/src/wp-includes/blocks/quote/block.json b/src/wp-includes/blocks/quote/block.json deleted file mode 100644 index 52609ee57d12a..0000000000000 --- a/src/wp-includes/blocks/quote/block.json +++ /dev/null @@ -1,105 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/quote", - "title": "Quote", - "category": "text", - "description": "Give quoted text visual emphasis. \"In quoting others, we cite ourselves.\" — Julio Cortázar", - "keywords": [ "blockquote", "cite" ], - "textdomain": "default", - "attributes": { - "value": { - "type": "string", - "source": "html", - "selector": "blockquote", - "multiline": "p", - "default": "", - "role": "content" - }, - "citation": { - "type": "rich-text", - "source": "rich-text", - "selector": "cite", - "role": "content" - }, - "textAlign": { - "type": "string" - } - }, - "supports": { - "anchor": true, - "align": [ "left", "right", "wide", "full" ], - "html": false, - "background": { - "backgroundImage": true, - "backgroundSize": true, - "__experimentalDefaultControls": { - "backgroundImage": true - } - }, - "__experimentalBorder": { - "color": true, - "radius": true, - "style": true, - "width": true, - "__experimentalDefaultControls": { - "color": true, - "radius": true, - "style": true, - "width": true - } - }, - "dimensions": { - "minHeight": true, - "__experimentalDefaultControls": { - "minHeight": false - } - }, - "__experimentalOnEnter": true, - "__experimentalOnMerge": true, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "color": { - "gradients": true, - "heading": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "layout": { - "allowEditing": false - }, - "spacing": { - "blockGap": true, - "padding": true, - "margin": true - }, - "interactivity": { - "clientNavigation": true - }, - "allowedBlocks": true - }, - "styles": [ - { - "name": "default", - "label": "Default", - "isDefault": true - }, - { "name": "plain", "label": "Plain" } - ], - "editorStyle": "wp-block-quote-editor", - "style": "wp-block-quote" -} diff --git a/src/wp-includes/blocks/read-more.php b/src/wp-includes/blocks/read-more.php deleted file mode 100644 index c01a0a377fc93..0000000000000 --- a/src/wp-includes/blocks/read-more.php +++ /dev/null @@ -1,63 +0,0 @@ -context['postId'] ) ) { - return ''; - } - - $post_ID = $block->context['postId']; - $post_title = get_the_title( $post_ID ); - if ( '' === $post_title ) { - $post_title = sprintf( - /* translators: %s is post ID to describe the link for screen readers. */ - __( 'untitled post %s' ), - $post_ID - ); - } - $screen_reader_text = sprintf( - /* translators: %s is either the post title or post ID to describe the link for screen readers. */ - __( ': %s' ), - $post_title - ); - $justify_class_name = empty( $attributes['justifyContent'] ) ? '' : "is-justified-{$attributes['justifyContent']}"; - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => $justify_class_name ) ); - $more_text = ! empty( $attributes['content'] ) ? wp_kses_post( $attributes['content'] ) : __( 'Read more' ); - return sprintf( - '%4s%5s', - $wrapper_attributes, - get_the_permalink( $post_ID ), - esc_attr( $attributes['linkTarget'] ), - $more_text, - $screen_reader_text - ); -} - -/** - * Registers the `core/read-more` block on the server. - * - * @since 6.0.0 - */ -function register_block_core_read_more() { - register_block_type_from_metadata( - __DIR__ . '/read-more', - array( - 'render_callback' => 'render_block_core_read_more', - ) - ); -} -add_action( 'init', 'register_block_core_read_more' ); diff --git a/src/wp-includes/blocks/read-more/block.json b/src/wp-includes/blocks/read-more/block.json deleted file mode 100644 index eabc7acf3e3a3..0000000000000 --- a/src/wp-includes/blocks/read-more/block.json +++ /dev/null @@ -1,60 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/read-more", - "title": "Read More", - "category": "theme", - "description": "Displays the link of a post, page, or any other content-type.", - "textdomain": "default", - "attributes": { - "content": { - "type": "string", - "role": "content" - }, - "linkTarget": { - "type": "string", - "default": "_self" - } - }, - "usesContext": [ "postId" ], - "supports": { - "html": false, - "color": { - "gradients": true, - "text": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalLetterSpacing": true, - "__experimentalTextDecoration": true, - "__experimentalDefaultControls": { - "fontSize": true, - "textDecoration": true - } - }, - "spacing": { - "margin": [ "top", "bottom" ], - "padding": true, - "__experimentalDefaultControls": { - "padding": true - } - }, - "__experimentalBorder": { - "color": true, - "radius": true, - "width": true, - "__experimentalDefaultControls": { - "width": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "style": "wp-block-read-more" -} diff --git a/src/wp-includes/blocks/require-dynamic-blocks.php b/src/wp-includes/blocks/require-dynamic-blocks.php deleted file mode 100644 index df5be6face017..0000000000000 --- a/src/wp-includes/blocks/require-dynamic-blocks.php +++ /dev/null @@ -1,80 +0,0 @@ -
      ' . __( 'Adding an RSS feed to this site’s homepage is not supported, as it could lead to a loop that slows down your site. Try using another block, like the Latest Posts block, to list posts from the site.' ) . '
      '; - } - - $rss = fetch_feed( $attributes['feedURL'] ); - - if ( is_wp_error( $rss ) ) { - return '
      ' . __( 'RSS Error:' ) . ' ' . esc_html( $rss->get_error_message() ) . '
      '; - } - - if ( ! $rss->get_item_quantity() ) { - return '
      ' . __( 'An error has occurred, which probably means the feed is down. Try again later.' ) . '
      '; - } - - $rss_items = $rss->get_items( 0, $attributes['itemsToShow'] ); - $list_items = ''; - - $open_in_new_tab = ! empty( $attributes['openInNewTab'] ); - $rel = ! empty( $attributes['rel'] ) ? trim( $attributes['rel'] ) : ''; - - $link_attributes = ''; - - if ( $open_in_new_tab ) { - $link_attributes .= ' target="_blank"'; - } - - if ( '' !== $rel ) { - $link_attributes .= ' rel="' . esc_attr( $rel ) . '"'; - } - - foreach ( $rss_items as $item ) { - $title = esc_html( trim( strip_tags( html_entity_decode( $item->get_title() ) ) ) ); - - if ( empty( $title ) ) { - $title = __( '(no title)' ); - } - $link = $item->get_link(); - $link = esc_url( $link ); - - if ( $link ) { - $title = "{$title}"; - } - $title = "
      {$title}
      "; - - $date_markup = ''; - if ( ! empty( $attributes['displayDate'] ) ) { - $timestamp = $item->get_date( 'U' ); - - if ( $timestamp ) { - $gmt_offset = get_option( 'gmt_offset' ); - $timestamp += (int) ( (float) $gmt_offset * HOUR_IN_SECONDS ); - - $date_markup = sprintf( - ' ', - esc_attr( date_i18n( 'c', $timestamp ) ), - esc_html( date_i18n( get_option( 'date_format' ), $timestamp ) ) - ); - } - } - - $author = ''; - if ( $attributes['displayAuthor'] ) { - $author = $item->get_author(); - if ( is_object( $author ) ) { - $author = $author->get_name(); - if ( ! empty( $author ) ) { - $author = '' . sprintf( - /* translators: byline. %s: author. */ - __( 'by %s' ), - esc_html( strip_tags( $author ) ) - ) . ''; - } - } - } - - $excerpt = ''; - $description = $item->get_description(); - if ( $attributes['displayExcerpt'] && ! empty( $description ) ) { - $excerpt = html_entity_decode( $description, ENT_QUOTES, get_option( 'blog_charset' ) ); - $excerpt = esc_attr( wp_trim_words( $excerpt, $attributes['excerptLength'], ' […]' ) ); - - // Change existing [...] to […]. - if ( '[...]' === substr( $excerpt, -5 ) ) { - $excerpt = substr( $excerpt, 0, -5 ) . '[…]'; - } - - $excerpt = '
      ' . esc_html( $excerpt ) . '
      '; - } - - $list_items .= "
    6. {$title}{$date_markup}{$author}{$excerpt}
    7. "; - } - - $classnames = array(); - if ( isset( $attributes['blockLayout'] ) && 'grid' === $attributes['blockLayout'] ) { - $classnames[] = 'is-grid'; - } - if ( isset( $attributes['columns'] ) && 'grid' === $attributes['blockLayout'] ) { - $classnames[] = 'columns-' . $attributes['columns']; - } - if ( $attributes['displayDate'] ) { - $classnames[] = 'has-dates'; - } - if ( $attributes['displayAuthor'] ) { - $classnames[] = 'has-authors'; - } - if ( $attributes['displayExcerpt'] ) { - $classnames[] = 'has-excerpts'; - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classnames ) ) ); - - return sprintf( '
        %s
      ', $wrapper_attributes, $list_items ); -} - -/** - * Registers the `core/rss` block on server. - * - * @since 5.2.0 - */ -function register_block_core_rss() { - register_block_type_from_metadata( - __DIR__ . '/rss', - array( - 'render_callback' => 'render_block_core_rss', - ) - ); -} -add_action( 'init', 'register_block_core_rss' ); diff --git a/src/wp-includes/blocks/rss/block.json b/src/wp-includes/blocks/rss/block.json deleted file mode 100644 index fc49e1d858e89..0000000000000 --- a/src/wp-includes/blocks/rss/block.json +++ /dev/null @@ -1,81 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/rss", - "title": "RSS", - "category": "widgets", - "description": "Display entries from any RSS or Atom feed.", - "keywords": [ "atom", "feed" ], - "textdomain": "default", - "attributes": { - "columns": { - "type": "number", - "default": 2 - }, - "blockLayout": { - "type": "string", - "default": "list" - }, - "feedURL": { - "type": "string", - "default": "", - "role": "content" - }, - "itemsToShow": { - "type": "number", - "default": 5 - }, - "displayExcerpt": { - "type": "boolean", - "default": false - }, - "displayAuthor": { - "type": "boolean", - "default": false - }, - "displayDate": { - "type": "boolean", - "default": false - }, - "excerptLength": { - "type": "number", - "default": 55 - }, - "openInNewTab": { - "type": "boolean", - "default": false - }, - "rel": { - "type": "string" - } - }, - "supports": { - "align": true, - "html": false, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true - }, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "padding": false, - "margin": false - } - }, - "color": { - "background": true, - "text": true, - "gradients": true, - "link": true - } - }, - "editorStyle": "wp-block-rss-editor", - "style": "wp-block-rss" -} diff --git a/src/wp-includes/blocks/search.php b/src/wp-includes/blocks/search.php deleted file mode 100644 index 7073d6ce8ab3f..0000000000000 --- a/src/wp-includes/blocks/search.php +++ /dev/null @@ -1,621 +0,0 @@ -`. Support these by defaulting an undefined label and - // buttonText to `__( 'Search' )`. - $attributes = wp_parse_args( - $attributes, - array( - 'label' => __( 'Search' ), - 'buttonText' => __( 'Search' ), - ) - ); - - $input_id = wp_unique_id( 'wp-block-search__input-' ); - $classnames = classnames_for_block_core_search( $attributes ); - $show_label = ! empty( $attributes['showLabel'] ); - $use_icon_button = ! empty( $attributes['buttonUseIcon'] ); - $show_button = ( ! empty( $attributes['buttonPosition'] ) && 'no-button' === $attributes['buttonPosition'] ) ? false : true; - $button_position = $show_button ? $attributes['buttonPosition'] : null; - $query_params = ( ! empty( $attributes['query'] ) ) ? $attributes['query'] : array(); - $button = ''; - $query_params_markup = ''; - $inline_styles = styles_for_block_core_search( $attributes ); - $color_classes = get_color_classes_for_block_core_search( $attributes ); - $typography_classes = get_typography_classes_for_block_core_search( $attributes ); - $is_button_inside = ! empty( $attributes['buttonPosition'] ) && - 'button-inside' === $attributes['buttonPosition']; - // Border color classes need to be applied to the elements that have a border color. - $border_color_classes = get_border_color_classes_for_block_core_search( $attributes ); - // This variable is a constant and its value is always false at this moment. - // It is defined this way because some values depend on it, in case it changes in the future. - $open_by_default = false; - - $label_inner_html = empty( $attributes['label'] ) ? __( 'Search' ) : wp_kses_post( $attributes['label'] ); - $label = new WP_HTML_Tag_Processor( sprintf( '', $inline_styles['label'], $label_inner_html ) ); - if ( $label->next_tag() ) { - $label->set_attribute( 'for', $input_id ); - $label->add_class( 'wp-block-search__label' ); - if ( $show_label && ! empty( $attributes['label'] ) ) { - if ( ! empty( $typography_classes ) ) { - $label->add_class( $typography_classes ); - } - } else { - $label->add_class( 'screen-reader-text' ); - } - } - - $input = new WP_HTML_Tag_Processor( sprintf( '', $inline_styles['input'] ) ); - $input_classes = array( 'wp-block-search__input' ); - if ( ! $is_button_inside && ! empty( $border_color_classes ) ) { - $input_classes[] = $border_color_classes; - } - if ( ! empty( $typography_classes ) ) { - $input_classes[] = $typography_classes; - } - if ( $input->next_tag() ) { - $input->add_class( implode( ' ', $input_classes ) ); - $input->set_attribute( 'id', $input_id ); - $input->set_attribute( 'value', get_search_query() ); - $input->set_attribute( 'placeholder', $attributes['placeholder'] ); - - // If it's interactive, enqueue the script module and add the directives. - $is_expandable_searchfield = 'button-only' === $button_position; - if ( $is_expandable_searchfield ) { - wp_enqueue_script_module( '@wordpress/block-library/search/view' ); - - $input->set_attribute( 'data-wp-bind--aria-hidden', '!context.isSearchInputVisible' ); - $input->set_attribute( 'data-wp-bind--tabindex', 'state.tabindex' ); - - // Adding these attributes manually is needed until the Interactivity API - // SSR logic is added to core. - $input->set_attribute( 'aria-hidden', 'true' ); - $input->set_attribute( 'tabindex', '-1' ); - } - } - - if ( count( $query_params ) > 0 ) { - foreach ( $query_params as $param => $value ) { - $query_params_markup .= sprintf( - '', - esc_attr( $param ), - esc_attr( $value ) - ); - } - } - - if ( $show_button ) { - $button_classes = array( 'wp-block-search__button' ); - $button_internal_markup = ''; - if ( ! empty( $color_classes ) ) { - $button_classes[] = $color_classes; - } - if ( ! empty( $typography_classes ) ) { - $button_classes[] = $typography_classes; - } - - if ( ! $is_button_inside && ! empty( $border_color_classes ) ) { - $button_classes[] = $border_color_classes; - } - if ( ! $use_icon_button ) { - if ( ! empty( $attributes['buttonText'] ) ) { - $button_internal_markup = wp_kses_post( $attributes['buttonText'] ); - } - } else { - $button_classes[] = 'has-icon'; - $button_internal_markup = - ' - - '; - } - - // Include the button element class. - $button_classes[] = wp_theme_get_element_class_name( 'button' ); - $button = new WP_HTML_Tag_Processor( sprintf( '', $inline_styles['button'], $button_internal_markup ) ); - - if ( $button->next_tag() ) { - $button->add_class( implode( ' ', $button_classes ) ); - if ( 'button-only' === $attributes['buttonPosition'] ) { - $button->set_attribute( 'data-wp-bind--aria-label', 'state.ariaLabel' ); - $button->set_attribute( 'data-wp-bind--aria-controls', 'state.ariaControls' ); - $button->set_attribute( 'data-wp-bind--aria-expanded', 'context.isSearchInputVisible' ); - $button->set_attribute( 'data-wp-bind--type', 'state.type' ); - $button->set_attribute( 'data-wp-on--click', 'actions.openSearchInput' ); - - // Adding these attributes manually is needed until the Interactivity - // API SSR logic is added to core. - $button->set_attribute( 'aria-label', __( 'Expand search field' ) ); - $button->set_attribute( 'aria-controls', 'wp-block-search__input-' . $input_id ); - $button->set_attribute( 'aria-expanded', 'false' ); - $button->set_attribute( 'type', 'button' ); - } else { - $button->set_attribute( 'aria-label', wp_strip_all_tags( $attributes['buttonText'] ) ); - } - } - } - - $field_markup_classes = array( - 'wp-block-search__inside-wrapper', - ); - if ( $is_button_inside && ! empty( $border_color_classes ) ) { - $field_markup_classes[] = $border_color_classes; - } - $field_markup = sprintf( - '
      %s
      ', - esc_attr( implode( ' ', $field_markup_classes ) ), - $inline_styles['wrapper'], - $input . $query_params_markup . $button - ); - $wrapper_attributes = get_block_wrapper_attributes( - array( 'class' => $classnames ) - ); - $form_directives = ''; - - // If it's interactive, add the directives. - if ( $is_expandable_searchfield ) { - $aria_label_expanded = __( 'Submit Search' ); - $aria_label_collapsed = __( 'Expand search field' ); - $form_context = wp_interactivity_data_wp_context( - array( - 'isSearchInputVisible' => $open_by_default, - 'inputId' => $input_id, - 'ariaLabelExpanded' => $aria_label_expanded, - 'ariaLabelCollapsed' => $aria_label_collapsed, - ) - ); - $form_directives = ' - data-wp-interactive="core/search" - ' . $form_context . ' - data-wp-class--wp-block-search__searchfield-hidden="!context.isSearchInputVisible" - data-wp-on--keydown="actions.handleSearchKeydown" - data-wp-on--focusout="actions.handleSearchFocusout" - '; - } - - return sprintf( - '%4s', - esc_url( home_url( '/' ) ), - $wrapper_attributes, - $form_directives, - $label . $field_markup - ); -} - -/** - * Registers the `core/search` block on the server. - * - * @since 5.2.0 - */ -function register_block_core_search() { - register_block_type_from_metadata( - __DIR__ . '/search', - array( - 'render_callback' => 'render_block_core_search', - ) - ); -} -add_action( 'init', 'register_block_core_search' ); - -/** - * Builds the correct top level classnames for the 'core/search' block. - * - * @since 5.6.0 - * - * @param array $attributes The block attributes. - * - * @return string The classnames used in the block. - */ -function classnames_for_block_core_search( $attributes ) { - $classnames = array(); - - if ( ! empty( $attributes['buttonPosition'] ) ) { - if ( 'button-inside' === $attributes['buttonPosition'] ) { - $classnames[] = 'wp-block-search__button-inside'; - } - - if ( 'button-outside' === $attributes['buttonPosition'] ) { - $classnames[] = 'wp-block-search__button-outside'; - } - - if ( 'no-button' === $attributes['buttonPosition'] ) { - $classnames[] = 'wp-block-search__no-button'; - } - - if ( 'button-only' === $attributes['buttonPosition'] ) { - $classnames[] = 'wp-block-search__button-only wp-block-search__searchfield-hidden'; - } - } - - if ( isset( $attributes['buttonUseIcon'] ) ) { - if ( ! empty( $attributes['buttonPosition'] ) && 'no-button' !== $attributes['buttonPosition'] ) { - if ( $attributes['buttonUseIcon'] ) { - $classnames[] = 'wp-block-search__icon-button'; - } else { - $classnames[] = 'wp-block-search__text-button'; - } - } - } - - return implode( ' ', $classnames ); -} - -/** - * This generates a CSS rule for the given border property and side if provided. - * Based on whether the Search block is configured to display the button inside - * or not, the generated rule is injected into the appropriate collection of - * styles for later application in the block's markup. - * - * @since 6.1.0 - * - * @param array $attributes The block attributes. - * @param string $property Border property to generate rule for e.g. width or color. - * @param string $side Optional side border. The dictates the value retrieved and final CSS property. - * @param array $wrapper_styles Current collection of wrapper styles. - * @param array $button_styles Current collection of button styles. - * @param array $input_styles Current collection of input styles. - */ -function apply_block_core_search_border_style( $attributes, $property, $side, &$wrapper_styles, &$button_styles, &$input_styles ) { - $is_button_inside = isset( $attributes['buttonPosition'] ) && 'button-inside' === $attributes['buttonPosition']; - - $path = array( 'style', 'border', $property ); - - if ( $side ) { - array_splice( $path, 2, 0, $side ); - } - - $value = _wp_array_get( $attributes, $path, false ); - - if ( empty( $value ) ) { - return; - } - - if ( 'color' === $property && $side ) { - $has_color_preset = str_contains( $value, 'var:preset|color|' ); - if ( $has_color_preset ) { - $named_color_value = substr( $value, strrpos( $value, '|' ) + 1 ); - $value = sprintf( 'var(--wp--preset--color--%s)', $named_color_value ); - } - } - - $property_suffix = $side ? sprintf( '%s-%s', $side, $property ) : $property; - - if ( $is_button_inside ) { - $wrapper_styles[] = sprintf( 'border-%s: %s;', $property_suffix, esc_attr( $value ) ); - } else { - $button_styles[] = sprintf( 'border-%s: %s;', $property_suffix, esc_attr( $value ) ); - $input_styles[] = sprintf( 'border-%s: %s;', $property_suffix, esc_attr( $value ) ); - } -} - -/** - * This adds CSS rules for a given border property e.g. width or color. It - * injects rules into the provided wrapper, button and input style arrays for - * uniform "flat" borders or those with individual sides configured. - * - * @since 6.1.0 - * - * @param array $attributes The block attributes. - * @param string $property Border property to generate rule for e.g. width or color. - * @param array $wrapper_styles Current collection of wrapper styles. - * @param array $button_styles Current collection of button styles. - * @param array $input_styles Current collection of input styles. - */ -function apply_block_core_search_border_styles( $attributes, $property, &$wrapper_styles, &$button_styles, &$input_styles ) { - apply_block_core_search_border_style( $attributes, $property, null, $wrapper_styles, $button_styles, $input_styles ); - apply_block_core_search_border_style( $attributes, $property, 'top', $wrapper_styles, $button_styles, $input_styles ); - apply_block_core_search_border_style( $attributes, $property, 'right', $wrapper_styles, $button_styles, $input_styles ); - apply_block_core_search_border_style( $attributes, $property, 'bottom', $wrapper_styles, $button_styles, $input_styles ); - apply_block_core_search_border_style( $attributes, $property, 'left', $wrapper_styles, $button_styles, $input_styles ); -} - -/** - * Builds an array of inline styles for the search block. - * - * The result will contain one entry for shared styles such as those for the - * inner input or button and a second for the inner wrapper should the block - * be positioning the button "inside". - * - * @since 5.8.0 - * - * @param array $attributes The block attributes. - * - * @return array Style HTML attribute. - */ -function styles_for_block_core_search( $attributes ) { - $wrapper_styles = array(); - $button_styles = array(); - $input_styles = array(); - $label_styles = array(); - $is_button_inside = ! empty( $attributes['buttonPosition'] ) && - 'button-inside' === $attributes['buttonPosition']; - $show_label = ( isset( $attributes['showLabel'] ) ) && false !== $attributes['showLabel']; - - // Add width styles. - $has_width = ! empty( $attributes['width'] ) && ! empty( $attributes['widthUnit'] ); - - if ( $has_width ) { - $wrapper_styles[] = sprintf( - 'width: %d%s;', - esc_attr( $attributes['width'] ), - esc_attr( $attributes['widthUnit'] ) - ); - } - - // Add border width and color styles. - apply_block_core_search_border_styles( $attributes, 'width', $wrapper_styles, $button_styles, $input_styles ); - apply_block_core_search_border_styles( $attributes, 'color', $wrapper_styles, $button_styles, $input_styles ); - apply_block_core_search_border_styles( $attributes, 'style', $wrapper_styles, $button_styles, $input_styles ); - - // Add border radius styles. - $has_border_radius = ! empty( $attributes['style']['border']['radius'] ); - - if ( $has_border_radius ) { - $default_padding = '4px'; - $border_radius = $attributes['style']['border']['radius']; - - if ( is_array( $border_radius ) ) { - // Apply styles for individual corner border radii. - foreach ( $border_radius as $key => $value ) { - // Get border-radius CSS variable from preset value if provided. - if ( is_string( $value ) && str_contains( $value, 'var:preset|border-radius|' ) ) { - $index_to_splice = strrpos( $value, '|' ) + 1; - $slug = _wp_to_kebab_case( substr( $value, $index_to_splice ) ); - $value = "var(--wp--preset--border-radius--$slug)"; - } - - if ( null !== $value ) { - // Convert camelCase key to kebab-case. - $name = strtolower( preg_replace( '/(? ! empty( $input_styles ) ? sprintf( ' style="%s"', esc_attr( safecss_filter_attr( implode( ' ', $input_styles ) ) ) ) : '', - 'button' => ! empty( $button_styles ) ? sprintf( ' style="%s"', esc_attr( safecss_filter_attr( implode( ' ', $button_styles ) ) ) ) : '', - 'wrapper' => ! empty( $wrapper_styles ) ? sprintf( ' style="%s"', esc_attr( safecss_filter_attr( implode( ' ', $wrapper_styles ) ) ) ) : '', - 'label' => ! empty( $label_styles ) ? sprintf( ' style="%s"', esc_attr( safecss_filter_attr( implode( ' ', $label_styles ) ) ) ) : '', - ); -} - -/** - * Returns typography classnames depending on whether there are named font sizes/families. - * - * @since 6.1.0 - * - * @param array $attributes The block attributes. - * - * @return string The typography color classnames to be applied to the block elements. - */ -function get_typography_classes_for_block_core_search( $attributes ) { - $typography_classes = array(); - $has_named_font_family = ! empty( $attributes['fontFamily'] ); - $has_named_font_size = ! empty( $attributes['fontSize'] ); - - if ( $has_named_font_size ) { - $typography_classes[] = sprintf( 'has-%s-font-size', esc_attr( $attributes['fontSize'] ) ); - } - - if ( $has_named_font_family ) { - $typography_classes[] = sprintf( 'has-%s-font-family', esc_attr( $attributes['fontFamily'] ) ); - } - - return implode( ' ', $typography_classes ); -} - -/** - * Returns typography styles to be included in an HTML style tag. - * This excludes text-decoration, which is applied only to the label and button elements of the search block. - * - * @since 6.1.0 - * - * @param array $attributes The block attributes. - * - * @return string A string of typography CSS declarations. - */ -function get_typography_styles_for_block_core_search( $attributes ) { - $typography_styles = array(); - - // Add typography styles. - if ( ! empty( $attributes['style']['typography']['fontSize'] ) ) { - $typography_styles[] = sprintf( - 'font-size: %s;', - wp_get_typography_font_size_value( - array( - 'size' => $attributes['style']['typography']['fontSize'], - ) - ) - ); - - } - - if ( ! empty( $attributes['style']['typography']['fontFamily'] ) ) { - $typography_styles[] = sprintf( 'font-family: %s;', $attributes['style']['typography']['fontFamily'] ); - } - - if ( ! empty( $attributes['style']['typography']['letterSpacing'] ) ) { - $typography_styles[] = sprintf( 'letter-spacing: %s;', $attributes['style']['typography']['letterSpacing'] ); - } - - if ( ! empty( $attributes['style']['typography']['fontWeight'] ) ) { - $typography_styles[] = sprintf( 'font-weight: %s;', $attributes['style']['typography']['fontWeight'] ); - } - - if ( ! empty( $attributes['style']['typography']['fontStyle'] ) ) { - $typography_styles[] = sprintf( 'font-style: %s;', $attributes['style']['typography']['fontStyle'] ); - } - - if ( ! empty( $attributes['style']['typography']['lineHeight'] ) ) { - $typography_styles[] = sprintf( 'line-height: %s;', $attributes['style']['typography']['lineHeight'] ); - } - - if ( ! empty( $attributes['style']['typography']['textTransform'] ) ) { - $typography_styles[] = sprintf( 'text-transform: %s;', $attributes['style']['typography']['textTransform'] ); - } - - return implode( '', $typography_styles ); -} - -/** - * Returns border color classnames depending on whether there are named or custom border colors. - * - * @since 5.9.0 - * - * @param array $attributes The block attributes. - * - * @return string The border color classnames to be applied to the block elements. - */ -function get_border_color_classes_for_block_core_search( $attributes ) { - $border_color_classes = array(); - $has_custom_border_color = ! empty( $attributes['style']['border']['color'] ); - $has_named_border_color = ! empty( $attributes['borderColor'] ); - - if ( $has_custom_border_color || $has_named_border_color ) { - $border_color_classes[] = 'has-border-color'; - } - - if ( $has_named_border_color ) { - $border_color_classes[] = sprintf( 'has-%s-border-color', esc_attr( $attributes['borderColor'] ) ); - } - - return implode( ' ', $border_color_classes ); -} - -/** - * Returns color classnames depending on whether there are named or custom text and background colors. - * - * @since 5.9.0 - * - * @param array $attributes The block attributes. - * - * @return string The color classnames to be applied to the block elements. - */ -function get_color_classes_for_block_core_search( $attributes ) { - $classnames = array(); - - // Text color. - $has_named_text_color = ! empty( $attributes['textColor'] ); - $has_custom_text_color = ! empty( $attributes['style']['color']['text'] ); - if ( $has_named_text_color ) { - $classnames[] = sprintf( 'has-text-color has-%s-color', $attributes['textColor'] ); - } elseif ( $has_custom_text_color ) { - // If a custom 'textColor' was selected instead of a preset, still add the generic `has-text-color` class. - $classnames[] = 'has-text-color'; - } - - // Background color. - $has_named_background_color = ! empty( $attributes['backgroundColor'] ); - $has_custom_background_color = ! empty( $attributes['style']['color']['background'] ); - $has_named_gradient = ! empty( $attributes['gradient'] ); - $has_custom_gradient = ! empty( $attributes['style']['color']['gradient'] ); - if ( - $has_named_background_color || - $has_custom_background_color || - $has_named_gradient || - $has_custom_gradient - ) { - $classnames[] = 'has-background'; - } - if ( $has_named_background_color ) { - $classnames[] = sprintf( 'has-%s-background-color', $attributes['backgroundColor'] ); - } - if ( $has_named_gradient ) { - $classnames[] = sprintf( 'has-%s-gradient-background', $attributes['gradient'] ); - } - - return implode( ' ', $classnames ); -} diff --git a/src/wp-includes/blocks/search/block.json b/src/wp-includes/blocks/search/block.json deleted file mode 100644 index c5af5a29d21be..0000000000000 --- a/src/wp-includes/blocks/search/block.json +++ /dev/null @@ -1,95 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/search", - "title": "Search", - "category": "widgets", - "description": "Help visitors find your content.", - "keywords": [ "find" ], - "textdomain": "default", - "attributes": { - "label": { - "type": "string", - "role": "content" - }, - "showLabel": { - "type": "boolean", - "default": true - }, - "placeholder": { - "type": "string", - "default": "", - "role": "content" - }, - "width": { - "type": "number" - }, - "widthUnit": { - "type": "string" - }, - "buttonText": { - "type": "string", - "role": "content" - }, - "buttonPosition": { - "type": "string", - "default": "button-outside" - }, - "buttonUseIcon": { - "type": "boolean", - "default": false - }, - "query": { - "type": "object", - "default": {} - }, - "isSearchFieldHidden": { - "type": "boolean", - "default": false - } - }, - "supports": { - "align": [ "left", "center", "right" ], - "color": { - "gradients": true, - "__experimentalSkipSerialization": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "interactivity": true, - "typography": { - "__experimentalSkipSerialization": true, - "__experimentalSelector": ".wp-block-search__label, .wp-block-search__input, .wp-block-search__button", - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "__experimentalBorder": { - "color": true, - "radius": true, - "width": true, - "__experimentalSkipSerialization": true, - "__experimentalDefaultControls": { - "color": true, - "radius": true, - "width": true - } - }, - "spacing": { - "margin": true - }, - "html": false - }, - "editorStyle": "wp-block-search-editor", - "style": "wp-block-search" -} diff --git a/src/wp-includes/blocks/search/view.asset.php b/src/wp-includes/blocks/search/view.asset.php deleted file mode 100644 index e9b5021ae35c5..0000000000000 --- a/src/wp-includes/blocks/search/view.asset.php +++ /dev/null @@ -1 +0,0 @@ - array(), 'version' => '2a0784014283afdd3c25'); diff --git a/src/wp-includes/blocks/search/view.min.asset.php b/src/wp-includes/blocks/search/view.min.asset.php deleted file mode 100644 index f9f2fddc7dd06..0000000000000 --- a/src/wp-includes/blocks/search/view.min.asset.php +++ /dev/null @@ -1 +0,0 @@ - array(), 'version' => '765a40956d200c79d99e'); diff --git a/src/wp-includes/blocks/separator/block.json b/src/wp-includes/blocks/separator/block.json deleted file mode 100644 index 926d978b7e4d5..0000000000000 --- a/src/wp-includes/blocks/separator/block.json +++ /dev/null @@ -1,48 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/separator", - "title": "Separator", - "category": "design", - "description": "Create a break between ideas or sections with a horizontal separator.", - "keywords": [ "horizontal-line", "hr", "divider" ], - "textdomain": "default", - "attributes": { - "opacity": { - "type": "string", - "default": "alpha-channel" - }, - "tagName": { - "type": "string", - "enum": [ "hr", "div" ], - "default": "hr" - } - }, - "supports": { - "anchor": true, - "align": [ "center", "wide", "full" ], - "color": { - "enableContrastChecker": false, - "__experimentalSkipSerialization": true, - "gradients": true, - "background": true, - "text": false, - "__experimentalDefaultControls": { - "background": true - } - }, - "spacing": { - "margin": [ "top", "bottom" ] - }, - "interactivity": { - "clientNavigation": true - } - }, - "styles": [ - { "name": "default", "label": "Default", "isDefault": true }, - { "name": "wide", "label": "Wide Line" }, - { "name": "dots", "label": "Dots" } - ], - "editorStyle": "wp-block-separator-editor", - "style": "wp-block-separator" -} diff --git a/src/wp-includes/blocks/shortcode.php b/src/wp-includes/blocks/shortcode.php deleted file mode 100644 index d96acfc55fa64..0000000000000 --- a/src/wp-includes/blocks/shortcode.php +++ /dev/null @@ -1,35 +0,0 @@ - 'render_block_core_shortcode', - ) - ); -} -add_action( 'init', 'register_block_core_shortcode' ); diff --git a/src/wp-includes/blocks/shortcode/block.json b/src/wp-includes/blocks/shortcode/block.json deleted file mode 100644 index 6e30210b7c081..0000000000000 --- a/src/wp-includes/blocks/shortcode/block.json +++ /dev/null @@ -1,22 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/shortcode", - "title": "Shortcode", - "category": "widgets", - "description": "Insert additional custom elements with a WordPress shortcode.", - "textdomain": "default", - "attributes": { - "text": { - "type": "string", - "source": "raw", - "role": "content" - } - }, - "supports": { - "className": false, - "customClassName": false, - "html": false - }, - "editorStyle": "wp-block-shortcode-editor" -} diff --git a/src/wp-includes/blocks/site-logo.php b/src/wp-includes/blocks/site-logo.php deleted file mode 100644 index 915563461e30c..0000000000000 --- a/src/wp-includes/blocks/site-logo.php +++ /dev/null @@ -1,234 +0,0 @@ -(.*?)#i', '\1', $custom_logo ); - } - - if ( $attributes['isLink'] && '_blank' === $attributes['linkTarget'] ) { - // Add the link target after the rel="home". - // Add an aria-label for informing that the page opens in a new tab. - $processor = new WP_HTML_Tag_Processor( $custom_logo ); - $processor->next_tag( 'a' ); - if ( 'home' === $processor->get_attribute( 'rel' ) ) { - $processor->set_attribute( 'aria-label', __( '(Home link, opens in a new tab)' ) ); - $processor->set_attribute( 'target', $attributes['linkTarget'] ); - } - $custom_logo = $processor->get_updated_html(); - } - - $classnames = array(); - if ( empty( $attributes['width'] ) ) { - $classnames[] = 'is-default-size'; - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classnames ) ) ); - $html = sprintf( '
      %s
      ', $wrapper_attributes, $custom_logo ); - return $html; -} - -/** - * Register a core site setting for a site logo - * - * @since 5.8.0 - */ -function register_block_core_site_logo_setting() { - register_setting( - 'general', - 'site_logo', - array( - 'show_in_rest' => array( - 'name' => 'site_logo', - ), - 'type' => 'integer', - 'label' => __( 'Logo' ), - 'description' => __( 'Site logo.' ), - ) - ); -} - -add_action( 'rest_api_init', 'register_block_core_site_logo_setting', 10 ); - -/** - * Register a core site setting for a site icon - * - * @since 5.9.0 - */ -function register_block_core_site_icon_setting() { - register_setting( - 'general', - 'site_icon', - array( - 'show_in_rest' => true, - 'type' => 'integer', - 'label' => __( 'Icon' ), - 'description' => __( 'Site icon.' ), - ) - ); -} - -add_action( 'rest_api_init', 'register_block_core_site_icon_setting', 10 ); - -/** - * Registers the `core/site-logo` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_site_logo() { - register_block_type_from_metadata( - __DIR__ . '/site-logo', - array( - 'render_callback' => 'render_block_core_site_logo', - ) - ); -} - -add_action( 'init', 'register_block_core_site_logo' ); - -/** - * Overrides the custom logo with a site logo, if the option is set. - * - * @since 5.8.0 - * - * @param string $custom_logo The custom logo set by a theme. - * - * @return string The site logo if set. - */ -function _override_custom_logo_theme_mod( $custom_logo ) { - $site_logo = get_option( 'site_logo' ); - return false === $site_logo ? $custom_logo : $site_logo; -} - -add_filter( 'theme_mod_custom_logo', '_override_custom_logo_theme_mod' ); - -/** - * Updates the site_logo option when the custom_logo theme-mod gets updated. - * - * @since 5.8.0 - * - * @param mixed $value Attachment ID of the custom logo or an empty value. - * @return mixed - */ -function _sync_custom_logo_to_site_logo( $value ) { - if ( empty( $value ) ) { - delete_option( 'site_logo' ); - } else { - update_option( 'site_logo', $value ); - } - - return $value; -} - -add_filter( 'pre_set_theme_mod_custom_logo', '_sync_custom_logo_to_site_logo' ); - -/** - * Deletes the site_logo when the custom_logo theme mod is removed. - * - * @since 5.8.0 - * - * @global array $_ignore_site_logo_changes - * - * @param array $old_value Previous theme mod settings. - * @param array $value Updated theme mod settings. - */ -function _delete_site_logo_on_remove_custom_logo( $old_value, $value ) { - global $_ignore_site_logo_changes; - - if ( $_ignore_site_logo_changes ) { - return; - } - - // If the custom_logo is being unset, it's being removed from theme mods. - if ( isset( $old_value['custom_logo'] ) && ! isset( $value['custom_logo'] ) ) { - delete_option( 'site_logo' ); - } -} - -/** - * Deletes the site logo when all theme mods are being removed. - * - * @since 5.8.0 - * - * @global array $_ignore_site_logo_changes - */ -function _delete_site_logo_on_remove_theme_mods() { - global $_ignore_site_logo_changes; - - if ( $_ignore_site_logo_changes ) { - return; - } - - if ( false !== get_theme_support( 'custom-logo' ) ) { - delete_option( 'site_logo' ); - } -} - -/** - * Hooks `_delete_site_logo_on_remove_custom_logo` in `update_option_theme_mods_$theme`. - * Hooks `_delete_site_logo_on_remove_theme_mods` in `delete_option_theme_mods_$theme`. - * - * Runs on `setup_theme` to account for dynamically-switched themes in the Customizer. - * - * @since 5.8.0 - */ -function _delete_site_logo_on_remove_custom_logo_on_setup_theme() { - $theme = get_option( 'stylesheet' ); - add_action( "update_option_theme_mods_$theme", '_delete_site_logo_on_remove_custom_logo', 10, 2 ); - add_action( "delete_option_theme_mods_$theme", '_delete_site_logo_on_remove_theme_mods' ); -} -add_action( 'setup_theme', '_delete_site_logo_on_remove_custom_logo_on_setup_theme', 11 ); - -/** - * Removes the custom_logo theme-mod when the site_logo option gets deleted. - * - * @since 5.9.0 - * - * @global array $_ignore_site_logo_changes - */ -function _delete_custom_logo_on_remove_site_logo() { - global $_ignore_site_logo_changes; - - // Prevent _delete_site_logo_on_remove_custom_logo and - // _delete_site_logo_on_remove_theme_mods from firing and causing an - // infinite loop. - $_ignore_site_logo_changes = true; - - // Remove the custom logo. - remove_theme_mod( 'custom_logo' ); - - $_ignore_site_logo_changes = false; -} -add_action( 'delete_option_site_logo', '_delete_custom_logo_on_remove_site_logo' ); diff --git a/src/wp-includes/blocks/site-logo/block.json b/src/wp-includes/blocks/site-logo/block.json deleted file mode 100644 index b49588d3716fa..0000000000000 --- a/src/wp-includes/blocks/site-logo/block.json +++ /dev/null @@ -1,72 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/site-logo", - "title": "Site Logo", - "category": "theme", - "description": "Display an image to represent this site. Update this block and the changes apply everywhere.", - "textdomain": "default", - "attributes": { - "width": { - "type": "number" - }, - "isLink": { - "type": "boolean", - "default": true, - "role": "content" - }, - "linkTarget": { - "type": "string", - "default": "_self", - "role": "content" - }, - "shouldSyncIcon": { - "type": "boolean" - } - }, - "example": { - "viewportWidth": 500, - "attributes": { - "width": 350, - "className": "block-editor-block-types-list__site-logo-example" - } - }, - "supports": { - "html": false, - "align": true, - "alignWide": false, - "color": { - "text": false, - "background": false - }, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "interactivity": { - "clientNavigation": true - }, - "filter": { - "duotone": true - } - }, - "styles": [ - { - "name": "default", - "label": "Default", - "isDefault": true - }, - { "name": "rounded", "label": "Rounded" } - ], - "selectors": { - "filter": { - "duotone": ".wp-block-site-logo img, .wp-block-site-logo .components-placeholder__illustration, .wp-block-site-logo .components-placeholder::before" - } - }, - "editorStyle": "wp-block-site-logo-editor", - "style": "wp-block-site-logo" -} diff --git a/src/wp-includes/blocks/site-tagline.php b/src/wp-includes/blocks/site-tagline.php deleted file mode 100644 index b59e1e556c320..0000000000000 --- a/src/wp-includes/blocks/site-tagline.php +++ /dev/null @@ -1,53 +0,0 @@ - $align_class_name ) ); - - if ( isset( $attributes['level'] ) && 0 !== $attributes['level'] ) { - $tag_name = 'h' . (int) $attributes['level']; - } - - return sprintf( - '<%1$s %2$s>%3$s', - $tag_name, - $wrapper_attributes, - $site_tagline - ); -} - -/** - * Registers the `core/site-tagline` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_site_tagline() { - register_block_type_from_metadata( - __DIR__ . '/site-tagline', - array( - 'render_callback' => 'render_block_core_site_tagline', - ) - ); -} - -add_action( 'init', 'register_block_core_site_tagline' ); diff --git a/src/wp-includes/blocks/site-tagline/block.json b/src/wp-includes/blocks/site-tagline/block.json deleted file mode 100644 index 7f94d962e9cbc..0000000000000 --- a/src/wp-includes/blocks/site-tagline/block.json +++ /dev/null @@ -1,74 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/site-tagline", - "title": "Site Tagline", - "category": "theme", - "description": "Describe in a few words what this site is about. This is important for search results, sharing on social media, and gives overall clarity to visitors.", - "keywords": [ "description" ], - "textdomain": "default", - "attributes": { - "textAlign": { - "type": "string" - }, - "level": { - "type": "number", - "default": 0 - }, - "levelOptions": { - "type": "array", - "default": [ 0, 1, 2, 3, 4, 5, 6 ] - } - }, - "example": { - "viewportWidth": 350, - "attributes": { - "textAlign": "center" - } - }, - "supports": { - "align": [ "wide", "full" ], - "html": false, - "color": { - "gradients": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "contentRole": true, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalFontStyle": true, - "__experimentalFontWeight": true, - "__experimentalLetterSpacing": true, - "__experimentalWritingMode": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true - } - }, - "editorStyle": "wp-block-site-tagline-editor", - "style": "wp-block-site-tagline" -} diff --git a/src/wp-includes/blocks/site-title.php b/src/wp-includes/blocks/site-title.php deleted file mode 100644 index 297d99894e104..0000000000000 --- a/src/wp-includes/blocks/site-title.php +++ /dev/null @@ -1,69 +0,0 @@ -%4$s', - esc_url( home_url() ), - esc_attr( $link_target ), - $aria_current, - esc_html( $site_title ) - ); - } - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => trim( $classes ) ) ); - - return sprintf( - '<%1$s %2$s>%3$s', - $tag_name, - $wrapper_attributes, - // already pre-escaped if it is a link. - $attributes['isLink'] ? $site_title : esc_html( $site_title ) - ); -} - -/** - * Registers the `core/site-title` block on the server. - * - * @since 5.8.0 - */ -function register_block_core_site_title() { - register_block_type_from_metadata( - __DIR__ . '/site-title', - array( - 'render_callback' => 'render_block_core_site_title', - ) - ); -} -add_action( 'init', 'register_block_core_site_title' ); diff --git a/src/wp-includes/blocks/site-title/block.json b/src/wp-includes/blocks/site-title/block.json deleted file mode 100644 index 8edf6b945f9ce..0000000000000 --- a/src/wp-includes/blocks/site-title/block.json +++ /dev/null @@ -1,81 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/site-title", - "title": "Site Title", - "category": "theme", - "description": "Displays the name of this site. Update the block, and the changes apply everywhere it’s used. This will also appear in the browser title bar and in search results.", - "textdomain": "default", - "attributes": { - "level": { - "type": "number", - "default": 1 - }, - "levelOptions": { - "type": "array", - "default": [ 0, 1, 2, 3, 4, 5, 6 ] - }, - "textAlign": { - "type": "string" - }, - "isLink": { - "type": "boolean", - "default": true, - "role": "content" - }, - "linkTarget": { - "type": "string", - "default": "_self", - "role": "content" - } - }, - "example": { - "viewportWidth": 500 - }, - "supports": { - "align": [ "wide", "full" ], - "html": false, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "spacing": { - "padding": true, - "margin": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalFontStyle": true, - "__experimentalFontWeight": true, - "__experimentalLetterSpacing": true, - "__experimentalWritingMode": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true - } - }, - "editorStyle": "wp-block-site-title-editor", - "style": "wp-block-site-title" -} diff --git a/src/wp-includes/blocks/social-link.php b/src/wp-includes/blocks/social-link.php deleted file mode 100644 index 3673504bc9396..0000000000000 --- a/src/wp-includes/blocks/social-link.php +++ /dev/null @@ -1,408 +0,0 @@ -context['openInNewTab'] ) ? $block->context['openInNewTab'] : false; - - $text = ! empty( $attributes['label'] ) ? trim( $attributes['label'] ) : ''; - - $service = isset( $attributes['service'] ) ? $attributes['service'] : 'Icon'; - $url = isset( $attributes['url'] ) ? $attributes['url'] : false; - $text = $text ? $text : block_core_social_link_get_name( $service ); - $rel = isset( $attributes['rel'] ) ? $attributes['rel'] : ''; - $show_labels = array_key_exists( 'showLabels', $block->context ) ? $block->context['showLabels'] : false; - - // Don't render a link if there is no URL set. - if ( ! $url ) { - return ''; - } - - /** - * Prepend emails with `mailto:` if not set. - * The `is_email` returns false for emails with schema. - */ - if ( is_email( $url ) ) { - $url = 'mailto:' . antispambot( $url ); - } - - /** - * Prepend URL with https:// if it doesn't appear to contain a scheme - * and it's not a relative link or a fragment. - */ - if ( ! parse_url( $url, PHP_URL_SCHEME ) && ! str_starts_with( $url, '//' ) && ! str_starts_with( $url, '#' ) ) { - $url = 'https://' . $url; - } - - $icon = block_core_social_link_get_icon( $service ); - $wrapper_attributes = get_block_wrapper_attributes( - array( - 'class' => 'wp-social-link wp-social-link-' . $service . block_core_social_link_get_color_classes( $block->context ), - 'style' => block_core_social_link_get_color_styles( $block->context ), - ) - ); - - $link = '
    8. '; - $link .= ''; - $link .= $icon; - $link .= '' . esc_html( $text ) . ''; - $link .= '
    9. '; - - $processor = new WP_HTML_Tag_Processor( $link ); - $processor->next_tag( 'a' ); - if ( $open_in_new_tab ) { - $processor->set_attribute( 'rel', trim( $rel . ' noopener nofollow' ) ); - $processor->set_attribute( 'target', '_blank' ); - } elseif ( '' !== $rel ) { - $processor->set_attribute( 'rel', trim( $rel ) ); - } - return $processor->get_updated_html(); -} - -/** - * Registers the `core/social-link` blocks. - * - * @since 5.4.0 - */ -function register_block_core_social_link() { - register_block_type_from_metadata( - __DIR__ . '/social-link', - array( - 'render_callback' => 'render_block_core_social_link', - ) - ); -} -add_action( 'init', 'register_block_core_social_link' ); - - -/** - * Returns the SVG for social link. - * - * @since 5.4.0 - * - * @param string $service The service icon. - * - * @return string SVG Element for service icon. - */ -function block_core_social_link_get_icon( $service ) { - $services = block_core_social_link_services(); - if ( isset( $services[ $service ] ) && isset( $services[ $service ]['icon'] ) ) { - return $services[ $service ]['icon']; - } - - return $services['share']['icon']; -} - -/** - * Returns the brand name for social link. - * - * @since 5.4.0 - * - * @param string $service The service icon. - * - * @return string Brand label. - */ -function block_core_social_link_get_name( $service ) { - $services = block_core_social_link_services(); - if ( isset( $services[ $service ] ) && isset( $services[ $service ]['name'] ) ) { - return $services[ $service ]['name']; - } - - return $services['share']['name']; -} - -/** - * Returns the SVG for social link. - * - * @since 5.4.0 - * - * @param string $service The service slug to extract data from. - * @param string $field The field ('name', 'icon', etc) to extract for a service. - * - * @return array|string - */ -function block_core_social_link_services( $service = '', $field = '' ) { - $services_data = array( - 'fivehundredpx' => array( - 'name' => _x( '500px', 'social link block variation name' ), - 'icon' => '', - ), - 'amazon' => array( - 'name' => _x( 'Amazon', 'social link block variation name' ), - 'icon' => '', - ), - 'bandcamp' => array( - 'name' => _x( 'Bandcamp', 'social link block variation name' ), - 'icon' => '', - ), - 'behance' => array( - 'name' => _x( 'Behance', 'social link block variation name' ), - 'icon' => '', - ), - 'bluesky' => array( - 'name' => _x( 'Bluesky', 'social link block variation name' ), - 'icon' => '', - ), - 'chain' => array( - 'name' => _x( 'Link', 'social link block variation name' ), - 'icon' => '', - ), - 'codepen' => array( - 'name' => _x( 'CodePen', 'social link block variation name' ), - 'icon' => '', - ), - 'deviantart' => array( - 'name' => _x( 'DeviantArt', 'social link block variation name' ), - 'icon' => '', - ), - 'discord' => array( - 'name' => _x( 'Discord', 'social link block variation name' ), - 'icon' => '', - ), - 'dribbble' => array( - 'name' => _x( 'Dribbble', 'social link block variation name' ), - 'icon' => '', - ), - 'dropbox' => array( - 'name' => _x( 'Dropbox', 'social link block variation name' ), - 'icon' => '', - ), - 'etsy' => array( - 'name' => _x( 'Etsy', 'social link block variation name' ), - 'icon' => '', - ), - 'facebook' => array( - 'name' => _x( 'Facebook', 'social link block variation name' ), - 'icon' => '', - ), - 'feed' => array( - 'name' => _x( 'RSS Feed', 'social link block variation name' ), - 'icon' => '', - ), - 'flickr' => array( - 'name' => _x( 'Flickr', 'social link block variation name' ), - 'icon' => '', - ), - 'foursquare' => array( - 'name' => _x( 'Foursquare', 'social link block variation name' ), - 'icon' => '', - ), - 'goodreads' => array( - 'name' => _x( 'Goodreads', 'social link block variation name' ), - 'icon' => '', - ), - 'google' => array( - 'name' => _x( 'Google', 'social link block variation name' ), - 'icon' => '', - ), - 'github' => array( - 'name' => _x( 'GitHub', 'social link block variation name' ), - 'icon' => '', - ), - 'gravatar' => array( - 'name' => _x( 'Gravatar', 'social link block variation name' ), - 'icon' => '', - ), - 'instagram' => array( - 'name' => _x( 'Instagram', 'social link block variation name' ), - 'icon' => '', - ), - 'lastfm' => array( - 'name' => _x( 'Last.fm', 'social link block variation name' ), - 'icon' => '', - ), - 'linkedin' => array( - 'name' => _x( 'LinkedIn', 'social link block variation name' ), - 'icon' => '', - ), - 'mail' => array( - 'name' => _x( 'Mail', 'social link block variation name' ), - 'icon' => '', - ), - 'mastodon' => array( - 'name' => _x( 'Mastodon', 'social link block variation name' ), - 'icon' => '', - ), - 'meetup' => array( - 'name' => _x( 'Meetup', 'social link block variation name' ), - 'icon' => '', - ), - 'medium' => array( - 'name' => _x( 'Medium', 'social link block variation name' ), - 'icon' => '', - ), - 'patreon' => array( - 'name' => _x( 'Patreon', 'social link block variation name' ), - 'icon' => '', - ), - 'pinterest' => array( - 'name' => _x( 'Pinterest', 'social link block variation name' ), - 'icon' => '', - ), - 'pocket' => array( - 'name' => _x( 'Pocket', 'social link block variation name' ), - 'icon' => '', - ), - 'reddit' => array( - 'name' => _x( 'Reddit', 'social link block variation name' ), - 'icon' => '', - ), - 'share' => array( - 'name' => _x( 'Share Icon', 'social link block variation name' ), - 'icon' => '', - ), - 'skype' => array( - 'name' => _x( 'Skype', 'social link block variation name' ), - 'icon' => '', - ), - 'snapchat' => array( - 'name' => _x( 'Snapchat', 'social link block variation name' ), - 'icon' => '', - ), - 'soundcloud' => array( - 'name' => _x( 'SoundCloud', 'social link block variation name' ), - 'icon' => '', - ), - 'spotify' => array( - 'name' => _x( 'Spotify', 'social link block variation name' ), - 'icon' => '', - ), - 'telegram' => array( - 'name' => _x( 'Telegram', 'social link block variation name' ), - 'icon' => '', - ), - 'threads' => array( - 'name' => _x( 'Threads', 'social link block variation name' ), - 'icon' => '', - ), - 'tiktok' => array( - 'name' => _x( 'TikTok', 'social link block variation name' ), - 'icon' => '', - ), - 'tumblr' => array( - 'name' => _x( 'Tumblr', 'social link block variation name' ), - 'icon' => '', - ), - 'twitch' => array( - 'name' => _x( 'Twitch', 'social link block variation name' ), - 'icon' => '', - ), - 'twitter' => array( - 'name' => _x( 'Twitter', 'social link block variation name' ), - 'icon' => '', - ), - 'vimeo' => array( - 'name' => _x( 'Vimeo', 'social link block variation name' ), - 'icon' => '', - ), - 'vk' => array( - 'name' => _x( 'VK', 'social link block variation name' ), - 'icon' => '', - ), - 'wordpress' => array( - 'name' => _x( 'WordPress', 'social link block variation name' ), - 'icon' => '', - ), - 'whatsapp' => array( - 'name' => _x( 'WhatsApp', 'social link block variation name' ), - 'icon' => '', - ), - 'x' => array( - 'name' => _x( 'X', 'social link block variation name' ), - 'icon' => '', - ), - 'yelp' => array( - 'name' => _x( 'Yelp', 'social link block variation name' ), - 'icon' => '', - ), - 'youtube' => array( - 'name' => _x( 'YouTube', 'social link block variation name' ), - 'icon' => '', - ), - ); - - /** - * Filter the list of available social service. - * - * This can be used to change icons or add custom icons (additionally to variations in the editor). - * Icons should be directly renderable - therefore SVGs work best. - * - * @since 6.9.0 - * - * @param array $services_data The list of services. Each item is an array containing a 'name' and 'icon' key. - * @return array The list of social services. - */ - $services_data = apply_filters( 'block_core_social_link_get_services', $services_data ); - - if ( ! empty( $service ) - && ! empty( $field ) - && isset( $services_data[ $service ] ) - && ( 'icon' === $field || 'name' === $field ) - ) { - return $services_data[ $service ][ $field ]; - } elseif ( ! empty( $service ) && isset( $services_data[ $service ] ) ) { - return $services_data[ $service ]; - } - - return $services_data; -} - -/** - * Returns CSS styles for icon and icon background colors. - * - * @since 5.7.0 - * - * @param array $context Block context passed to Social Link. - * - * @return string Inline CSS styles for link's icon and background colors. - */ -function block_core_social_link_get_color_styles( $context ) { - $styles = array(); - - if ( array_key_exists( 'iconColorValue', $context ) ) { - $styles[] = 'color:' . $context['iconColorValue'] . ';'; - } - - if ( array_key_exists( 'iconBackgroundColorValue', $context ) ) { - $styles[] = 'background-color:' . $context['iconBackgroundColorValue'] . ';'; - } - - return implode( '', $styles ); -} - -/** - * Returns CSS classes for icon and icon background colors. - * - * @since 6.3.0 - * - * @param array $context Block context passed to Social Sharing Link. - * - * @return string CSS classes for link's icon and background colors. - */ -function block_core_social_link_get_color_classes( $context ) { - $classes = array(); - - if ( array_key_exists( 'iconColor', $context ) ) { - $classes[] = 'has-' . $context['iconColor'] . '-color'; - } - - if ( array_key_exists( 'iconBackgroundColor', $context ) ) { - $classes[] = 'has-' . $context['iconBackgroundColor'] . '-background-color'; - } - - return ' ' . implode( ' ', $classes ); -} diff --git a/src/wp-includes/blocks/social-link/block.json b/src/wp-includes/blocks/social-link/block.json deleted file mode 100644 index 667fd74b208f2..0000000000000 --- a/src/wp-includes/blocks/social-link/block.json +++ /dev/null @@ -1,42 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/social-link", - "title": "Social Icon", - "category": "widgets", - "parent": [ "core/social-links" ], - "description": "Display an icon linking to a social profile or site.", - "textdomain": "default", - "attributes": { - "url": { - "type": "string", - "role": "content" - }, - "service": { - "type": "string" - }, - "label": { - "type": "string", - "role": "content" - }, - "rel": { - "type": "string" - } - }, - "usesContext": [ - "openInNewTab", - "showLabels", - "iconColor", - "iconColorValue", - "iconBackgroundColor", - "iconBackgroundColorValue" - ], - "supports": { - "reusable": false, - "html": false, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-social-link-editor" -} diff --git a/src/wp-includes/blocks/social-links/block.json b/src/wp-includes/blocks/social-links/block.json deleted file mode 100644 index 8caa8f5bf8abb..0000000000000 --- a/src/wp-includes/blocks/social-links/block.json +++ /dev/null @@ -1,107 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/social-links", - "title": "Social Icons", - "category": "widgets", - "allowedBlocks": [ "core/social-link" ], - "description": "Display icons linking to your social profiles or sites.", - "keywords": [ "links" ], - "textdomain": "default", - "attributes": { - "iconColor": { - "type": "string" - }, - "customIconColor": { - "type": "string" - }, - "iconColorValue": { - "type": "string" - }, - "iconBackgroundColor": { - "type": "string" - }, - "customIconBackgroundColor": { - "type": "string" - }, - "iconBackgroundColorValue": { - "type": "string" - }, - "openInNewTab": { - "type": "boolean", - "default": false - }, - "showLabels": { - "type": "boolean", - "default": false - }, - "size": { - "type": "string" - } - }, - "providesContext": { - "openInNewTab": "openInNewTab", - "showLabels": "showLabels", - "iconColor": "iconColor", - "iconColorValue": "iconColorValue", - "iconBackgroundColor": "iconBackgroundColor", - "iconBackgroundColorValue": "iconBackgroundColorValue" - }, - "supports": { - "align": [ "left", "center", "right" ], - "anchor": true, - "html": false, - "__experimentalExposeControlsToChildren": true, - "layout": { - "allowSwitching": false, - "allowInheriting": false, - "allowVerticalAlignment": false, - "default": { - "type": "flex" - } - }, - "color": { - "enableContrastChecker": false, - "background": true, - "gradients": true, - "text": false, - "__experimentalDefaultControls": { - "background": false - } - }, - "spacing": { - "blockGap": [ "horizontal", "vertical" ], - "margin": true, - "padding": true, - "units": [ "px", "em", "rem", "vh", "vw" ], - "__experimentalDefaultControls": { - "blockGap": true, - "margin": true, - "padding": false - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - }, - "contentRole": true - }, - "styles": [ - { "name": "default", "label": "Default", "isDefault": true }, - { "name": "logos-only", "label": "Logos Only" }, - { "name": "pill-shape", "label": "Pill Shape" } - ], - "editorStyle": "wp-block-social-links-editor", - "style": "wp-block-social-links" -} diff --git a/src/wp-includes/blocks/spacer/block.json b/src/wp-includes/blocks/spacer/block.json deleted file mode 100644 index 447ea99cc0b67..0000000000000 --- a/src/wp-includes/blocks/spacer/block.json +++ /dev/null @@ -1,33 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/spacer", - "title": "Spacer", - "category": "design", - "description": "Add white space between blocks and customize its height.", - "textdomain": "default", - "attributes": { - "height": { - "type": "string", - "default": "100px" - }, - "width": { - "type": "string" - } - }, - "usesContext": [ "orientation" ], - "supports": { - "anchor": true, - "spacing": { - "margin": [ "top", "bottom" ], - "__experimentalDefaultControls": { - "margin": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-spacer-editor", - "style": "wp-block-spacer" -} diff --git a/src/wp-includes/blocks/table/block.json b/src/wp-includes/blocks/table/block.json deleted file mode 100644 index 84f2783d3ff8c..0000000000000 --- a/src/wp-includes/blocks/table/block.json +++ /dev/null @@ -1,220 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/table", - "title": "Table", - "category": "text", - "description": "Create structured content in rows and columns to display information.", - "textdomain": "default", - "attributes": { - "hasFixedLayout": { - "type": "boolean", - "default": true - }, - "caption": { - "type": "rich-text", - "source": "rich-text", - "selector": "figcaption", - "role": "content" - }, - "head": { - "type": "array", - "default": [], - "source": "query", - "selector": "thead tr", - "query": { - "cells": { - "type": "array", - "default": [], - "source": "query", - "selector": "td,th", - "query": { - "content": { - "type": "rich-text", - "source": "rich-text", - "role": "content" - }, - "tag": { - "type": "string", - "default": "td", - "source": "tag" - }, - "scope": { - "type": "string", - "source": "attribute", - "attribute": "scope" - }, - "align": { - "type": "string", - "source": "attribute", - "attribute": "data-align" - }, - "colspan": { - "type": "string", - "source": "attribute", - "attribute": "colspan" - }, - "rowspan": { - "type": "string", - "source": "attribute", - "attribute": "rowspan" - } - } - } - } - }, - "body": { - "type": "array", - "default": [], - "source": "query", - "selector": "tbody tr", - "query": { - "cells": { - "type": "array", - "default": [], - "source": "query", - "selector": "td,th", - "query": { - "content": { - "type": "rich-text", - "source": "rich-text", - "role": "content" - }, - "tag": { - "type": "string", - "default": "td", - "source": "tag" - }, - "scope": { - "type": "string", - "source": "attribute", - "attribute": "scope" - }, - "align": { - "type": "string", - "source": "attribute", - "attribute": "data-align" - }, - "colspan": { - "type": "string", - "source": "attribute", - "attribute": "colspan" - }, - "rowspan": { - "type": "string", - "source": "attribute", - "attribute": "rowspan" - } - } - } - } - }, - "foot": { - "type": "array", - "default": [], - "source": "query", - "selector": "tfoot tr", - "query": { - "cells": { - "type": "array", - "default": [], - "source": "query", - "selector": "td,th", - "query": { - "content": { - "type": "rich-text", - "source": "rich-text", - "role": "content" - }, - "tag": { - "type": "string", - "default": "td", - "source": "tag" - }, - "scope": { - "type": "string", - "source": "attribute", - "attribute": "scope" - }, - "align": { - "type": "string", - "source": "attribute", - "attribute": "data-align" - }, - "colspan": { - "type": "string", - "source": "attribute", - "attribute": "colspan" - }, - "rowspan": { - "type": "string", - "source": "attribute", - "attribute": "rowspan" - } - } - } - } - } - }, - "supports": { - "anchor": true, - "align": true, - "color": { - "__experimentalSkipSerialization": true, - "gradients": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontStyle": true, - "__experimentalFontWeight": true, - "__experimentalLetterSpacing": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "__experimentalBorder": { - "__experimentalSkipSerialization": true, - "color": true, - "style": true, - "width": true, - "__experimentalDefaultControls": { - "color": true, - "style": true, - "width": true - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "selectors": { - "root": ".wp-block-table > table", - "spacing": ".wp-block-table" - }, - "styles": [ - { - "name": "regular", - "label": "Default", - "isDefault": true - }, - { "name": "stripes", "label": "Stripes" } - ], - "editorStyle": "wp-block-table-editor", - "style": "wp-block-table" -} diff --git a/src/wp-includes/blocks/tag-cloud.php b/src/wp-includes/blocks/tag-cloud.php deleted file mode 100644 index 8949dd8e5b11f..0000000000000 --- a/src/wp-includes/blocks/tag-cloud.php +++ /dev/null @@ -1,63 +0,0 @@ -[a-z%]+)$/i', $smallest_font_size, $m ) ? $m['unit'] : 'pt' ); - - $args = array( - 'echo' => false, - 'unit' => $unit, - 'taxonomy' => $attributes['taxonomy'], - 'show_count' => $attributes['showTagCounts'], - 'number' => $attributes['numberOfTags'], - 'smallest' => floatVal( $attributes['smallestFontSize'] ), - 'largest' => floatVal( $attributes['largestFontSize'] ), - ); - $tag_cloud = wp_tag_cloud( $args ); - - if ( empty( $tag_cloud ) ) { - // Display placeholder content when there are no tags only in editor. - if ( wp_is_serving_rest_request() ) { - $tag_cloud = __( 'There’s no content to show here yet.' ); - } else { - return ''; - } - } - - $wrapper_attributes = get_block_wrapper_attributes(); - - return sprintf( - '

      %2$s

      ', - $wrapper_attributes, - $tag_cloud - ); -} - -/** - * Registers the `core/tag-cloud` block on server. - * - * @since 5.2.0 - */ -function register_block_core_tag_cloud() { - register_block_type_from_metadata( - __DIR__ . '/tag-cloud', - array( - 'render_callback' => 'render_block_core_tag_cloud', - ) - ); -} -add_action( 'init', 'register_block_core_tag_cloud' ); diff --git a/src/wp-includes/blocks/tag-cloud/block.json b/src/wp-includes/blocks/tag-cloud/block.json deleted file mode 100644 index 044bc0c533376..0000000000000 --- a/src/wp-includes/blocks/tag-cloud/block.json +++ /dev/null @@ -1,69 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/tag-cloud", - "title": "Tag Cloud", - "category": "widgets", - "description": "A cloud of popular keywords, each sized by how often it appears.", - "textdomain": "default", - "attributes": { - "numberOfTags": { - "type": "number", - "default": 45, - "minimum": 1, - "maximum": 100 - }, - "taxonomy": { - "type": "string", - "default": "post_tag" - }, - "showTagCounts": { - "type": "boolean", - "default": false - }, - "smallestFontSize": { - "type": "string", - "default": "8pt" - }, - "largestFontSize": { - "type": "string", - "default": "22pt" - } - }, - "styles": [ - { "name": "default", "label": "Default", "isDefault": true }, - { "name": "outline", "label": "Outline" } - ], - "supports": { - "html": false, - "align": true, - "spacing": { - "margin": true, - "padding": true - }, - "typography": { - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalLetterSpacing": true - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - }, - "editorStyle": "wp-block-tag-cloud-editor" -} diff --git a/src/wp-includes/blocks/template-part.php b/src/wp-includes/blocks/template-part.php deleted file mode 100644 index c73b64408733d..0000000000000 --- a/src/wp-includes/blocks/template-part.php +++ /dev/null @@ -1,303 +0,0 @@ - 'wp_template_part', - 'post_status' => 'publish', - 'post_name__in' => array( $attributes['slug'] ), - 'tax_query' => array( - array( - 'taxonomy' => 'wp_theme', - 'field' => 'name', - 'terms' => $theme, - ), - ), - 'posts_per_page' => 1, - 'no_found_rows' => true, - 'lazy_load_term_meta' => false, // Do not lazy load term meta, as template parts only have one term. - ) - ); - $template_part_post = $template_part_query->have_posts() ? $template_part_query->next_post() : null; - if ( $template_part_post ) { - // A published post might already exist if this template part was customized elsewhere - // or if it's part of a customized template. - $block_template = _build_block_template_result_from_post( $template_part_post ); - $content = $block_template->content; - if ( isset( $block_template->area ) ) { - $area = $block_template->area; - } - /** - * Fires when a block template part is loaded from a template post stored in the database. - * - * @since 5.9.0 - * - * @param string $template_part_id The requested template part namespaced to the theme. - * @param array $attributes The block attributes. - * @param WP_Post $template_part_post The template part post object. - * @param string $content The template part content. - */ - do_action( 'render_block_core_template_part_post', $template_part_id, $attributes, $template_part_post, $content ); - } else { - $template_part_file_path = ''; - // Else, if the template part was provided by the active theme, - // render the corresponding file content. - if ( 0 === validate_file( $attributes['slug'] ) ) { - $block_template = get_block_file_template( $template_part_id, 'wp_template_part' ); - - if ( isset( $block_template->content ) ) { - $content = $block_template->content; - } - if ( isset( $block_template->area ) ) { - $area = $block_template->area; - } - - // Needed for the `render_block_core_template_part_file` and `render_block_core_template_part_none` actions below. - $block_template_file = _get_block_template_file( 'wp_template_part', $attributes['slug'] ); - if ( $block_template_file ) { - $template_part_file_path = $block_template_file['path']; - } - } - - if ( '' !== $content && null !== $content ) { - /** - * Fires when a block template part is loaded from a template part in the theme. - * - * @since 5.9.0 - * - * @param string $template_part_id The requested template part namespaced to the theme. - * @param array $attributes The block attributes. - * @param string $template_part_file_path Absolute path to the template path. - * @param string $content The template part content. - */ - do_action( 'render_block_core_template_part_file', $template_part_id, $attributes, $template_part_file_path, $content ); - } else { - /** - * Fires when a requested block template part does not exist in the database nor in the theme. - * - * @since 5.9.0 - * - * @param string $template_part_id The requested template part namespaced to the theme. - * @param array $attributes The block attributes. - * @param string $template_part_file_path Absolute path to the not found template path. - */ - do_action( 'render_block_core_template_part_none', $template_part_id, $attributes, $template_part_file_path ); - } - } - } - - // WP_DEBUG_DISPLAY must only be honored when WP_DEBUG. This precedent - // is set in `wp_debug_mode()`. - $is_debug = WP_DEBUG && WP_DEBUG_DISPLAY; - - if ( is_null( $content ) ) { - if ( $is_debug && isset( $attributes['slug'] ) ) { - return sprintf( - /* translators: %s: Template part slug. */ - __( 'Template part has been deleted or is unavailable: %s' ), - $attributes['slug'] - ); - } - - return ''; - } - - if ( isset( $seen_ids[ $template_part_id ] ) ) { - return $is_debug ? - // translators: Visible only in the front end, this warning takes the place of a faulty block. - __( '[block rendering halted]' ) : - ''; - } - - // Look up area definition. - $area_definition = null; - $defined_areas = get_allowed_block_template_part_areas(); - foreach ( $defined_areas as $defined_area ) { - if ( $defined_area['area'] === $area ) { - $area_definition = $defined_area; - break; - } - } - - // If $area is not allowed, set it back to the uncategorized default. - if ( ! $area_definition ) { - $area = WP_TEMPLATE_PART_AREA_UNCATEGORIZED; - } - - // Run through the actions that are typically taken on the_content. - $content = shortcode_unautop( $content ); - $content = do_shortcode( $content ); - $seen_ids[ $template_part_id ] = true; - $content = do_blocks( $content ); - unset( $seen_ids[ $template_part_id ] ); - $content = wptexturize( $content ); - $content = convert_smilies( $content ); - $content = wp_filter_content_tags( $content, "template_part_{$area}" ); - - // Handle embeds for block template parts. - global $wp_embed; - $content = $wp_embed->autoembed( $content ); - - if ( empty( $attributes['tagName'] ) || tag_escape( $attributes['tagName'] ) !== $attributes['tagName'] ) { - $area_tag = 'div'; - if ( $area_definition && isset( $area_definition['area_tag'] ) ) { - $area_tag = $area_definition['area_tag']; - } - $html_tag = $area_tag; - } else { - $html_tag = esc_attr( $attributes['tagName'] ); - } - $wrapper_attributes = get_block_wrapper_attributes(); - - return "<$html_tag $wrapper_attributes>" . str_replace( ']]>', ']]>', $content ) . ""; -} - -/** - * Returns an array of area variation objects for the template part block. - * - * @since 6.1.0 - * - * @param array $instance_variations The variations for instances. - * - * @return array Array containing the block variation objects. - */ -function build_template_part_block_area_variations( $instance_variations ) { - $variations = array(); - $defined_areas = get_allowed_block_template_part_areas(); - - foreach ( $defined_areas as $area ) { - if ( 'uncategorized' !== $area['area'] ) { - $has_instance_for_area = false; - foreach ( $instance_variations as $variation ) { - if ( $variation['attributes']['area'] === $area['area'] ) { - $has_instance_for_area = true; - break; - } - } - - $scope = $has_instance_for_area ? array() : array( 'inserter' ); - - $variations[] = array( - 'name' => 'area_' . $area['area'], - 'title' => $area['label'], - 'description' => $area['description'], - 'attributes' => array( - 'area' => $area['area'], - ), - 'scope' => $scope, - 'icon' => $area['icon'], - ); - } - } - return $variations; -} - -/** - * Returns an array of instance variation objects for the template part block - * - * @since 6.1.0 - * - * @return array Array containing the block variation objects. - */ -function build_template_part_block_instance_variations() { - // Block themes are unavailable during installation. - if ( wp_installing() ) { - return array(); - } - - if ( ! current_theme_supports( 'block-templates' ) && ! current_theme_supports( 'block-template-parts' ) ) { - return array(); - } - - $variations = array(); - $template_parts = get_block_templates( - array( - 'post_type' => 'wp_template_part', - ), - 'wp_template_part' - ); - - $defined_areas = get_allowed_block_template_part_areas(); - $icon_by_area = array_combine( array_column( $defined_areas, 'area' ), array_column( $defined_areas, 'icon' ) ); - - foreach ( $template_parts as $template_part ) { - $variations[] = array( - 'name' => 'instance_' . sanitize_title( $template_part->slug ), - 'title' => $template_part->title, - // If there's no description for the template part don't show the - // block description. This is a bit hacky, but prevent the fallback - // by using a non-breaking space so that the value of description - // isn't falsey. - 'description' => $template_part->description || ' ', - 'attributes' => array( - 'slug' => $template_part->slug, - 'theme' => $template_part->theme, - 'area' => $template_part->area, - ), - 'scope' => array( 'inserter' ), - 'icon' => isset( $icon_by_area[ $template_part->area ] ) ? $icon_by_area[ $template_part->area ] : null, - 'example' => array( - 'attributes' => array( - 'slug' => $template_part->slug, - 'theme' => $template_part->theme, - 'area' => $template_part->area, - ), - ), - ); - } - return $variations; -} - -/** - * Returns an array of all template part block variations. - * - * @since 5.9.0 - * - * @return array Array containing the block variation objects. - */ -function build_template_part_block_variations() { - $instance_variations = build_template_part_block_instance_variations(); - $area_variations = build_template_part_block_area_variations( $instance_variations ); - return array_merge( $area_variations, $instance_variations ); -} - -/** - * Registers the `core/template-part` block on the server. - * - * @since 5.9.0 - */ -function register_block_core_template_part() { - register_block_type_from_metadata( - __DIR__ . '/template-part', - array( - 'render_callback' => 'render_block_core_template_part', - 'variation_callback' => 'build_template_part_block_variations', - ) - ); -} -add_action( 'init', 'register_block_core_template_part' ); diff --git a/src/wp-includes/blocks/template-part/block.json b/src/wp-includes/blocks/template-part/block.json deleted file mode 100644 index 9710bdeee2e53..0000000000000 --- a/src/wp-includes/blocks/template-part/block.json +++ /dev/null @@ -1,33 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/template-part", - "title": "Template Part", - "category": "theme", - "description": "Edit the different global regions of your site, like the header, footer, sidebar, or create your own.", - "textdomain": "default", - "attributes": { - "slug": { - "type": "string" - }, - "theme": { - "type": "string" - }, - "tagName": { - "type": "string" - }, - "area": { - "type": "string" - } - }, - "supports": { - "align": true, - "html": false, - "reusable": false, - "renaming": false, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-template-part-editor" -} diff --git a/src/wp-includes/blocks/term-count.php b/src/wp-includes/blocks/term-count.php deleted file mode 100644 index 9794896524eb4..0000000000000 --- a/src/wp-includes/blocks/term-count.php +++ /dev/null @@ -1,80 +0,0 @@ -context['termId'] ) && isset( $block->context['taxonomy'] ) ) { - $term = get_term( $block->context['termId'], $block->context['taxonomy'] ); - } else { - $term = get_queried_object(); - if ( ! $term instanceof WP_Term ) { - $term = null; - } - } - - if ( ! $term || is_wp_error( $term ) ) { - return ''; - } - - $term_count = $term->count; - - // Format the term count based on bracket type. - switch ( $attributes['bracketType'] ) { - case 'none': - // No formatting needed. - break; - case 'round': - $term_count = "({$term_count})"; - break; - case 'square': - $term_count = "[{$term_count}]"; - break; - case 'curly': - $term_count = "{{$term_count}}"; - break; - case 'angle': - $term_count = "<{$term_count}>"; - break; - default: - // Default to no formatting for unknown types. - break; - } - - $wrapper_attributes = get_block_wrapper_attributes(); - - return sprintf( - '
      %2$s
      ', - $wrapper_attributes, - $term_count - ); -} - -/** - * Registers the `core/term-count` block on the server. - * - * @since 6.9.0 - */ -function register_block_core_term_count() { - register_block_type_from_metadata( - __DIR__ . '/term-count', - array( - 'render_callback' => 'render_block_core_term_count', - ) - ); -} -add_action( 'init', 'register_block_core_term_count' ); diff --git a/src/wp-includes/blocks/term-count/block.json b/src/wp-includes/blocks/term-count/block.json deleted file mode 100644 index c4de1e61f8d1f..0000000000000 --- a/src/wp-includes/blocks/term-count/block.json +++ /dev/null @@ -1,58 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/term-count", - "title": "Term Count", - "category": "theme", - "description": "Displays the post count of a taxonomy term.", - "textdomain": "default", - "usesContext": [ "termId", "taxonomy" ], - "attributes": { - "bracketType": { - "type": "string", - "enum": [ "none", "round", "square", "curly", "angle" ], - "default": "round" - } - }, - "supports": { - "html": false, - "color": { - "gradients": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "spacing": { - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "color": true, - "width": true, - "style": true - } - } - }, - "style": "wp-block-term-count" -} diff --git a/src/wp-includes/blocks/term-description.php b/src/wp-includes/blocks/term-description.php deleted file mode 100644 index 9f61dbba07fbc..0000000000000 --- a/src/wp-includes/blocks/term-description.php +++ /dev/null @@ -1,61 +0,0 @@ -context['termId'] ) && isset( $block->context['taxonomy'] ) ) { - $term = get_term( $block->context['termId'], $block->context['taxonomy'] ); - if ( $term && ! is_wp_error( $term ) ) { - $term_description = $term->description; - } - } elseif ( is_category() || is_tag() || is_tax() ) { - $term_description = term_description(); - } - - if ( empty( $term_description ) ) { - return ''; - } - - $classes = array(); - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - - return '
      ' . $term_description . '
      '; -} - -/** - * Registers the `core/term-description` block on the server. - * - * @since 5.9.0 - */ -function register_block_core_term_description() { - register_block_type_from_metadata( - __DIR__ . '/term-description', - array( - 'render_callback' => 'render_block_core_term_description', - ) - ); -} -add_action( 'init', 'register_block_core_term_description' ); diff --git a/src/wp-includes/blocks/term-description/block.json b/src/wp-includes/blocks/term-description/block.json deleted file mode 100644 index a882625ad6f50..0000000000000 --- a/src/wp-includes/blocks/term-description/block.json +++ /dev/null @@ -1,58 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/term-description", - "title": "Term Description", - "category": "theme", - "description": "Display the description of categories, tags and custom taxonomies when viewing an archive.", - "textdomain": "default", - "usesContext": [ "termId", "taxonomy" ], - "attributes": { - "textAlign": { - "type": "string" - } - }, - "supports": { - "align": [ "wide", "full" ], - "html": false, - "color": { - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "spacing": { - "padding": true, - "margin": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "radius": true, - "color": true, - "width": true, - "style": true - } - } - } -} diff --git a/src/wp-includes/blocks/term-name.php b/src/wp-includes/blocks/term-name.php deleted file mode 100644 index 3a2bf18bb5f21..0000000000000 --- a/src/wp-includes/blocks/term-name.php +++ /dev/null @@ -1,81 +0,0 @@ -context['termId'] ) && isset( $block->context['taxonomy'] ) ) { - $term = get_term( $block->context['termId'], $block->context['taxonomy'] ); - } else { - $term = get_queried_object(); - if ( ! $term instanceof WP_Term ) { - $term = null; - } - } - - if ( ! $term || is_wp_error( $term ) ) { - return ''; - } - - $term_name = $term->name; - $level = isset( $attributes['level'] ) ? $attributes['level'] : 0; - $tag_name = 0 === $level ? 'p' : 'h' . (int) $level; - - if ( isset( $attributes['isLink'] ) && $attributes['isLink'] ) { - $term_link = get_term_link( $term ); - if ( ! is_wp_error( $term_link ) ) { - $term_name = sprintf( - '%2$s', - esc_url( $term_link ), - $term_name - ); - } - } - - $classes = array(); - if ( isset( $attributes['textAlign'] ) ) { - $classes[] = 'has-text-align-' . $attributes['textAlign']; - } - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classes[] = 'has-link-color'; - } - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => implode( ' ', $classes ) ) ); - - return sprintf( - '<%1$s %2$s>%3$s', - $tag_name, - $wrapper_attributes, - $term_name - ); -} - -/** - * Registers the `core/term-name` block on the server. - * - * @since 6.9.0 - */ -function register_block_core_term_name() { - register_block_type_from_metadata( - __DIR__ . '/term-name', - array( - 'render_callback' => 'render_block_core_term_name', - ) - ); -} -add_action( 'init', 'register_block_core_term_name' ); diff --git a/src/wp-includes/blocks/term-name/block.json b/src/wp-includes/blocks/term-name/block.json deleted file mode 100644 index 29b0cbe22b77e..0000000000000 --- a/src/wp-includes/blocks/term-name/block.json +++ /dev/null @@ -1,68 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/term-name", - "title": "Term Name", - "category": "theme", - "description": "Displays the name of a taxonomy term.", - "keywords": [ "term title" ], - "textdomain": "default", - "usesContext": [ "termId", "taxonomy" ], - "attributes": { - "textAlign": { - "type": "string" - }, - "level": { - "type": "number", - "default": 0 - }, - "isLink": { - "type": "boolean", - "default": false - } - }, - "supports": { - "align": [ "wide", "full" ], - "html": false, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true, - "link": true - } - }, - "spacing": { - "padding": true - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true, - "__experimentalDefaultControls": { - "color": true, - "width": true, - "style": true - } - } - }, - "style": "wp-block-term-name" -} diff --git a/src/wp-includes/blocks/term-template.php b/src/wp-includes/blocks/term-template.php deleted file mode 100644 index 3cbe21f60c0d4..0000000000000 --- a/src/wp-includes/blocks/term-template.php +++ /dev/null @@ -1,137 +0,0 @@ -context ) || empty( $block->context['termQuery'] ) ) { - return ''; - } - - $query = $block->context['termQuery']; - - $query_args = array( - 'number' => $query['perPage'], - 'order' => $query['order'], - 'orderby' => $query['orderBy'], - 'hide_empty' => $query['hideEmpty'], - ); - - $inherit_query = isset( $query['inherit'] ) - && $query['inherit'] - && ( is_tax() || is_category() || is_tag() ); - - if ( $inherit_query ) { - // Get the current term and taxonomy from the queried object. - $queried_object = get_queried_object(); - - // For hierarchical taxonomies, show children of the current term. - // For non-hierarchical taxonomies, show all terms (don't set parent). - if ( is_taxonomy_hierarchical( $queried_object->taxonomy ) ) { - // If showNested is true, use child_of to include nested terms. - // Otherwise, use parent to show only direct children. - if ( ! empty( $query['showNested'] ) ) { - $query_args['child_of'] = $queried_object->term_id; - } else { - $query_args['parent'] = $queried_object->term_id; - } - } - $query_args['taxonomy'] = $queried_object->taxonomy; - } else { - // If not inheriting set `taxonomy` from the block attribute. - $query_args['taxonomy'] = $query['taxonomy']; - - // If we are including specific terms we ignore `showNested` argument. - if ( ! empty( $query['include'] ) ) { - $query_args['include'] = array_unique( array_map( 'intval', $query['include'] ) ); - $query_args['orderby'] = 'include'; - $query_args['order'] = 'asc'; - } elseif ( empty( $query['showNested'] ) ) { - // We set parent only when inheriting from the taxonomy archive context or not - // showing nested terms, otherwise nested terms are not displayed. - $query_args['parent'] = 0; - } - } - - $terms_query = new WP_Term_Query( $query_args ); - $terms = $terms_query->get_terms(); - - if ( ! $terms || is_wp_error( $terms ) ) { - return ''; - } - - $content = ''; - foreach ( $terms as $term ) { - // Get an instance of the current Term Template block. - $block_instance = $block->parsed_block; - - // Set the block name to one that does not correspond to an existing registered block. - // This ensures that for the inner instances of the Term Template block, we do not render any block supports. - $block_instance['blockName'] = 'core/null'; - - $term_id = $term->term_id; - $taxonomy = $term->taxonomy; - - $filter_block_context = static function ( $context ) use ( $term_id, $taxonomy ) { - $context['termId'] = $term_id; - $context['taxonomy'] = $taxonomy; - return $context; - }; - - // Use an early priority to so that other 'render_block_context' filters have access to the values. - add_filter( 'render_block_context', $filter_block_context, 1 ); - - // Render the inner blocks of the Term Template block with `dynamic` set to `false` to prevent calling - // `render_callback` and ensure that no wrapper markup is included. - $block_content = ( new WP_Block( $block_instance ) )->render( array( 'dynamic' => false ) ); - - remove_filter( 'render_block_context', $filter_block_context, 1 ); - - // Wrap the render inner blocks in a `li` element with the appropriate term classes. - $term_classes = "wp-block-term term-{$term->term_id} {$term->taxonomy} taxonomy-{$term->taxonomy}"; - - $content .= '
    10. ' . $block_content . '
    11. '; - } - - $classnames = ''; - - if ( isset( $attributes['style']['elements']['link']['color']['text'] ) ) { - $classnames .= 'has-link-color'; - } - - $wrapper_attributes = get_block_wrapper_attributes( array( 'class' => trim( $classnames ) ) ); - - return sprintf( - '
        %s
      ', - $wrapper_attributes, - $content - ); -} - -/** - * Registers the `core/term-template` block on the server. - * - * @since 6.9.0 - */ -function register_block_core_term_template() { - register_block_type_from_metadata( - __DIR__ . '/term-template', - array( - 'render_callback' => 'render_block_core_term_template', - ) - ); -} -add_action( 'init', 'register_block_core_term_template' ); diff --git a/src/wp-includes/blocks/term-template/block.json b/src/wp-includes/blocks/term-template/block.json deleted file mode 100644 index 2f4b9838c71bd..0000000000000 --- a/src/wp-includes/blocks/term-template/block.json +++ /dev/null @@ -1,61 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/term-template", - "title": "Term Template", - "category": "theme", - "ancestor": [ "core/terms-query" ], - "description": "Contains the block elements used to render a taxonomy term, like the name, description, and more.", - "textdomain": "default", - "usesContext": [ "termQuery" ], - "supports": { - "reusable": false, - "html": false, - "align": [ "wide", "full" ], - "layout": true, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "typography": { - "fontSize": true, - "lineHeight": true, - "__experimentalFontFamily": true, - "__experimentalFontWeight": true, - "__experimentalFontStyle": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalLetterSpacing": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "spacing": { - "margin": true, - "padding": true, - "blockGap": { - "__experimentalDefault": "1.25em" - }, - "__experimentalDefaultControls": { - "blockGap": true, - "padding": false, - "margin": false - } - }, - "interactivity": { - "clientNavigation": true - }, - "__experimentalBorder": { - "radius": true, - "color": true, - "width": true, - "style": true - } - }, - "style": "wp-block-term-template", - "editorStyle": "wp-block-term-template-editor" -} diff --git a/src/wp-includes/blocks/terms-query/block.json b/src/wp-includes/blocks/terms-query/block.json deleted file mode 100644 index 05b7a2c12e22f..0000000000000 --- a/src/wp-includes/blocks/terms-query/block.json +++ /dev/null @@ -1,39 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/terms-query", - "title": "Terms Query", - "category": "theme", - "description": "An advanced block that allows displaying taxonomy terms based on different query parameters and visual configurations.", - "keywords": [ "terms", "taxonomy", "categories", "tags", "list" ], - "textdomain": "default", - "attributes": { - "termQuery": { - "type": "object", - "default": { - "perPage": 10, - "taxonomy": "category", - "order": "asc", - "orderBy": "name", - "include": [], - "hideEmpty": true, - "showNested": false, - "inherit": false - } - }, - "tagName": { - "type": "string", - "default": "div" - } - }, - "usesContext": [ "templateSlug" ], - "providesContext": { - "termQuery": "termQuery" - }, - "supports": { - "align": [ "wide", "full" ], - "html": false, - "layout": true, - "interactivity": true - } -} diff --git a/src/wp-includes/blocks/text-columns/block.json b/src/wp-includes/blocks/text-columns/block.json deleted file mode 100644 index 2599df111d34b..0000000000000 --- a/src/wp-includes/blocks/text-columns/block.json +++ /dev/null @@ -1,39 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/text-columns", - "title": "Text Columns (deprecated)", - "icon": "columns", - "category": "design", - "description": "This block is deprecated. Please use the Columns block instead.", - "textdomain": "default", - "attributes": { - "content": { - "type": "array", - "source": "query", - "selector": "p", - "query": { - "children": { - "type": "string", - "source": "html" - } - }, - "default": [ {}, {} ] - }, - "columns": { - "type": "number", - "default": 2 - }, - "width": { - "type": "string" - } - }, - "supports": { - "inserter": false, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-text-columns-editor", - "style": "wp-block-text-columns" -} diff --git a/src/wp-includes/blocks/verse/block.json b/src/wp-includes/blocks/verse/block.json deleted file mode 100644 index 81cccd72965b1..0000000000000 --- a/src/wp-includes/blocks/verse/block.json +++ /dev/null @@ -1,79 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/verse", - "title": "Verse", - "category": "text", - "description": "Insert poetry. Use special spacing formats. Or quote song lyrics.", - "keywords": [ "poetry", "poem" ], - "textdomain": "default", - "attributes": { - "content": { - "type": "rich-text", - "source": "rich-text", - "selector": "pre", - "__unstablePreserveWhiteSpace": true, - "role": "content" - }, - "textAlign": { - "type": "string" - } - }, - "supports": { - "anchor": true, - "background": { - "backgroundImage": true, - "backgroundSize": true, - "__experimentalDefaultControls": { - "backgroundImage": true - } - }, - "color": { - "gradients": true, - "link": true, - "__experimentalDefaultControls": { - "background": true, - "text": true - } - }, - "dimensions": { - "minHeight": true, - "__experimentalDefaultControls": { - "minHeight": false - } - }, - "typography": { - "fontSize": true, - "__experimentalFontFamily": true, - "lineHeight": true, - "__experimentalFontStyle": true, - "__experimentalFontWeight": true, - "__experimentalLetterSpacing": true, - "__experimentalTextTransform": true, - "__experimentalTextDecoration": true, - "__experimentalWritingMode": true, - "__experimentalDefaultControls": { - "fontSize": true - } - }, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "__experimentalBorder": { - "radius": true, - "width": true, - "color": true, - "style": true - }, - "interactivity": { - "clientNavigation": true - } - }, - "style": "wp-block-verse", - "editorStyle": "wp-block-verse-editor" -} diff --git a/src/wp-includes/blocks/video.php b/src/wp-includes/blocks/video.php deleted file mode 100644 index 3696bdca3b2e8..0000000000000 --- a/src/wp-includes/blocks/video.php +++ /dev/null @@ -1,91 +0,0 @@ - 0 && $metadata['height'] > 0 ) - ) { - return $content; - } - - // Locate the VIDEO tag to add the dimensions. - $p = new WP_HTML_Tag_Processor( $content ); - if ( ! $p->next_tag( array( 'tag_name' => 'VIDEO' ) ) ) { - return $content; - } - - $p->set_attribute( 'width', (string) $metadata['width'] ); - $p->set_attribute( 'height', (string) $metadata['height'] ); - - /* - * The aspect-ratio style is needed due to an issue with the CSS spec: . - * Note that a style rule using attr() like the following cannot currently be used: - * - * .wp-block-video video[width][height] { - * aspect-ratio: attr(width type()) / attr(height type()); - * } - * - * This is because this attr() is yet only implemented in Chromium: . - */ - $style = $p->get_attribute( 'style' ); - if ( ! is_string( $style ) ) { - $style = ''; - } - $aspect_ratio_style = sprintf( 'aspect-ratio: %d / %d;', $metadata['width'], $metadata['height'] ); - $p->set_attribute( 'style', $aspect_ratio_style . $style ); - - return $p->get_updated_html(); -} - -/** - * Registers the `core/video` block on server. - * - * @since 6.9.0 - */ -function register_block_core_video(): void { - register_block_type_from_metadata( - __DIR__ . '/video', - array( - 'render_callback' => 'render_block_core_video', - ) - ); -} -add_action( 'init', 'register_block_core_video' ); diff --git a/src/wp-includes/blocks/video/block.json b/src/wp-includes/blocks/video/block.json deleted file mode 100644 index d2dcd95365c3b..0000000000000 --- a/src/wp-includes/blocks/video/block.json +++ /dev/null @@ -1,102 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/video", - "title": "Video", - "category": "media", - "description": "Embed a video from your media library or upload a new one.", - "keywords": [ "movie" ], - "textdomain": "default", - "attributes": { - "autoplay": { - "type": "boolean", - "source": "attribute", - "selector": "video", - "attribute": "autoplay" - }, - "caption": { - "type": "rich-text", - "source": "rich-text", - "selector": "figcaption", - "role": "content" - }, - "controls": { - "type": "boolean", - "source": "attribute", - "selector": "video", - "attribute": "controls", - "default": true - }, - "id": { - "type": "number", - "role": "content" - }, - "loop": { - "type": "boolean", - "source": "attribute", - "selector": "video", - "attribute": "loop" - }, - "muted": { - "type": "boolean", - "source": "attribute", - "selector": "video", - "attribute": "muted" - }, - "poster": { - "type": "string", - "source": "attribute", - "selector": "video", - "attribute": "poster" - }, - "preload": { - "type": "string", - "source": "attribute", - "selector": "video", - "attribute": "preload", - "default": "metadata" - }, - "blob": { - "type": "string", - "role": "local" - }, - "src": { - "type": "string", - "source": "attribute", - "selector": "video", - "attribute": "src", - "role": "content" - }, - "playsInline": { - "type": "boolean", - "source": "attribute", - "selector": "video", - "attribute": "playsinline" - }, - "tracks": { - "role": "content", - "type": "array", - "items": { - "type": "object" - }, - "default": [] - } - }, - "supports": { - "anchor": true, - "align": true, - "spacing": { - "margin": true, - "padding": true, - "__experimentalDefaultControls": { - "margin": false, - "padding": false - } - }, - "interactivity": { - "clientNavigation": true - } - }, - "editorStyle": "wp-block-video-editor", - "style": "wp-block-video" -} diff --git a/src/wp-includes/blocks/widget-group.php b/src/wp-includes/blocks/widget-group.php deleted file mode 100644 index e8769612a2f17..0000000000000 --- a/src/wp-includes/blocks/widget-group.php +++ /dev/null @@ -1,93 +0,0 @@ -'; - $after_title = ''; - } - - $html = ''; - - if ( ! empty( $attributes['title'] ) ) { - $html .= $before_title . esc_html( $attributes['title'] ) . $after_title; - } - - $html .= '
      '; - foreach ( $block->inner_blocks as $inner_block ) { - $html .= $inner_block->render(); - } - $html .= '
      '; - - return $html; -} - -/** - * Registers the 'core/widget-group' block. - * - * @since 5.9.0 - */ -function register_block_core_widget_group() { - register_block_type_from_metadata( - __DIR__ . '/widget-group', - array( - 'render_callback' => 'render_block_core_widget_group', - ) - ); -} - -add_action( 'init', 'register_block_core_widget_group' ); - -/** - * Make a note of the sidebar being rendered before WordPress starts rendering - * it. This lets us get to the current sidebar in - * render_block_core_widget_group(). - * - * @since 5.9.0 - * - * @global int|string $_sidebar_being_rendered - * - * @param int|string $index Index, name, or ID of the dynamic sidebar. - */ -function note_sidebar_being_rendered( $index ) { - global $_sidebar_being_rendered; - $_sidebar_being_rendered = $index; -} -add_action( 'dynamic_sidebar_before', 'note_sidebar_being_rendered' ); - -/** - * Clear whatever we set in note_sidebar_being_rendered() after WordPress - * finishes rendering a sidebar. - * - * @since 5.9.0 - * - * @global int|string $_sidebar_being_rendered - */ -function discard_sidebar_being_rendered() { - global $_sidebar_being_rendered; - unset( $_sidebar_being_rendered ); -} -add_action( 'dynamic_sidebar_after', 'discard_sidebar_being_rendered' ); diff --git a/src/wp-includes/blocks/widget-group/block.json b/src/wp-includes/blocks/widget-group/block.json deleted file mode 100644 index 6e7ba57b38dbc..0000000000000 --- a/src/wp-includes/blocks/widget-group/block.json +++ /dev/null @@ -1,20 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/block.json", - "apiVersion": 3, - "name": "core/widget-group", - "title": "Widget Group", - "category": "widgets", - "attributes": { - "title": { - "type": "string" - } - }, - "supports": { - "html": false, - "inserter": true, - "customClassName": true, - "reusable": false - }, - "editorStyle": "wp-block-widget-group-editor", - "style": "wp-block-widget-group" -} diff --git a/src/wp-includes/class-wp-block-parser-block.php b/src/wp-includes/class-wp-block-parser-block.php deleted file mode 100644 index 97dd687c1ffe1..0000000000000 --- a/src/wp-includes/class-wp-block-parser-block.php +++ /dev/null @@ -1,90 +0,0 @@ - 3 ) - * - * @since 5.0.0 - * @var array|null - */ - public $attrs; - - /** - * List of inner blocks (of this same class) - * - * @since 5.0.0 - * @var WP_Block_Parser_Block[] - */ - public $innerBlocks; // phpcs:ignore WordPress.NamingConventions.ValidVariableName - - /** - * Resultant HTML from inside block comment delimiters - * after removing inner blocks - * - * @example "...Just testing..." -> "Just testing..." - * - * @since 5.0.0 - * @var string - */ - public $innerHTML; // phpcs:ignore WordPress.NamingConventions.ValidVariableName - - /** - * List of string fragments and null markers where inner blocks were found - * - * @example array( - * 'innerHTML' => 'BeforeInnerAfter', - * 'innerBlocks' => array( block, block ), - * 'innerContent' => array( 'Before', null, 'Inner', null, 'After' ), - * ) - * - * @since 5.0.0 - * @var array - */ - public $innerContent; // phpcs:ignore WordPress.NamingConventions.ValidVariableName - - /** - * Constructor. - * - * Will populate object properties from the provided arguments. - * - * @since 5.0.0 - * - * @param string $name Name of block. - * @param array $attrs Optional set of attributes from block comment delimiters. - * @param array $inner_blocks List of inner blocks (of this same class). - * @param string $inner_html Resultant HTML from inside block comment delimiters after removing inner blocks. - * @param array $inner_content List of string fragments and null markers where inner blocks were found. - */ - public function __construct( $name, $attrs, $inner_blocks, $inner_html, $inner_content ) { - $this->blockName = $name; // phpcs:ignore WordPress.NamingConventions.ValidVariableName - $this->attrs = $attrs; - $this->innerBlocks = $inner_blocks; // phpcs:ignore WordPress.NamingConventions.ValidVariableName - $this->innerHTML = $inner_html; // phpcs:ignore WordPress.NamingConventions.ValidVariableName - $this->innerContent = $inner_content; // phpcs:ignore WordPress.NamingConventions.ValidVariableName - } -} diff --git a/src/wp-includes/class-wp-block-parser-frame.php b/src/wp-includes/class-wp-block-parser-frame.php deleted file mode 100644 index 6ab5dd3087dfb..0000000000000 --- a/src/wp-includes/class-wp-block-parser-frame.php +++ /dev/null @@ -1,79 +0,0 @@ -block = $block; - $this->token_start = $token_start; - $this->token_length = $token_length; - $this->prev_offset = isset( $prev_offset ) ? $prev_offset : $token_start + $token_length; - $this->leading_html_start = $leading_html_start; - } -} diff --git a/src/wp-includes/class-wp-block-parser.php b/src/wp-includes/class-wp-block-parser.php deleted file mode 100644 index bf8a59249d99d..0000000000000 --- a/src/wp-includes/class-wp-block-parser.php +++ /dev/null @@ -1,404 +0,0 @@ -This is inside a block!" - * - * @since 5.0.0 - * @var string - */ - public $document; - - /** - * Tracks parsing progress through document - * - * @since 5.0.0 - * @var int - */ - public $offset; - - /** - * List of parsed blocks - * - * @since 5.0.0 - * @var array[] - */ - public $output; - - /** - * Stack of partially-parsed structures in memory during parse - * - * @since 5.0.0 - * @var WP_Block_Parser_Frame[] - */ - public $stack; - - /** - * Parses a document and returns a list of block structures - * - * When encountering an invalid parse will return a best-effort - * parse. In contrast to the specification parser this does not - * return an error on invalid inputs. - * - * @since 5.0.0 - * - * @param string $document Input document being parsed. - * @return array[] - */ - public function parse( $document ) { - $this->document = $document; - $this->offset = 0; - $this->output = array(); - $this->stack = array(); - - while ( $this->proceed() ) { - continue; - } - - return $this->output; - } - - /** - * Processes the next token from the input document - * and returns whether to proceed eating more tokens - * - * This is the "next step" function that essentially - * takes a token as its input and decides what to do - * with that token before descending deeper into a - * nested block tree or continuing along the document - * or breaking out of a level of nesting. - * - * @internal - * @since 5.0.0 - * @return bool - */ - public function proceed() { - $next_token = $this->next_token(); - list( $token_type, $block_name, $attrs, $start_offset, $token_length ) = $next_token; - $stack_depth = count( $this->stack ); - - // we may have some HTML soup before the next block. - $leading_html_start = $start_offset > $this->offset ? $this->offset : null; - - switch ( $token_type ) { - case 'no-more-tokens': - // if not in a block then flush output. - if ( 0 === $stack_depth ) { - $this->add_freeform(); - return false; - } - - /* - * Otherwise we have a problem - * This is an error - * - * we have options - * - treat it all as freeform text - * - assume an implicit closer (easiest when not nesting) - */ - - // for the easy case we'll assume an implicit closer. - if ( 1 === $stack_depth ) { - $this->add_block_from_stack(); - return false; - } - - /* - * for the nested case where it's more difficult we'll - * have to assume that multiple closers are missing - * and so we'll collapse the whole stack piecewise - */ - while ( 0 < count( $this->stack ) ) { - $this->add_block_from_stack(); - } - return false; - - case 'void-block': - /* - * easy case is if we stumbled upon a void block - * in the top-level of the document - */ - if ( 0 === $stack_depth ) { - if ( isset( $leading_html_start ) ) { - $this->output[] = (array) $this->freeform( - substr( - $this->document, - $leading_html_start, - $start_offset - $leading_html_start - ) - ); - } - - $this->output[] = (array) new WP_Block_Parser_Block( $block_name, $attrs, array(), '', array() ); - $this->offset = $start_offset + $token_length; - return true; - } - - // otherwise we found an inner block. - $this->add_inner_block( - new WP_Block_Parser_Block( $block_name, $attrs, array(), '', array() ), - $start_offset, - $token_length - ); - $this->offset = $start_offset + $token_length; - return true; - - case 'block-opener': - // track all newly-opened blocks on the stack. - array_push( - $this->stack, - new WP_Block_Parser_Frame( - new WP_Block_Parser_Block( $block_name, $attrs, array(), '', array() ), - $start_offset, - $token_length, - $start_offset + $token_length, - $leading_html_start - ) - ); - $this->offset = $start_offset + $token_length; - return true; - - case 'block-closer': - /* - * if we're missing an opener we're in trouble - * This is an error - */ - if ( 0 === $stack_depth ) { - /* - * we have options - * - assume an implicit opener - * - assume _this_ is the opener - * - give up and close out the document - */ - $this->add_freeform(); - return false; - } - - // if we're not nesting then this is easy - close the block. - if ( 1 === $stack_depth ) { - $this->add_block_from_stack( $start_offset ); - $this->offset = $start_offset + $token_length; - return true; - } - - /* - * otherwise we're nested and we have to close out the current - * block and add it as a new innerBlock to the parent - */ - $stack_top = array_pop( $this->stack ); - $html = substr( $this->document, $stack_top->prev_offset, $start_offset - $stack_top->prev_offset ); - $stack_top->block->innerHTML .= $html; - $stack_top->block->innerContent[] = $html; - $stack_top->prev_offset = $start_offset + $token_length; - - $this->add_inner_block( - $stack_top->block, - $stack_top->token_start, - $stack_top->token_length, - $start_offset + $token_length - ); - $this->offset = $start_offset + $token_length; - return true; - - default: - // This is an error. - $this->add_freeform(); - return false; - } - } - - /** - * Scans the document from where we last left off - * and finds the next valid token to parse if it exists - * - * Returns the type of the find: kind of find, block information, attributes - * - * @internal - * @since 5.0.0 - * @since 4.6.1 fixed a bug in attribute parsing which caused catastrophic backtracking on invalid block comments - * @return array - */ - public function next_token() { - $matches = null; - - /* - * aye the magic - * we're using a single RegExp to tokenize the block comment delimiters - * we're also using a trick here because the only difference between a - * block opener and a block closer is the leading `/` before `wp:` (and - * a closer has no attributes). we can trap them both and process the - * match back in PHP to see which one it was. - */ - $has_match = preg_match( - '/).)*+)?}\s+)?(?P\/)?-->/s', - $this->document, - $matches, - PREG_OFFSET_CAPTURE, - $this->offset - ); - - // if we get here we probably have catastrophic backtracking or out-of-memory in the PCRE. - if ( false === $has_match ) { - return array( 'no-more-tokens', null, null, null, null ); - } - - // we have no more tokens. - if ( 0 === $has_match ) { - return array( 'no-more-tokens', null, null, null, null ); - } - - list( $match, $started_at ) = $matches[0]; - - $length = strlen( $match ); - $is_closer = isset( $matches['closer'] ) && -1 !== $matches['closer'][1]; - $is_void = isset( $matches['void'] ) && -1 !== $matches['void'][1]; - $namespace = $matches['namespace']; - $namespace = ( isset( $namespace ) && -1 !== $namespace[1] ) ? $namespace[0] : 'core/'; - $name = $namespace . $matches['name'][0]; - $has_attrs = isset( $matches['attrs'] ) && -1 !== $matches['attrs'][1]; - - /* - * Fun fact! It's not trivial in PHP to create "an empty associative array" since all arrays - * are associative arrays. If we use `array()` we get a JSON `[]` - */ - $attrs = $has_attrs - ? json_decode( $matches['attrs'][0], /* as-associative */ true ) - : array(); - - /* - * This state isn't allowed - * This is an error - */ - if ( $is_closer && ( $is_void || $has_attrs ) ) { - // we can ignore them since they don't hurt anything. - } - - if ( $is_void ) { - return array( 'void-block', $name, $attrs, $started_at, $length ); - } - - if ( $is_closer ) { - return array( 'block-closer', $name, null, $started_at, $length ); - } - - return array( 'block-opener', $name, $attrs, $started_at, $length ); - } - - /** - * Returns a new block object for freeform HTML - * - * @internal - * @since 5.0.0 - * - * @param string $inner_html HTML content of block. - * @return WP_Block_Parser_Block freeform block object. - */ - public function freeform( $inner_html ) { - return new WP_Block_Parser_Block( null, array(), array(), $inner_html, array( $inner_html ) ); - } - - /** - * Pushes a length of text from the input document - * to the output list as a freeform block. - * - * @internal - * @since 5.0.0 - * @param null $length how many bytes of document text to output. - */ - public function add_freeform( $length = null ) { - $length = $length ? $length : strlen( $this->document ) - $this->offset; - - if ( 0 === $length ) { - return; - } - - $this->output[] = (array) $this->freeform( substr( $this->document, $this->offset, $length ) ); - } - - /** - * Given a block structure from memory pushes - * a new block to the output list. - * - * @internal - * @since 5.0.0 - * @param WP_Block_Parser_Block $block The block to add to the output. - * @param int $token_start Byte offset into the document where the first token for the block starts. - * @param int $token_length Byte length of entire block from start of opening token to end of closing token. - * @param int|null $last_offset Last byte offset into document if continuing form earlier output. - */ - public function add_inner_block( WP_Block_Parser_Block $block, $token_start, $token_length, $last_offset = null ) { - $parent = $this->stack[ count( $this->stack ) - 1 ]; - $parent->block->innerBlocks[] = (array) $block; - $html = substr( $this->document, $parent->prev_offset, $token_start - $parent->prev_offset ); - - if ( ! empty( $html ) ) { - $parent->block->innerHTML .= $html; - $parent->block->innerContent[] = $html; - } - - $parent->block->innerContent[] = null; - $parent->prev_offset = $last_offset ? $last_offset : $token_start + $token_length; - } - - /** - * Pushes the top block from the parsing stack to the output list. - * - * @internal - * @since 5.0.0 - * @param int|null $end_offset byte offset into document for where we should stop sending text output as HTML. - */ - public function add_block_from_stack( $end_offset = null ) { - $stack_top = array_pop( $this->stack ); - $prev_offset = $stack_top->prev_offset; - - $html = isset( $end_offset ) - ? substr( $this->document, $prev_offset, $end_offset - $prev_offset ) - : substr( $this->document, $prev_offset ); - - if ( ! empty( $html ) ) { - $stack_top->block->innerHTML .= $html; - $stack_top->block->innerContent[] = $html; - } - - if ( isset( $stack_top->leading_html_start ) ) { - $this->output[] = (array) $this->freeform( - substr( - $this->document, - $stack_top->leading_html_start, - $stack_top->token_start - $stack_top->leading_html_start - ) - ); - } - - $this->output[] = (array) $stack_top->block; - } -} - -/** - * WP_Block_Parser_Block class. - * - * Required for backward compatibility in WordPress Core. - */ -require_once __DIR__ . '/class-wp-block-parser-block.php'; - -/** - * WP_Block_Parser_Frame class. - * - * Required for backward compatibility in WordPress Core. - */ -require_once __DIR__ . '/class-wp-block-parser-frame.php'; diff --git a/src/wp-includes/default-filters.php b/src/wp-includes/default-filters.php index 68dccd979f2fe..db3748c5265c8 100644 --- a/src/wp-includes/default-filters.php +++ b/src/wp-includes/default-filters.php @@ -620,6 +620,7 @@ add_action( 'enqueue_block_editor_assets', 'enqueue_editor_block_styles_assets' ); add_action( 'enqueue_block_editor_assets', 'wp_enqueue_editor_block_directory_assets' ); add_action( 'enqueue_block_editor_assets', 'wp_enqueue_editor_format_library_assets' ); +add_action( 'enqueue_block_editor_assets', 'wp_enqueue_block_editor_script_modules' ); add_action( 'enqueue_block_editor_assets', 'wp_enqueue_global_styles_css_custom_properties' ); add_action( 'wp_print_scripts', 'wp_just_in_time_script_localization' ); add_filter( 'print_scripts_array', 'wp_prototype_before_jquery' ); diff --git a/src/wp-includes/script-loader.php b/src/wp-includes/script-loader.php index 9d2df0dac687f..e1d9c9b9049a8 100644 --- a/src/wp-includes/script-loader.php +++ b/src/wp-includes/script-loader.php @@ -218,46 +218,6 @@ function wp_get_script_polyfill( $scripts, $tests ) { return $polyfill; } -/** - * Registers development scripts that integrate with `@wordpress/scripts`. - * - * @see https://github.com/WordPress/gutenberg/tree/trunk/packages/scripts#start - * - * @since 6.0.0 - * - * @param WP_Scripts $scripts WP_Scripts object. - */ -function wp_register_development_scripts( $scripts ) { - if ( - ! defined( 'SCRIPT_DEBUG' ) || ! SCRIPT_DEBUG - || empty( $scripts->registered['react'] ) - || defined( 'WP_RUN_CORE_TESTS' ) - ) { - return; - } - - $development_scripts = array( - 'react-refresh-entry', - 'react-refresh-runtime', - ); - - foreach ( $development_scripts as $script_name ) { - $assets = include ABSPATH . WPINC . '/assets/script-loader-' . $script_name . '.php'; - if ( ! is_array( $assets ) ) { - return; - } - $scripts->add( - 'wp-' . $script_name, - '/wp-includes/js/dist/development/' . $script_name . '.js', - $assets['dependencies'], - $assets['version'] - ); - } - - // See https://github.com/pmmmwh/react-refresh-webpack-plugin/blob/main/docs/TROUBLESHOOTING.md#externalising-react. - $scripts->registered['react']->deps[] = 'wp-react-refresh-entry'; -} - /** * Registers all the WordPress packages scripts that are in the standardized * `js/dist/` location. @@ -658,7 +618,6 @@ function wp_tinymce_inline_scripts() { */ function wp_default_packages( $scripts ) { wp_default_packages_vendor( $scripts ); - wp_register_development_scripts( $scripts ); wp_register_tinymce_scripts( $scripts ); wp_default_packages_scripts( $scripts ); diff --git a/src/wp-includes/script-modules.php b/src/wp-includes/script-modules.php index c1e90c1c852eb..85cc4accf2e52 100644 --- a/src/wp-includes/script-modules.php +++ b/src/wp-includes/script-modules.php @@ -150,8 +150,8 @@ function wp_default_script_modules() { * Expects multidimensional array like: * * 'interactivity/index.min.js' => array('dependencies' => array(…), 'version' => '…'), - * 'interactivity/debug.min.js' => array('dependencies' => array(…), 'version' => '…'), - * 'interactivity-router/index.min.js' => … + * 'interactivity-router/index.min.js' => array('dependencies' => array(…), 'version' => '…'), + * 'block-library/navigation/view.min.js' => … */ $assets = include ABSPATH . WPINC . "/assets/script-modules-packages{$suffix}.php"; @@ -159,30 +159,12 @@ function wp_default_script_modules() { /* * Build the WordPress Script Module ID from the file name. * Prepend `@wordpress/` and remove extensions and `/index` if present: - * - interactivity/index.min.js => @wordpress/interactivity - * - interactivity/debug.min.js => @wordpress/interactivity/debug - * - block-library/query/view.js => @wordpress/block-library/query/view + * - interactivity/index.min.js => @wordpress/interactivity + * - interactivity-router/index.min.js => @wordpress/interactivity-router + * - block-library/navigation/view.js => @wordpress/block-library/navigation/view */ $script_module_id = '@wordpress/' . preg_replace( '~(?:/index)?(?:\.min)?\.js$~D', '', $file_name, 1 ); - switch ( $script_module_id ) { - /* - * Interactivity exposes two entrypoints, "/index" and "/debug". - * "/debug" should replace "/index" in development. - */ - case '@wordpress/interactivity/debug': - if ( ! SCRIPT_DEBUG ) { - continue 2; - } - $script_module_id = '@wordpress/interactivity'; - break; - case '@wordpress/interactivity': - if ( SCRIPT_DEBUG ) { - continue 2; - } - break; - } - /* * The Interactivity API is designed with server-side rendering as its primary goal, so all of its script modules * should be loaded with low fetchpriority and printed in the footer since they should not be needed in the @@ -207,7 +189,21 @@ function wp_default_script_modules() { wp_interactivity()->add_client_navigation_support_to_script_module( $script_module_id ); } - $path = includes_url( "js/dist/script-modules/{$file_name}" ); - wp_register_script_module( $script_module_id, $path, $script_module_data['dependencies'], $script_module_data['version'], $args ); + $path = includes_url( "js/dist/script-modules/{$file_name}" ); + $module_deps = $script_module_data['module_dependencies'] ?? array(); + wp_register_script_module( $script_module_id, $path, $module_deps, $script_module_data['version'], $args ); } } + +/** + * Enqueues script modules required by the block editor. + * + * @since 6.9.0 + */ +function wp_enqueue_block_editor_script_modules() { + /* + * Enqueue the LaTeX to MathML loader for the math block editor. + * The loader dynamically imports the main LaTeX to MathML module when needed. + */ + wp_enqueue_script_module( '@wordpress/latex-to-mathml/loader' ); +} diff --git a/src/wp-includes/theme-i18n.json b/src/wp-includes/theme-i18n.json deleted file mode 100644 index 8ceaee85afbbe..0000000000000 --- a/src/wp-includes/theme-i18n.json +++ /dev/null @@ -1,127 +0,0 @@ -{ - "title": "Style variation name", - "description": "Style variation description", - "settings": { - "typography": { - "fontSizes": [ - { - "name": "Font size name" - } - ], - "fontFamilies": [ - { - "name": "Font family name" - } - ] - }, - "color": { - "palette": [ - { - "name": "Color name" - } - ], - "gradients": [ - { - "name": "Gradient name" - } - ], - "duotone": [ - { - "name": "Duotone name" - } - ] - }, - "spacing": { - "spacingSizes": [ - { - "name": "Space size name" - } - ] - }, - "dimensions": { - "aspectRatios": [ - { - "name": "Aspect ratio name" - } - ] - }, - "shadow": { - "presets": [ - { - "name": "Shadow name" - } - ] - }, - "border": { - "radiusSizes": [ - { - "name": "Border radius size name" - } - ] - }, - "blocks": { - "*": { - "typography": { - "fontSizes": [ - { - "name": "Font size name" - } - ], - "fontFamilies": [ - { - "name": "Font family name" - } - ] - }, - "color": { - "palette": [ - { - "name": "Color name" - } - ], - "gradients": [ - { - "name": "Gradient name" - } - ], - "duotone": [ - { - "name": "Duotone name" - } - ] - }, - "dimensions": { - "aspectRatios": [ - { - "name": "Aspect ratio name" - } - ] - }, - "spacing": { - "spacingSizes": [ - { - "name": "Space size name" - } - ] - }, - "border": { - "radiusSizes": [ - { - "name": "Border radius size name" - } - ] - } - } - } - }, - "customTemplates": [ - { - "title": "Custom template name" - } - ], - "templateParts": [ - { - "title": "Template part name" - } - ] -} diff --git a/src/wp-includes/theme.json b/src/wp-includes/theme.json deleted file mode 100644 index 362cfe7d3ecc0..0000000000000 --- a/src/wp-includes/theme.json +++ /dev/null @@ -1,413 +0,0 @@ -{ - "$schema": "https://schemas.wp.org/trunk/theme.json", - "version": 3, - "settings": { - "appearanceTools": false, - "useRootPaddingAwareAlignments": false, - "border": { - "color": false, - "radius": false, - "style": false, - "width": false - }, - "color": { - "background": true, - "button": true, - "caption": true, - "custom": true, - "customDuotone": true, - "customGradient": true, - "defaultDuotone": true, - "defaultGradients": true, - "defaultPalette": true, - "duotone": [ - { - "name": "Dark grayscale", - "colors": [ "#000000", "#7f7f7f" ], - "slug": "dark-grayscale" - }, - { - "name": "Grayscale", - "colors": [ "#000000", "#ffffff" ], - "slug": "grayscale" - }, - { - "name": "Purple and yellow", - "colors": [ "#8c00b7", "#fcff41" ], - "slug": "purple-yellow" - }, - { - "name": "Blue and red", - "colors": [ "#000097", "#ff4747" ], - "slug": "blue-red" - }, - { - "name": "Midnight", - "colors": [ "#000000", "#00a5ff" ], - "slug": "midnight" - }, - { - "name": "Magenta and yellow", - "colors": [ "#c7005a", "#fff278" ], - "slug": "magenta-yellow" - }, - { - "name": "Purple and green", - "colors": [ "#a60072", "#67ff66" ], - "slug": "purple-green" - }, - { - "name": "Blue and orange", - "colors": [ "#1900d8", "#ffa96b" ], - "slug": "blue-orange" - } - ], - "gradients": [ - { - "name": "Vivid cyan blue to vivid purple", - "gradient": "linear-gradient(135deg,rgb(6,147,227) 0%,rgb(155,81,224) 100%)", - "slug": "vivid-cyan-blue-to-vivid-purple" - }, - { - "name": "Light green cyan to vivid green cyan", - "gradient": "linear-gradient(135deg,rgb(122,220,180) 0%,rgb(0,208,130) 100%)", - "slug": "light-green-cyan-to-vivid-green-cyan" - }, - { - "name": "Luminous vivid amber to luminous vivid orange", - "gradient": "linear-gradient(135deg,rgb(252,185,0) 0%,rgb(255,105,0) 100%)", - "slug": "luminous-vivid-amber-to-luminous-vivid-orange" - }, - { - "name": "Luminous vivid orange to vivid red", - "gradient": "linear-gradient(135deg,rgb(255,105,0) 0%,rgb(207,46,46) 100%)", - "slug": "luminous-vivid-orange-to-vivid-red" - }, - { - "name": "Very light gray to cyan bluish gray", - "gradient": "linear-gradient(135deg,rgb(238,238,238) 0%,rgb(169,184,195) 100%)", - "slug": "very-light-gray-to-cyan-bluish-gray" - }, - { - "name": "Cool to warm spectrum", - "gradient": "linear-gradient(135deg,rgb(74,234,220) 0%,rgb(151,120,209) 20%,rgb(207,42,186) 40%,rgb(238,44,130) 60%,rgb(251,105,98) 80%,rgb(254,248,76) 100%)", - "slug": "cool-to-warm-spectrum" - }, - { - "name": "Blush light purple", - "gradient": "linear-gradient(135deg,rgb(255,206,236) 0%,rgb(152,150,240) 100%)", - "slug": "blush-light-purple" - }, - { - "name": "Blush bordeaux", - "gradient": "linear-gradient(135deg,rgb(254,205,165) 0%,rgb(254,45,45) 50%,rgb(107,0,62) 100%)", - "slug": "blush-bordeaux" - }, - { - "name": "Luminous dusk", - "gradient": "linear-gradient(135deg,rgb(255,203,112) 0%,rgb(199,81,192) 50%,rgb(65,88,208) 100%)", - "slug": "luminous-dusk" - }, - { - "name": "Pale ocean", - "gradient": "linear-gradient(135deg,rgb(255,245,203) 0%,rgb(182,227,212) 50%,rgb(51,167,181) 100%)", - "slug": "pale-ocean" - }, - { - "name": "Electric grass", - "gradient": "linear-gradient(135deg,rgb(202,248,128) 0%,rgb(113,206,126) 100%)", - "slug": "electric-grass" - }, - { - "name": "Midnight", - "gradient": "linear-gradient(135deg,rgb(2,3,129) 0%,rgb(40,116,252) 100%)", - "slug": "midnight" - } - ], - "heading": true, - "link": false, - "palette": [ - { - "name": "Black", - "slug": "black", - "color": "#000000" - }, - { - "name": "Cyan bluish gray", - "slug": "cyan-bluish-gray", - "color": "#abb8c3" - }, - { - "name": "White", - "slug": "white", - "color": "#ffffff" - }, - { - "name": "Pale pink", - "slug": "pale-pink", - "color": "#f78da7" - }, - { - "name": "Vivid red", - "slug": "vivid-red", - "color": "#cf2e2e" - }, - { - "name": "Luminous vivid orange", - "slug": "luminous-vivid-orange", - "color": "#ff6900" - }, - { - "name": "Luminous vivid amber", - "slug": "luminous-vivid-amber", - "color": "#fcb900" - }, - { - "name": "Light green cyan", - "slug": "light-green-cyan", - "color": "#7bdcb5" - }, - { - "name": "Vivid green cyan", - "slug": "vivid-green-cyan", - "color": "#00d084" - }, - { - "name": "Pale cyan blue", - "slug": "pale-cyan-blue", - "color": "#8ed1fc" - }, - { - "name": "Vivid cyan blue", - "slug": "vivid-cyan-blue", - "color": "#0693e3" - }, - { - "name": "Vivid purple", - "slug": "vivid-purple", - "color": "#9b51e0" - } - ], - "text": true - }, - "dimensions": { - "defaultAspectRatios": true, - "aspectRatios": [ - { - "name": "Square - 1:1", - "slug": "square", - "ratio": "1" - }, - { - "name": "Standard - 4:3", - "slug": "4-3", - "ratio": "4/3" - }, - { - "name": "Portrait - 3:4", - "slug": "3-4", - "ratio": "3/4" - }, - { - "name": "Classic - 3:2", - "slug": "3-2", - "ratio": "3/2" - }, - { - "name": "Classic Portrait - 2:3", - "slug": "2-3", - "ratio": "2/3" - }, - { - "name": "Wide - 16:9", - "slug": "16-9", - "ratio": "16/9" - }, - { - "name": "Tall - 9:16", - "slug": "9-16", - "ratio": "9/16" - } - ] - }, - "shadow": { - "defaultPresets": true, - "presets": [ - { - "name": "Natural", - "slug": "natural", - "shadow": "6px 6px 9px rgba(0, 0, 0, 0.2)" - }, - { - "name": "Deep", - "slug": "deep", - "shadow": "12px 12px 50px rgba(0, 0, 0, 0.4)" - }, - { - "name": "Sharp", - "slug": "sharp", - "shadow": "6px 6px 0px rgba(0, 0, 0, 0.2)" - }, - { - "name": "Outlined", - "slug": "outlined", - "shadow": "6px 6px 0px -3px rgb(255, 255, 255), 6px 6px rgb(0, 0, 0)" - }, - { - "name": "Crisp", - "slug": "crisp", - "shadow": "6px 6px 0px rgb(0, 0, 0)" - } - ] - }, - "spacing": { - "blockGap": null, - "margin": false, - "padding": false, - "customSpacingSize": true, - "defaultSpacingSizes": true, - "units": [ "px", "em", "rem", "vh", "vw", "%" ], - "spacingScale": { - "operator": "*", - "increment": 1.5, - "steps": 7, - "mediumStep": 1.5, - "unit": "rem" - } - }, - "typography": { - "customFontSize": true, - "defaultFontSizes": true, - "dropCap": true, - "fontSizes": [ - { - "name": "Small", - "slug": "small", - "size": "13px" - }, - { - "name": "Medium", - "slug": "medium", - "size": "20px" - }, - { - "name": "Large", - "slug": "large", - "size": "36px" - }, - { - "name": "Extra Large", - "slug": "x-large", - "size": "42px" - } - ], - "fontStyle": true, - "fontWeight": true, - "letterSpacing": true, - "lineHeight": false, - "textAlign": true, - "textDecoration": true, - "textTransform": true, - "writingMode": false - }, - "blocks": { - "core/button": { - "border": { - "radius": true - } - }, - "core/image": { - "lightbox": { - "allowEditing": true - } - }, - "core/pullquote": { - "border": { - "color": true, - "radius": true, - "style": true, - "width": true - } - } - } - }, - "styles": { - "blocks": { - "core/button": { - "variations": { - "outline": { - "border": { - "width": "2px", - "style": "solid", - "color": "currentColor" - }, - "color": { - "text": "currentColor", - "gradient": "transparent none" - }, - "spacing": { - "padding": { - "top": "0.667em", - "right": "1.33em", - "bottom": "0.667em", - "left": "1.33em" - } - } - } - } - }, - "core/site-logo": { - "variations": { - "rounded": { - "border": { - "radius": "9999px" - } - } - } - } - }, - "elements": { - "button": { - "color": { - "text": "#fff", - "background": "#32373c" - }, - "spacing": { - "padding": { - "top": "calc(0.667em + 2px)", - "right": "calc(1.333em + 2px)", - "bottom": "calc(0.667em + 2px)", - "left": "calc(1.333em + 2px)" - } - }, - "typography": { - "fontSize": "inherit", - "fontFamily": "inherit", - "fontStyle": "inherit", - "fontWeight": "inherit", - "letterSpacing": "inherit", - "textTransform": "inherit", - "lineHeight": "inherit", - "textDecoration": "none" - }, - "border": { - "width": "0" - } - }, - "link": { - "typography": { - "textDecoration": "underline" - } - } - }, - "spacing": { - "blockGap": "24px", - "padding": { - "top": "0px", - "right": "0px", - "bottom": "0px", - "left": "0px" - } - } - } -} diff --git a/src/wp-settings.php b/src/wp-settings.php index 45f96ace09a1c..adaa0b161c3f6 100644 --- a/src/wp-settings.php +++ b/src/wp-settings.php @@ -242,6 +242,8 @@ require ABSPATH . WPINC . '/cron.php'; require ABSPATH . WPINC . '/deprecated.php'; require ABSPATH . WPINC . '/script-loader.php'; +require ABSPATH . WPINC . '/build/routes.php'; +require ABSPATH . WPINC . '/build/pages.php'; require ABSPATH . WPINC . '/taxonomy.php'; require ABSPATH . WPINC . '/class-wp-taxonomy.php'; require ABSPATH . WPINC . '/class-wp-term.php'; diff --git a/tests/phpunit/data/blocks/fixtures/core__categories.server.html b/tests/phpunit/data/blocks/fixtures/core__categories.server.html index f073f8f5ee213..f10bd41b123bc 100644 --- a/tests/phpunit/data/blocks/fixtures/core__categories.server.html +++ b/tests/phpunit/data/blocks/fixtures/core__categories.server.html @@ -1 +1 @@ -
      • No categories
      +
      • No categories
      diff --git a/tests/phpunit/tests/admin/wpSiteHealth.php b/tests/phpunit/tests/admin/wpSiteHealth.php index 86974db2160e3..0c6a42f71bea3 100644 --- a/tests/phpunit/tests/admin/wpSiteHealth.php +++ b/tests/phpunit/tests/admin/wpSiteHealth.php @@ -490,7 +490,7 @@ public function data_object_cache_thresholds() { array( 'comments_count', 0 ), array( 'posts_count', 0 ), array( 'terms_count', 1 ), - array( 'options_count', 100 ), + array( 'options_count', 1 ), array( 'users_count', 0 ), array( 'alloptions_count', 100 ), array( 'alloptions_bytes', 1000 ), diff --git a/tests/phpunit/tests/script-modules/wpScriptModules.php b/tests/phpunit/tests/script-modules/wpScriptModules.php index 4b103953c8451..047176bdb2d8b 100644 --- a/tests/phpunit/tests/script-modules/wpScriptModules.php +++ b/tests/phpunit/tests/script-modules/wpScriptModules.php @@ -1823,7 +1823,7 @@ public function test_default_script_modules() { $actual_preloads = $this->normalize_markup_for_snapshot( get_echo( array( wp_script_modules(), 'print_script_module_preloads' ) ) ); $this->assertEqualHTML( ' - + ', $actual_preloads, '', @@ -1897,7 +1897,7 @@ public function test_dependent_of_default_script_modules() { $expected = ' - + '; diff --git a/tools/gutenberg/build-gutenberg.js b/tools/gutenberg/build-gutenberg.js new file mode 100644 index 0000000000000..344f1b58bed47 --- /dev/null +++ b/tools/gutenberg/build-gutenberg.js @@ -0,0 +1,162 @@ +#!/usr/bin/env node + +/** + * Build Gutenberg Script + * + * This script builds the Gutenberg repository using its build command + * as specified in the root package.json's "gutenberg" configuration. + * + * @package WordPress + */ + +const { spawn } = require( 'child_process' ); +const fs = require( 'fs' ); +const path = require( 'path' ); + +// Paths +const rootDir = path.resolve( __dirname, '../..' ); +const gutenbergDir = path.join( rootDir, 'gutenberg' ); + +/** + * Execute a command and return a promise. + * Captures output and only displays it on failure for cleaner logs. + * + * @param {string} command - Command to execute. + * @param {string[]} args - Command arguments. + * @param {Object} options - Spawn options. + * @return {Promise} Promise that resolves when command completes. + */ +function exec( command, args, options = {} ) { + return new Promise( ( resolve, reject ) => { + let stdout = ''; + let stderr = ''; + + const child = spawn( command, args, { + cwd: options.cwd || rootDir, + stdio: [ 'ignore', 'pipe', 'pipe' ], + shell: process.platform === 'win32', // Use shell on Windows to find .cmd files + ...options, + } ); + + // Capture output + if ( child.stdout ) { + child.stdout.on( 'data', ( data ) => { + stdout += data.toString(); + } ); + } + + if ( child.stderr ) { + child.stderr.on( 'data', ( data ) => { + stderr += data.toString(); + } ); + } + + child.on( 'close', ( code ) => { + if ( code !== 0 ) { + // Show output only on failure + if ( stdout ) { + console.error( '\nCommand output:' ); + console.error( stdout ); + } + if ( stderr ) { + console.error( '\nCommand errors:' ); + console.error( stderr ); + } + reject( + new Error( + `${ command } ${ args.join( + ' ' + ) } failed with code ${ code }` + ) + ); + } else { + resolve(); + } + } ); + + child.on( 'error', reject ); + } ); +} + +/** + * Main execution function. + */ +async function main() { + console.log( '🔍 Checking Gutenberg setup...' ); + + // Verify Gutenberg directory exists + if ( ! fs.existsSync( gutenbergDir ) ) { + console.error( '❌ Gutenberg directory not found at:', gutenbergDir ); + console.error( ' Run: node tools/gutenberg/checkout-gutenberg.js' ); + process.exit( 1 ); + } + + // Verify node_modules exists + const nodeModulesPath = path.join( gutenbergDir, 'node_modules' ); + if ( ! fs.existsSync( nodeModulesPath ) ) { + console.error( '❌ Gutenberg dependencies not installed' ); + console.error( ' Run: node tools/gutenberg/checkout-gutenberg.js' ); + process.exit( 1 ); + } + + console.log( '✅ Gutenberg directory found' ); + + // Modify Gutenberg's package.json for Core build + console.log( '\n⚙️ Configuring build for WordPress Core...' ); + const gutenbergPackageJsonPath = path.join( gutenbergDir, 'package.json' ); + + try { + const content = fs.readFileSync( gutenbergPackageJsonPath, 'utf8' ); + const gutenbergPackageJson = JSON.parse( content ); + + // Set Core environment variables + gutenbergPackageJson.config = gutenbergPackageJson.config || {}; + gutenbergPackageJson.config.IS_GUTENBERG_PLUGIN = false; + gutenbergPackageJson.config.IS_WORDPRESS_CORE = true; + + fs.writeFileSync( + gutenbergPackageJsonPath, + JSON.stringify( gutenbergPackageJson, null, '\t' ) + '\n' + ); + + console.log( ' ✅ IS_GUTENBERG_PLUGIN = false' ); + console.log( ' ✅ IS_WORDPRESS_CORE = true' ); + } catch ( error ) { + console.error( + '❌ Error modifying Gutenberg package.json:', + error.message + ); + process.exit( 1 ); + } + + // Build Gutenberg + console.log( '\n🔨 Building Gutenberg for WordPress Core...' ); + console.log( ' (This may take a few minutes)' ); + + const startTime = Date.now(); + + try { + // On Windows, shell mode is used and needs the argument wrapped in quotes + // On Unix, arguments are passed directly without shell parsing + const baseUrlArg = + process.platform === 'win32' + ? '--base-url="includes_url( \'build\' )"' + : "--base-url=includes_url( 'build' )"; + + await exec( 'npm', [ 'run', 'build', '--', baseUrlArg ], { + cwd: gutenbergDir, + } ); + + const duration = Math.round( ( Date.now() - startTime ) / 1000 ); + console.log( `✅ Build completed in ${ duration }s` ); + } catch ( error ) { + console.error( '❌ Build failed:', error.message ); + process.exit( 1 ); + } +} + +// Run main function +main().catch( ( error ) => { + console.error( '❌ Unexpected error:', error ); + process.exit( 1 ); +} ); diff --git a/tools/gutenberg/checkout-gutenberg.js b/tools/gutenberg/checkout-gutenberg.js new file mode 100644 index 0000000000000..42e35a1967b78 --- /dev/null +++ b/tools/gutenberg/checkout-gutenberg.js @@ -0,0 +1,239 @@ +#!/usr/bin/env node + +/** + * Checkout Gutenberg Repository Script + * + * This script checks out the Gutenberg repository at a specific commit/branch/tag + * as specified in the root package.json's "gutenberg" configuration. + * + * It handles: + * - Initial clone if directory doesn't exist + * - Updating existing checkout to correct ref + * - Installing dependencies with npm ci + * - Idempotent operation (safe to run multiple times) + * + * @package WordPress + */ + +const { spawn } = require( 'child_process' ); +const fs = require( 'fs' ); +const path = require( 'path' ); + +// Constants +const GUTENBERG_REPO = 'https://github.com/WordPress/gutenberg.git'; + +// Paths +const rootDir = path.resolve( __dirname, '../..' ); +const gutenbergDir = path.join( rootDir, 'gutenberg' ); +const packageJsonPath = path.join( rootDir, 'package.json' ); + +/** + * Execute a command and return a promise. + * Captures output and only displays it on failure for cleaner logs. + * + * @param {string} command - Command to execute. + * @param {string[]} args - Command arguments. + * @param {Object} options - Spawn options. + * @return {Promise} Promise that resolves when command completes. + */ +function exec( command, args, options = {} ) { + return new Promise( ( resolve, reject ) => { + let stdout = ''; + let stderr = ''; + + const child = spawn( command, args, { + cwd: options.cwd || rootDir, + stdio: [ 'ignore', 'pipe', 'pipe' ], + shell: process.platform === 'win32', // Use shell on Windows to find .cmd files + ...options, + } ); + + // Capture output + if ( child.stdout ) { + child.stdout.on( 'data', ( data ) => { + stdout += data.toString(); + } ); + } + + if ( child.stderr ) { + child.stderr.on( 'data', ( data ) => { + stderr += data.toString(); + } ); + } + + child.on( 'close', ( code ) => { + if ( code !== 0 ) { + // Show output only on failure + if ( stdout ) { + console.error( '\nCommand output:' ); + console.error( stdout ); + } + if ( stderr ) { + console.error( '\nCommand errors:' ); + console.error( stderr ); + } + reject( + new Error( + `${ command } ${ args.join( + ' ' + ) } failed with code ${ code }` + ) + ); + } else { + resolve(); + } + } ); + + child.on( 'error', reject ); + } ); +} + +/** + * Execute a command and capture its output. + * + * @param {string} command - Command to execute. + * @param {string[]} args - Command arguments. + * @param {Object} options - Spawn options. + * @return {Promise} Promise that resolves with command output. + */ +function execOutput( command, args, options = {} ) { + return new Promise( ( resolve, reject ) => { + const child = spawn( command, args, { + cwd: options.cwd || rootDir, + shell: process.platform === 'win32', // Use shell on Windows to find .cmd files + ...options, + } ); + + let stdout = ''; + let stderr = ''; + + if ( child.stdout ) { + child.stdout.on( 'data', ( data ) => { + stdout += data.toString(); + } ); + } + + if ( child.stderr ) { + child.stderr.on( 'data', ( data ) => { + stderr += data.toString(); + } ); + } + + child.on( 'close', ( code ) => { + if ( code !== 0 ) { + reject( new Error( `${ command } failed: ${ stderr }` ) ); + } else { + resolve( stdout.trim() ); + } + } ); + + child.on( 'error', reject ); + } ); +} + +/** + * Main execution function. + */ +async function main() { + console.log( '🔍 Checking Gutenberg configuration...' ); + + // Read Gutenberg ref from package.json + let ref; + try { + const packageJson = JSON.parse( + fs.readFileSync( packageJsonPath, 'utf8' ) + ); + ref = packageJson.gutenberg?.ref; + + if ( ! ref ) { + throw new Error( 'Missing "gutenberg.ref" in package.json' ); + } + + console.log( ` Repository: ${ GUTENBERG_REPO }` ); + console.log( ` Reference: ${ ref }` ); + } catch ( error ) { + console.error( '❌ Error reading package.json:', error.message ); + process.exit( 1 ); + } + + // Check if Gutenberg directory exists + const gutenbergExists = fs.existsSync( gutenbergDir ); + + if ( ! gutenbergExists ) { + console.log( '\n📥 Cloning Gutenberg repository (shallow clone)...' ); + try { + // Generic shallow clone approach that works for both branches and commit hashes + // 1. Clone with no checkout and shallow depth + await exec( 'git', [ + 'clone', + '--depth', + '1', + '--no-checkout', + GUTENBERG_REPO, + 'gutenberg', + ] ); + + // 2. Fetch the specific ref with depth 1 (works for branches, tags, and commits) + await exec( 'git', [ 'fetch', '--depth', '1', 'origin', ref ], { + cwd: gutenbergDir, + } ); + + // 3. Checkout FETCH_HEAD + await exec( 'git', [ 'checkout', 'FETCH_HEAD' ], { + cwd: gutenbergDir, + } ); + + console.log( '✅ Cloned successfully' ); + } catch ( error ) { + console.error( '❌ Clone failed:', error.message ); + process.exit( 1 ); + } + } else { + console.log( '\n✅ Gutenberg directory already exists' ); + } + + // Fetch and checkout target ref + console.log( `\n📡 Fetching and checking out: ${ ref }` ); + try { + // Fetch the specific ref (works for branches, tags, and commit hashes) + await exec( 'git', [ 'fetch', '--depth', '1', 'origin', ref ], { + cwd: gutenbergDir, + } ); + + // Checkout what was just fetched + await exec( 'git', [ 'checkout', 'FETCH_HEAD' ], { + cwd: gutenbergDir, + } ); + + console.log( '✅ Checked out successfully' ); + } catch ( error ) { + console.error( '❌ Fetch/checkout failed:', error.message ); + process.exit( 1 ); + } + + // Install dependencies + console.log( '\n📦 Installing dependencies...' ); + const nodeModulesExists = fs.existsSync( + path.join( gutenbergDir, 'node_modules' ) + ); + + if ( ! nodeModulesExists ) { + console.log( ' (This may take a few minutes on first run)' ); + } + + try { + await exec( 'npm', [ 'ci' ], { cwd: gutenbergDir } ); + console.log( '✅ Dependencies installed' ); + } catch ( error ) { + console.error( '❌ npm ci failed:', error.message ); + process.exit( 1 ); + } + + console.log( '\n✅ Gutenberg checkout complete!' ); +} + +// Run main function +main().catch( ( error ) => { + console.error( '❌ Unexpected error:', error ); + process.exit( 1 ); +} ); diff --git a/tools/gutenberg/copy-gutenberg-build.js b/tools/gutenberg/copy-gutenberg-build.js new file mode 100644 index 0000000000000..7257e5f3b1d8d --- /dev/null +++ b/tools/gutenberg/copy-gutenberg-build.js @@ -0,0 +1,1135 @@ +#!/usr/bin/env node + +/** + * Copy Gutenberg Build Script + * + * This script copies and transforms Gutenberg's build output to WordPress Core. + * It handles path transformations from plugin structure to Core structure. + * + * @package WordPress + */ + +const fs = require( 'fs' ); +const path = require( 'path' ); +const json2php = require( 'json2php' ); + +// Paths +const rootDir = path.resolve( __dirname, '../..' ); +const gutenbergDir = path.join( rootDir, 'gutenberg' ); +const gutenbergBuildDir = path.join( gutenbergDir, 'build' ); +const gutenbergPackagesDir = path.join( gutenbergDir, 'packages' ); + +// Determine build target from command line argument (--dev or --build-dir) +// Default to 'src' for development +const args = process.argv.slice( 2 ); +const buildDirArg = args.find( ( arg ) => arg.startsWith( '--build-dir=' ) ); +const buildTarget = buildDirArg + ? buildDirArg.split( '=' )[ 1 ] + : args.includes( '--dev' ) + ? 'src' + : 'build'; + +const wpIncludesDir = path.join( rootDir, buildTarget, 'wp-includes' ); + +/** + * Copy configuration. + * Defines what to copy from Gutenberg build and where it goes in Core. + */ +const COPY_CONFIG = { + // PHP infrastructure files (to wp-includes/build/) + phpInfrastructure: { + destination: 'build', + files: [ 'routes.php', 'pages.php' ], + directories: [ 'pages', 'routes' ], + }, + + // JavaScript packages (to wp-includes/js/dist/) + scripts: { + source: 'scripts', + destination: 'js/dist', + copyDirectories: true, // Copy subdirectories + patterns: [ '*.js', '*.js.map' ], + // Rename vendors/ to vendor/ when copying + directoryRenames: { + vendors: 'vendor', + }, + }, + + // Script modules (to wp-includes/js/dist/script-modules/) + modules: { + source: 'modules', + destination: 'js/dist/script-modules', + copyAll: true, + }, + + // Styles (to wp-includes/css/dist/) + styles: { + source: 'styles', + destination: 'css/dist', + copyAll: true, + }, + + // Blocks (to wp-includes/blocks/) + // Unified configuration for all block types + blocks: { + destination: 'blocks', + sources: [ + { + // Block library blocks + name: 'block-library', + scripts: 'scripts/block-library', + styles: 'styles/block-library', + php: 'block-library/src', + }, + { + // Widget blocks + name: 'widgets', + scripts: 'scripts/widgets/blocks', + styles: 'styles/widgets', + php: 'widgets/src/blocks', + }, + ], + }, + + // PHP source files (non-block files, copied from packages) + phpSource: { + files: [ + { + // Block parser classes + package: 'block-serialization-default-parser', + files: [ + 'class-wp-block-parser.php', + 'class-wp-block-parser-block.php', + 'class-wp-block-parser-frame.php', + ], + destination: '', // Root of wp-includes + }, + ], + }, + + // Theme JSON files (from Gutenberg lib directory) + themeJson: { + files: [ + { from: 'theme.json', to: 'theme.json' }, + { from: 'theme-i18n.json', to: 'theme-i18n.json' }, + ], + }, +}; + +/** + * Check if a block is experimental by reading its block.json. + * + * @param {string} blockJsonPath - Path to block.json file. + * @return {boolean} True if block is experimental. + */ +function isExperimentalBlock( blockJsonPath ) { + try { + if ( ! fs.existsSync( blockJsonPath ) ) { + return false; + } + const blockJson = JSON.parse( + fs.readFileSync( blockJsonPath, 'utf8' ) + ); + return !! blockJson.__experimental; + } catch ( error ) { + return false; + } +} + +/** + * Recursively copy directory. + * + * @param {string} src - Source directory. + * @param {string} dest - Destination directory. + * @param {Function} transform - Optional transform function for file contents. + * @param {Object} options - Optional configuration. + * @param {boolean} options.excludePHP - Skip PHP files. + * @param {boolean} options.excludeExperimental - Skip experimental blocks. + */ +function copyDirectory( src, dest, transform = null, options = {} ) { + if ( ! fs.existsSync( src ) ) { + return; + } + + fs.mkdirSync( dest, { recursive: true } ); + + const entries = fs.readdirSync( src, { withFileTypes: true } ); + + for ( const entry of entries ) { + const srcPath = path.join( src, entry.name ); + const destPath = path.join( dest, entry.name ); + + if ( entry.isDirectory() ) { + // Check if this directory is an experimental block + if ( options.excludeExperimental ) { + const blockJsonPath = path.join( srcPath, 'block.json' ); + if ( isExperimentalBlock( blockJsonPath ) ) { + continue; + } + } + + copyDirectory( srcPath, destPath, transform, options ); + } else { + // Skip PHP files if excludePHP is true + if ( options.excludePHP && /\.php$/.test( entry.name ) ) { + continue; + } + + let content = fs.readFileSync( srcPath ); + + // Apply transformation if provided and file is text + if ( transform && /\.(php|js|css)$/.test( entry.name ) ) { + try { + content = transform( + content.toString(), + srcPath, + destPath + ); + } catch ( error ) { + console.error( + ` ⚠️ Transform error in ${ entry.name }:`, + error.message + ); + } + } + + fs.writeFileSync( destPath, content ); + } + } +} + +/** + * Copy all assets for blocks from Gutenberg to Core. + * Handles scripts, styles, PHP, and JSON for all block types in a unified way. + * + * @param {Object} config - Block configuration from COPY_CONFIG.blocks + */ +function copyBlockAssets( config ) { + const blocksDest = path.join( wpIncludesDir, config.destination ); + + for ( const source of config.sources ) { + const scriptsSrc = path.join( gutenbergBuildDir, source.scripts ); + const stylesSrc = path.join( gutenbergBuildDir, source.styles ); + const phpSrc = path.join( gutenbergPackagesDir, source.php ); + + if ( ! fs.existsSync( scriptsSrc ) ) { + continue; + } + + // Get all block directories from the scripts source + const blockDirs = fs + .readdirSync( scriptsSrc, { withFileTypes: true } ) + .filter( ( entry ) => entry.isDirectory() ) + .map( ( entry ) => entry.name ); + + for ( const blockName of blockDirs ) { + // Skip experimental blocks + const blockJsonPath = path.join( + scriptsSrc, + blockName, + 'block.json' + ); + if ( isExperimentalBlock( blockJsonPath ) ) { + continue; + } + + const blockDest = path.join( blocksDest, blockName ); + fs.mkdirSync( blockDest, { recursive: true } ); + + // 1. Copy scripts/JSON (everything except PHP) + const blockScriptsSrc = path.join( scriptsSrc, blockName ); + if ( fs.existsSync( blockScriptsSrc ) ) { + const files = fs.readdirSync( blockScriptsSrc ); + for ( const file of files ) { + if ( file.endsWith( '.php' ) ) { + continue; // Skip PHP, copied from packages + } + fs.copyFileSync( + path.join( blockScriptsSrc, file ), + path.join( blockDest, file ) + ); + } + } + + // 2. Copy styles (if they exist in per-block directory) + const blockStylesSrc = path.join( stylesSrc, blockName ); + if ( fs.existsSync( blockStylesSrc ) ) { + const cssFiles = fs + .readdirSync( blockStylesSrc ) + .filter( ( file ) => file.endsWith( '.css' ) ); + for ( const cssFile of cssFiles ) { + fs.copyFileSync( + path.join( blockStylesSrc, cssFile ), + path.join( blockDest, cssFile ) + ); + } + } + + // 3. Copy PHP from packages + const blockPhpSrc = path.join( phpSrc, blockName, 'index.php' ); + if ( fs.existsSync( blockPhpSrc ) ) { + const phpDest = path.join( + wpIncludesDir, + config.destination, + `${ blockName }.php` + ); + const content = fs.readFileSync( blockPhpSrc, 'utf8' ); + fs.writeFileSync( phpDest, content ); + } + } + + console.log( + ` ✅ ${ source.name } blocks copied (${ blockDirs.length } blocks)` + ); + } +} + +/** + * Generate script-modules-packages.min.php from individual asset files. + * Reads all view.min.asset.php files from modules/block-library and combines them + * into a single PHP file. + */ +function generateScriptModulesPackages() { + const modulesDir = path.join( gutenbergBuildDir, 'modules' ); + const assetsMin = {}; + const assetsRegular = {}; + + /** + * Recursively process directory to find .asset.php files. + * + * @param {string} dir - Directory to process. + * @param {string} baseDir - Base directory for relative paths. + */ + function processDirectory( dir, baseDir ) { + if ( ! fs.existsSync( dir ) ) { + return; + } + + const entries = fs.readdirSync( dir, { withFileTypes: true } ); + + for ( const entry of entries ) { + const fullPath = path.join( dir, entry.name ); + + if ( entry.isDirectory() ) { + processDirectory( fullPath, baseDir ); + } else if ( entry.name.endsWith( '.min.asset.php' ) ) { + const relativePath = path.relative( baseDir, fullPath ); + // Normalize path separators to forward slashes for cross-platform consistency + const normalizedPath = relativePath + .split( path.sep ) + .join( '/' ); + const jsPathMin = normalizedPath.replace( + /\.asset\.php$/, + '.js' + ); + const jsPathRegular = jsPathMin.replace( /\.min\.js$/, '.js' ); + + try { + // Read and parse the PHP asset file + const phpContent = fs.readFileSync( fullPath, 'utf8' ); + // Extract the array from PHP: `require_once ABSPATH . WPINC . '/blocks/${ name }.php';` + ) + .join( '\n' ) } +`; + + fs.writeFileSync( + path.join( wpIncludesDir, 'blocks/require-dynamic-blocks.php' ), + dynamicContent + ); + + // Generate require-static-blocks.php + const staticContent = ` `\t'${ name }',` ).join( '\n' ) } +); +`; + + fs.writeFileSync( + path.join( wpIncludesDir, 'blocks/require-static-blocks.php' ), + staticContent + ); + + console.log( + ` ✅ Generated: ${ dynamicBlocks.length } dynamic, ${ staticBlocks.length } static blocks` + ); +} + +/** + * Generate blocks-json.php from all block.json files. + * Reads all block.json files and combines them into a single PHP array. + * Uses json2php to maintain consistency with Core's formatting. + */ +function generateBlocksJson() { + const blocksDir = path.join( wpIncludesDir, 'blocks' ); + const blocks = {}; + + if ( ! fs.existsSync( blocksDir ) ) { + console.error( ' ⚠️ Blocks directory not found' ); + return; + } + + const entries = fs.readdirSync( blocksDir, { withFileTypes: true } ); + + for ( const entry of entries ) { + if ( ! entry.isDirectory() ) { + continue; + } + + const blockJsonPath = path.join( blocksDir, entry.name, 'block.json' ); + + if ( fs.existsSync( blockJsonPath ) ) { + try { + const blockJson = JSON.parse( + fs.readFileSync( blockJsonPath, 'utf8' ) + ); + blocks[ entry.name ] = blockJson; + } catch ( error ) { + console.error( + ` ⚠️ Error reading ${ entry.name }/block.json:`, + error.message + ); + } + } + } + + // Generate the PHP file content using json2php for consistent formatting + const phpContent = + ' 1 ) { + currentArray += 'array('; + } + i += 5; // Skip 'array(' + continue; + } + + if ( depth > 0 ) { + if ( char === '(' ) { + depth++; + currentArray += char; + } else if ( char === ')' ) { + depth--; + if ( depth === 0 ) { + // Found complete nested array + const placeholder = `__ARRAY_${ nestedArrays.length }__`; + nestedArrays.push( currentArray ); + content = + content.substring( 0, arrayStart ) + + placeholder + + content.substring( i + 1 ); + i = arrayStart + placeholder.length - 1; + currentArray = ''; + } else { + currentArray += char; + } + } else { + currentArray += char; + } + } + } else if ( depth > 0 ) { + currentArray += char; + } + } + + // Now parse the simplified content + const result = {}; + const values = []; + let isAssociative = false; + + // Split by top-level commas + const parts = []; + depth = 0; + inString = false; + let currentPart = ''; + + for ( let i = 0; i < content.length; i++ ) { + const char = content[ i ]; + + if ( + ( char === "'" || char === '"' ) && + ( i === 0 || content[ i - 1 ] !== '\\' ) + ) { + inString = ! inString; + } + + if ( ! inString && char === ',' && depth === 0 ) { + parts.push( currentPart.trim() ); + currentPart = ''; + } else { + currentPart += char; + if ( ! inString ) { + if ( char === '(' ) depth++; + if ( char === ')' ) depth--; + } + } + } + if ( currentPart.trim() ) { + parts.push( currentPart.trim() ); + } + + // Parse each part + for ( const part of parts ) { + const arrowMatch = part.match( /^(.+?)\s*=>\s*(.+)$/ ); + + if ( arrowMatch ) { + isAssociative = true; + let key = arrowMatch[ 1 ].trim().replace( /^['"]|['"]$/g, '' ); + let value = arrowMatch[ 2 ].trim(); + + // Replace placeholders + while ( value.match( /__ARRAY_(\d+)__/ ) ) { + value = value.replace( /__ARRAY_(\d+)__/, ( match, index ) => { + return 'array(' + nestedArrays[ parseInt( index ) ] + ')'; + } ); + } + + result[ key ] = parseValue( value ); + } else { + // No arrow, indexed array + let value = part; + + // Replace placeholders + while ( value.match( /__ARRAY_(\d+)__/ ) ) { + value = value.replace( /__ARRAY_(\d+)__/, ( match, index ) => { + return 'array(' + nestedArrays[ parseInt( index ) ] + ')'; + } ); + } + + values.push( parseValue( value ) ); + } + } + + return isAssociative ? result : values; + + /** + * Parse a single value. + * + * @param {string} value - The value string to parse. + * @return {*} Parsed value. + */ + function parseValue( value ) { + value = value.trim(); + + if ( value.startsWith( 'array(' ) && value.endsWith( ')' ) ) { + return parsePHPArray( value.substring( 6, value.length - 1 ) ); + } else if ( value.match( /^['"].*['"]$/ ) ) { + return value.substring( 1, value.length - 1 ); + } else if ( value === 'true' ) { + return true; + } else if ( value === 'false' ) { + return false; + } else if ( ! isNaN( value ) && value !== '' ) { + return parseInt( value, 10 ); + } + return value; + } +} + +/** + * Transform PHP file contents to work in Core. + * + * @param {string} content - File content. + * @return {string} Transformed content. + */ +function transformPHPContent( content ) { + let transformed = content; + + // Fix boot module asset file path for Core's different directory structure + // FROM: __DIR__ . '/../../modules/boot/index.min.asset.php' + // TO: ABSPATH . WPINC . '/js/dist/script-modules/boot/index.min.asset.php' + // This is needed because Core copies modules to a different location than the plugin structure + transformed = transformed.replace( + /__DIR__\s*\.\s*['"]\/\.\.\/\.\.\/modules\/boot\/index\.min\.asset\.php['"]/g, + "ABSPATH . WPINC . '/js/dist/script-modules/boot/index.min.asset.php'" + ); + + return transformed; +} + +/** + * Main execution function. + */ +async function main() { + console.log( '🔍 Checking Gutenberg build...' ); + console.log( ` Build target: ${ buildTarget }/` ); + + // Verify Gutenberg build exists + if ( ! fs.existsSync( gutenbergBuildDir ) ) { + console.error( '❌ Gutenberg build directory not found' ); + console.error( ' Run: node tools/gutenberg/build-gutenberg.js' ); + process.exit( 1 ); + } + + console.log( '✅ Gutenberg build found' ); + + // 1. Copy PHP infrastructure + console.log( '\n📦 Copying PHP infrastructure...' ); + const phpConfig = COPY_CONFIG.phpInfrastructure; + const phpDest = path.join( wpIncludesDir, phpConfig.destination ); + + // Copy PHP files + for ( const file of phpConfig.files ) { + const src = path.join( gutenbergBuildDir, file ); + const dest = path.join( phpDest, file ); + + if ( fs.existsSync( src ) ) { + fs.mkdirSync( path.dirname( dest ), { recursive: true } ); + let content = fs.readFileSync( src, 'utf8' ); + content = transformPHPContent( content ); + fs.writeFileSync( dest, content ); + console.log( ` ✅ ${ file }` ); + } else { + console.log( + ` ⚠️ ${ file } not found (may not exist in this Gutenberg version)` + ); + } + } + + // Copy PHP directories + for ( const dir of phpConfig.directories ) { + const src = path.join( gutenbergBuildDir, dir ); + const dest = path.join( phpDest, dir ); + + if ( fs.existsSync( src ) ) { + console.log( ` 📁 Copying ${ dir }/...` ); + copyDirectory( src, dest, transformPHPContent ); + console.log( ` ✅ ${ dir }/ copied` ); + } + } + + // 2. Copy JavaScript packages + console.log( '\n📦 Copying JavaScript packages...' ); + const scriptsConfig = COPY_CONFIG.scripts; + const scriptsSrc = path.join( gutenbergBuildDir, scriptsConfig.source ); + const scriptsDest = path.join( wpIncludesDir, scriptsConfig.destination ); + + // Transform function to remove source map comments from all JS files + const removeSourceMaps = ( content ) => { + return content.replace( /\/\/# sourceMappingURL=.*$/m, '' ).trimEnd(); + }; + + if ( fs.existsSync( scriptsSrc ) ) { + const entries = fs.readdirSync( scriptsSrc, { withFileTypes: true } ); + + for ( const entry of entries ) { + const src = path.join( scriptsSrc, entry.name ); + + if ( entry.isDirectory() ) { + // Check if this should be copied as a directory (like vendors/) + if ( + scriptsConfig.copyDirectories && + scriptsConfig.directoryRenames && + scriptsConfig.directoryRenames[ entry.name ] + ) { + // Copy special directories with rename (vendors/ → vendor/) + // Only copy react-jsx-runtime from vendors (react and react-dom come from Core's node_modules) + const destName = + scriptsConfig.directoryRenames[ entry.name ]; + const dest = path.join( scriptsDest, destName ); + + if ( entry.name === 'vendors' ) { + // Only copy react-jsx-runtime files, skip react and react-dom + const vendorFiles = fs.readdirSync( src ); + let copiedCount = 0; + for ( const file of vendorFiles ) { + if ( file.startsWith( 'react-jsx-runtime' ) ) { + const srcFile = path.join( src, file ); + const destFile = path.join( dest, file ); + fs.mkdirSync( dest, { recursive: true } ); + + if ( + file.endsWith( '.js' ) && + ! file.endsWith( '.js.map' ) + ) { + let content = fs.readFileSync( + srcFile, + 'utf8' + ); + content = removeSourceMaps( content ); + fs.writeFileSync( destFile, content ); + } else { + fs.copyFileSync( srcFile, destFile ); + } + copiedCount++; + } + } + console.log( + ` ✅ ${ entry.name }/ → ${ destName }/ (react-jsx-runtime only, ${ copiedCount } files)` + ); + } else { + // Copy other special directories normally + copyDirectory( src, dest, removeSourceMaps ); + console.log( + ` ✅ ${ entry.name }/ → ${ destName }/` + ); + } + } else { + // Flatten package structure: package-name/index.js → package-name.js + // This matches Core's expected file structure + const packageFiles = fs.readdirSync( src ); + + for ( const file of packageFiles ) { + if ( + /^index\.(js|js\.map|min\.js|min\.js\.map|min\.asset\.php)$/.test( + file + ) + ) { + const srcFile = path.join( src, file ); + // Replace 'index.' with 'package-name.' + const destFile = file.replace( + /^index\./, + `${ entry.name }.` + ); + const destPath = path.join( scriptsDest, destFile ); + + fs.mkdirSync( path.dirname( destPath ), { + recursive: true, + } ); + + // Apply source map removal for .js files + if ( + file.endsWith( '.js' ) && + ! file.endsWith( '.js.map' ) + ) { + let content = fs.readFileSync( + srcFile, + 'utf8' + ); + content = removeSourceMaps( content ); + fs.writeFileSync( destPath, content ); + } else { + // Copy other files as-is + fs.copyFileSync( srcFile, destPath ); + } + } + } + } + } else if ( + entry.isFile() && + /\.(js|js\.map)$/.test( entry.name ) + ) { + // Copy root-level JS files + const dest = path.join( scriptsDest, entry.name ); + fs.mkdirSync( path.dirname( dest ), { recursive: true } ); + + if ( + entry.name.endsWith( '.js' ) && + ! entry.name.endsWith( '.js.map' ) + ) { + let content = fs.readFileSync( src, 'utf8' ); + content = removeSourceMaps( content ); + fs.writeFileSync( dest, content ); + } else { + fs.copyFileSync( src, dest ); + } + } + } + + console.log( ' ✅ JavaScript packages copied' ); + } + + // 3. Copy script modules + console.log( '\n📦 Copying script modules...' ); + const modulesConfig = COPY_CONFIG.modules; + const modulesSrc = path.join( gutenbergBuildDir, modulesConfig.source ); + const modulesDest = path.join( wpIncludesDir, modulesConfig.destination ); + + if ( fs.existsSync( modulesSrc ) ) { + // Use the same source map removal transform + copyDirectory( modulesSrc, modulesDest, removeSourceMaps ); + console.log( ' ✅ Script modules copied' ); + } + + // 4. Copy styles + console.log( '\n📦 Copying styles...' ); + const stylesConfig = COPY_CONFIG.styles; + const stylesSrc = path.join( gutenbergBuildDir, stylesConfig.source ); + const stylesDest = path.join( wpIncludesDir, stylesConfig.destination ); + + if ( fs.existsSync( stylesSrc ) ) { + copyDirectory( stylesSrc, stylesDest ); + console.log( ' ✅ Styles copied' ); + } + + // 5. Copy blocks (unified: scripts, styles, PHP, JSON) + console.log( '\n📦 Copying blocks...' ); + const blocksDest = path.join( + wpIncludesDir, + COPY_CONFIG.blocks.destination + ); + copyBlockAssets( COPY_CONFIG.blocks ); + + // 6. Copy non-block PHP source files (from packages) + console.log( '\n📦 Copying non-block PHP files...' ); + const phpSourceConfig = COPY_CONFIG.phpSource; + + for ( const fileGroup of phpSourceConfig.files ) { + const packageSrc = path.join( gutenbergPackagesDir, fileGroup.package ); + + if ( ! fs.existsSync( packageSrc ) ) { + console.log( ` ⚠️ Package not found: ${ fileGroup.package }` ); + continue; + } + + for ( const file of fileGroup.files ) { + const src = path.join( packageSrc, file ); + const dest = path.join( + wpIncludesDir, + fileGroup.destination, + file + ); + + if ( fs.existsSync( src ) ) { + fs.mkdirSync( path.dirname( dest ), { recursive: true } ); + let content = fs.readFileSync( src, 'utf8' ); + fs.writeFileSync( dest, content ); + } + } + console.log( + ` ✅ ${ fileGroup.package } (${ fileGroup.files.length } files)` + ); + } + + // 7. Copy theme JSON files (from Gutenberg lib directory) + console.log( '\n📦 Copying theme JSON files...' ); + const themeJsonConfig = COPY_CONFIG.themeJson; + const gutenbergLibDir = path.join( gutenbergDir, 'lib' ); + + for ( const fileMap of themeJsonConfig.files ) { + const src = path.join( gutenbergLibDir, fileMap.from ); + const dest = path.join( wpIncludesDir, fileMap.to ); + + if ( fs.existsSync( src ) ) { + let content = fs.readFileSync( src, 'utf8' ); + + if ( themeJsonConfig.transform && fileMap.from === 'theme.json' ) { + // Transform schema URL for Core + content = content.replace( + '"$schema": "../schemas/json/theme.json"', + '"$schema": "https://schemas.wp.org/trunk/theme.json"' + ); + } + + fs.writeFileSync( dest, content ); + console.log( ` ✅ ${ fileMap.to }` ); + } else { + console.log( ` ⚠️ Not found: ${ fileMap.from }` ); + } + } + + // 9. Generate script-modules-packages.min.php from individual asset files + console.log( '\n📦 Generating script-modules-packages.min.php...' ); + generateScriptModulesPackages(); + + // 10. Generate script-loader-packages.min.php + console.log( '\n📦 Generating script-loader-packages.min.php...' ); + generateScriptLoaderPackages(); + + // 11. Generate require-dynamic-blocks.php and require-static-blocks.php + console.log( '\n📦 Generating block registration files...' ); + generateBlockRegistrationFiles(); + + // 12. Generate blocks-json.php from block.json files + console.log( '\n📦 Generating blocks-json.php...' ); + generateBlocksJson(); + + // Summary + console.log( '\n✅ Copy complete!' ); + console.log( '\n📊 Summary:' ); + console.log( ` PHP infrastructure: ${ phpDest }` ); + console.log( ` JavaScript: ${ scriptsDest }` ); + console.log( ` Script modules: ${ modulesDest }` ); + console.log( ` Styles: ${ stylesDest }` ); + console.log( ` Blocks: ${ blocksDest }` ); +} + +// Run main function +main().catch( ( error ) => { + console.error( '❌ Unexpected error:', error ); + process.exit( 1 ); +} ); diff --git a/tools/vendors/copy-vendors.js b/tools/vendors/copy-vendors.js new file mode 100644 index 0000000000000..12660fc639645 --- /dev/null +++ b/tools/vendors/copy-vendors.js @@ -0,0 +1,185 @@ +#!/usr/bin/env node + +/** + * Copy Vendor Scripts + * + * This script copies vendor dependencies from node_modules to wp-includes/js/dist/vendor/. + * These are Core's own dependencies (moment, lodash, regenerator-runtime, polyfills, etc.) + * separate from Gutenberg packages. + * + * @package WordPress + */ + +const fs = require( 'fs' ); +const path = require( 'path' ); + +// Paths +const rootDir = path.resolve( __dirname, '../..' ); +const nodeModulesDir = path.join( rootDir, 'node_modules' ); + +// Parse command line arguments +const args = process.argv.slice( 2 ); +const buildDirArg = args.find( arg => arg.startsWith( '--build-dir=' ) ); +const buildTarget = buildDirArg + ? buildDirArg.split( '=' )[1] + : ( args.includes( '--dev' ) ? 'src' : 'build' ); + +const vendorDir = path.join( rootDir, buildTarget, 'wp-includes/js/dist/vendor' ); + +/** + * Vendor files to copy from node_modules. + */ +const VENDOR_FILES = { + // Moment.js + 'moment': { + files: [ + { from: 'moment/moment.js', to: 'moment.js' }, + { from: 'moment/min/moment.min.js', to: 'moment.min.js' }, + ], + }, + + // Lodash + 'lodash': { + files: [ + { from: 'lodash/lodash.js', to: 'lodash.js' }, + { from: 'lodash/lodash.min.js', to: 'lodash.min.js' }, + ], + }, + + // Regenerator Runtime + 'regenerator-runtime': { + files: [ + { from: 'regenerator-runtime/runtime.js', to: 'regenerator-runtime.js' }, + { from: 'regenerator-runtime/runtime.js', to: 'regenerator-runtime.min.js' }, + ], + }, + + // React (UMD builds from node_modules) + 'react': { + files: [ + { from: 'react/umd/react.development.js', to: 'react.js' }, + { from: 'react/umd/react.production.min.js', to: 'react.min.js' }, + ], + }, + + // React DOM (UMD builds from node_modules) + 'react-dom': { + files: [ + { from: 'react-dom/umd/react-dom.development.js', to: 'react-dom.js' }, + { from: 'react-dom/umd/react-dom.production.min.js', to: 'react-dom.min.js' }, + ], + }, + + // Main Polyfill bundle + 'wp-polyfill': { + files: [ + { from: '@wordpress/babel-preset-default/build/polyfill.js', to: 'wp-polyfill.js' }, + { from: '@wordpress/babel-preset-default/build/polyfill.min.js', to: 'wp-polyfill.min.js' }, + ], + }, + + // Polyfills - Fetch (same source for both - was minified by webpack) + 'wp-polyfill-fetch': { + files: [ + { from: 'whatwg-fetch/dist/fetch.umd.js', to: 'wp-polyfill-fetch.js' }, + { from: 'whatwg-fetch/dist/fetch.umd.js', to: 'wp-polyfill-fetch.min.js' }, + ], + }, + + // Polyfills - FormData + 'wp-polyfill-formdata': { + files: [ + { from: 'formdata-polyfill/FormData.js', to: 'wp-polyfill-formdata.js' }, + { from: 'formdata-polyfill/formdata.min.js', to: 'wp-polyfill-formdata.min.js' }, + ], + }, + + // Polyfills - Element Closest (same for both) + 'wp-polyfill-element-closest': { + files: [ + { from: 'element-closest/browser.js', to: 'wp-polyfill-element-closest.js' }, + { from: 'element-closest/browser.js', to: 'wp-polyfill-element-closest.min.js' }, + ], + }, + + // Polyfills - Object Fit + 'wp-polyfill-object-fit': { + files: [ + { from: 'objectFitPolyfill/src/objectFitPolyfill.js', to: 'wp-polyfill-object-fit.js' }, + { from: 'objectFitPolyfill/dist/objectFitPolyfill.min.js', to: 'wp-polyfill-object-fit.min.js' }, + ], + }, + + // Polyfills - Inert + 'wp-polyfill-inert': { + files: [ + { from: 'wicg-inert/dist/inert.js', to: 'wp-polyfill-inert.js' }, + { from: 'wicg-inert/dist/inert.min.js', to: 'wp-polyfill-inert.min.js' }, + ], + }, + + // Polyfills - URL + 'wp-polyfill-url': { + files: [ + { from: 'core-js-url-browser/url.js', to: 'wp-polyfill-url.js' }, + { from: 'core-js-url-browser/url.min.js', to: 'wp-polyfill-url.min.js' }, + ], + }, + + // Polyfills - DOMRect (same source for both - was minified by webpack) + 'wp-polyfill-dom-rect': { + files: [ + { from: 'polyfill-library/polyfills/__dist/DOMRect/raw.js', to: 'wp-polyfill-dom-rect.js' }, + { from: 'polyfill-library/polyfills/__dist/DOMRect/raw.js', to: 'wp-polyfill-dom-rect.min.js' }, + ], + }, + + // Polyfills - Node.contains (same source for both - was minified by webpack) + 'wp-polyfill-node-contains': { + files: [ + { from: 'polyfill-library/polyfills/__dist/Node.prototype.contains/raw.js', to: 'wp-polyfill-node-contains.js' }, + { from: 'polyfill-library/polyfills/__dist/Node.prototype.contains/raw.js', to: 'wp-polyfill-node-contains.min.js' }, + ], + }, +}; + +/** + * Main execution function. + */ +async function main() { + console.log( '📦 Copying vendor scripts from node_modules...' ); + console.log( ` Build target: ${ buildTarget }/` ); + + // Create vendor directory + fs.mkdirSync( vendorDir, { recursive: true } ); + + let copied = 0; + let skipped = 0; + + for ( const [ vendor, config ] of Object.entries( VENDOR_FILES ) ) { + for ( const file of config.files ) { + const srcPath = path.join( nodeModulesDir, file.from ); + const destPath = path.join( vendorDir, file.to ); + + if ( fs.existsSync( srcPath ) ) { + fs.copyFileSync( srcPath, destPath ); + copied++; + } else { + console.log( ` ⚠️ Skipping ${ file.to }: source not found` ); + skipped++; + } + } + } + + console.log( `\n✅ Vendor scripts copied!` ); + console.log( ` Copied: ${ copied } files` ); + if ( skipped > 0 ) { + console.log( ` Skipped: ${ skipped } files` ); + } +} + +// Run main function +main().catch( ( error ) => { + console.error( '❌ Unexpected error:', error ); + process.exit( 1 ); +} ); diff --git a/tools/webpack/blocks.js b/tools/webpack/blocks.js deleted file mode 100644 index f1c9d20cd8504..0000000000000 --- a/tools/webpack/blocks.js +++ /dev/null @@ -1,146 +0,0 @@ -/** - * External dependencies - */ -const CopyWebpackPlugin = require( 'copy-webpack-plugin' ); - -/** - * Internal dependencies - */ -const { - baseDir, - getBaseConfig, - normalizeJoin, - stylesTransform, -} = require( './shared' ); -const { - isDynamic, - toDirectoryName, - getStableBlocksMetadata, -} = require( '../release/sync-stable-blocks' ); - -module.exports = function ( - env = { environment: 'production', watch: false, buildTarget: false } -) { - const mode = env.environment; - const suffix = mode === 'production' ? '.min' : ''; - let buildTarget = env.buildTarget - ? env.buildTarget - : mode === 'production' - ? 'build' - : 'src'; - buildTarget = buildTarget + '/wp-includes'; - - const blocks = getStableBlocksMetadata(); - const dynamicBlockFolders = blocks - .filter( isDynamic ) - .map( toDirectoryName ); - const blockFolders = blocks.map( toDirectoryName ); - const blockPHPFiles = { - 'widgets/src/blocks/legacy-widget/index.php': - 'wp-includes/blocks/legacy-widget.php', - 'widgets/src/blocks/widget-group/index.php': - 'wp-includes/blocks/widget-group.php', - ...dynamicBlockFolders.reduce( ( files, blockName ) => { - files[ - `block-library/src/${ blockName }/index.php` - ] = `wp-includes/blocks/${ blockName }.php`; - return files; - }, {} ), - }; - const blockMetadataFiles = { - 'widgets/src/blocks/legacy-widget/block.json': - 'wp-includes/blocks/legacy-widget/block.json', - 'widgets/src/blocks/widget-group/block.json': - 'wp-includes/blocks/widget-group/block.json', - ...blockFolders.reduce( ( files, blockName ) => { - files[ - `block-library/src/${ blockName }/block.json` - ] = `wp-includes/blocks/${ blockName }/block.json`; - return files; - }, {} ), - }; - - const blockPHPCopies = Object.keys( blockPHPFiles ).map( ( filename ) => ( { - from: normalizeJoin( baseDir, `node_modules/@wordpress/${ filename }` ), - to: normalizeJoin( baseDir, `src/${ blockPHPFiles[ filename ] }` ), - } ) ); - - const blockMetadataCopies = Object.keys( blockMetadataFiles ).map( - ( filename ) => ( { - from: normalizeJoin( - baseDir, - `node_modules/@wordpress/${ filename }` - ), - to: normalizeJoin( - baseDir, - `src/${ blockMetadataFiles[ filename ] }` - ), - } ) - ); - - const blockStylesheetCopies = blockFolders.map( ( blockName ) => ( { - from: normalizeJoin( - baseDir, - `node_modules/@wordpress/block-library/build-style/${ blockName }/*.css` - ), - to: normalizeJoin( - baseDir, - `${ buildTarget }/blocks/${ blockName }/[name]${ suffix }.css` - ), - transform: stylesTransform( mode ), - noErrorOnMissing: true, - } ) ); - - // Todo: This list need of entry points need to be automatically fetched from the package - // We shouldn't have to maintain it manually. - const interactiveBlocks = [ - 'navigation', - 'image', - 'query', - 'file', - 'search', - ]; - - const baseConfig = getBaseConfig( env ); - const config = { - ...baseConfig, - entry: interactiveBlocks.reduce(( memo, blockName ) => { - memo[ blockName ] = { - import: normalizeJoin( - baseDir, - `node_modules/@wordpress/block-library/build-module/${ blockName }/view` - ), - }; - return memo; - }, {}), - experiments: { - outputModule: true, - }, - output: { - devtoolNamespace: 'wp', - filename: `./blocks/[name]/view${ suffix }.js`, - path: normalizeJoin( baseDir, buildTarget ), - library: { - type: 'module', - }, - environment: { module: true }, - }, - externalsType: 'module', - externals: { - '@wordpress/interactivity': '@wordpress/interactivity', - '@wordpress/interactivity-router': 'import @wordpress/interactivity-router', - }, - plugins: [ - ...baseConfig.plugins, - new CopyWebpackPlugin( { - patterns: [ - ...blockPHPCopies, - ...blockMetadataCopies, - ...blockStylesheetCopies, - ], - } ), - ], - }; - - return config; -}; diff --git a/tools/webpack/development.js b/tools/webpack/development.js deleted file mode 100644 index 316c5bc4f72b5..0000000000000 --- a/tools/webpack/development.js +++ /dev/null @@ -1,61 +0,0 @@ -/** - * External dependencies - */ -const { join } = require( 'path' ); - -/** - * WordPress dependencies - */ -const DependencyExtractionWebpackPlugin = require( '@wordpress/dependency-extraction-webpack-plugin' ); - -const baseDir = join( __dirname, '../../' ); - -module.exports = function( env = { environment: 'production', buildTarget: false } ) { - const mode = env.environment; - const suffix = mode === 'production' ? '.min' : ''; - let buildTarget = env.buildTarget ? env.buildTarget : ( mode === 'production' ? 'build' : 'src' ); - buildTarget = buildTarget + '/wp-includes'; - - const sharedConfig = { - mode: 'development', - target: 'browserslist', - output: { - filename: `[name]${ suffix }.js`, - path: join( baseDir, `${ buildTarget }/js/dist/development` ), - }, - }; - - // See https://github.com/pmmmwh/react-refresh-webpack-plugin/blob/main/docs/TROUBLESHOOTING.md#externalising-react. - return [ - { - ...sharedConfig, - name: 'react-refresh-entry', - entry: { - 'react-refresh-entry': - '@pmmmwh/react-refresh-webpack-plugin/client/ReactRefreshEntry.js', - }, - plugins: [ new DependencyExtractionWebpackPlugin( { - outputFilename: `../../../assets/script-loader-[name]${ suffix }.php`, - } ) ], - }, - { - ...sharedConfig, - name: 'react-refresh-runtime', - entry: { - 'react-refresh-runtime': { - import: 'react-refresh/runtime', - library: { - name: 'ReactRefreshRuntime', - type: 'window', - }, - }, - }, - plugins: [ - new DependencyExtractionWebpackPlugin( { - useDefaults: false, - outputFilename: `../../../assets/script-loader-[name]${ suffix }.php` - } ), - ], - }, - ]; -}; diff --git a/tools/webpack/packages.js b/tools/webpack/packages.js deleted file mode 100644 index f431d43b682ee..0000000000000 --- a/tools/webpack/packages.js +++ /dev/null @@ -1,218 +0,0 @@ -/** - * External dependencies - */ -const CopyWebpackPlugin = require( 'copy-webpack-plugin' ); -const LiveReloadPlugin = require( 'webpack-livereload-plugin' ); -const UglifyJS = require( 'uglify-js' ); - -/** - * WordPress dependencies - */ -const { - camelCaseDash, -} = require( '@wordpress/dependency-extraction-webpack-plugin/lib/util' ); -const DependencyExtractionPlugin = require( '@wordpress/dependency-extraction-webpack-plugin' ); - -/** - * Internal dependencies - */ -const { - baseDir, - getBaseConfig, - normalizeJoin, - stylesTransform, - BUNDLED_PACKAGES, - MODULES, - WORDPRESS_NAMESPACE, -} = require( './shared' ); -const { dependencies } = require( '../../package' ); - -const exportDefaultPackages = [ - 'api-fetch', - 'deprecated', - 'dom-ready', - 'redux-routine', - 'token-list', - 'server-side-render', - 'shortcode', - 'warning', -]; - -/** - * Maps vendors to copy commands for the CopyWebpackPlugin. - * - * @param {Object} vendors Vendors to include in the vendor folder. - * @param {string} buildTarget The folder in which to build the packages. - * - * @return {Object[]} Copy object suitable for the CopyWebpackPlugin. - */ -function mapVendorCopies( vendors, buildTarget ) { - return Object.keys( vendors ).map( ( filename ) => ( { - from: normalizeJoin( baseDir, `node_modules/${ vendors[ filename ] }` ), - to: normalizeJoin( - baseDir, - `${ buildTarget }/js/dist/vendor/${ filename }` - ), - } ) ); -} - -module.exports = function ( - env = { environment: 'production', watch: false, buildTarget: false } -) { - const mode = env.environment; - const suffix = mode === 'production' ? '.min' : ''; - let buildTarget = env.buildTarget - ? env.buildTarget - : mode === 'production' - ? 'build' - : 'src'; - buildTarget = buildTarget + '/wp-includes'; - - const packages = Object.keys( dependencies ) - .filter( - ( packageName ) => - ! BUNDLED_PACKAGES.includes( packageName ) && - ! MODULES.includes( packageName ) && - packageName.startsWith( WORDPRESS_NAMESPACE ) - ) - .map( ( packageName ) => - packageName.replace( WORDPRESS_NAMESPACE, '' ) - ); - - const vendors = { - 'lodash.js': 'lodash/lodash.js', - 'wp-polyfill.js': '@wordpress/babel-preset-default/build/polyfill.js', - 'wp-polyfill-fetch.js': 'whatwg-fetch/dist/fetch.umd.js', - 'wp-polyfill-element-closest.js': 'element-closest/browser.js', - 'wp-polyfill-node-contains.js': - 'polyfill-library/polyfills/__dist/Node.prototype.contains/raw.js', - 'wp-polyfill-url.js': 'core-js-url-browser/url.js', - 'wp-polyfill-dom-rect.js': - 'polyfill-library/polyfills/__dist/DOMRect/raw.js', - 'wp-polyfill-formdata.js': 'formdata-polyfill/FormData.js', - 'wp-polyfill-object-fit.js': - 'objectFitPolyfill/src/objectFitPolyfill.js', - 'wp-polyfill-inert.js': 'wicg-inert/dist/inert.js', - 'moment.js': 'moment/moment.js', - 'regenerator-runtime.js': 'regenerator-runtime/runtime.js', - 'react.js': 'react/umd/react.development.js', - 'react-dom.js': 'react-dom/umd/react-dom.development.js', - }; - - const minifiedVendors = { - 'lodash.min.js': 'lodash/lodash.min.js', - 'wp-polyfill.min.js': - '@wordpress/babel-preset-default/build/polyfill.min.js', - 'wp-polyfill-element-closest.min.js': 'element-closest/browser.js', - 'wp-polyfill-formdata.min.js': 'formdata-polyfill/formdata.min.js', - 'wp-polyfill-url.min.js': 'core-js-url-browser/url.min.js', - 'wp-polyfill-object-fit.min.js': - 'objectFitPolyfill/dist/objectFitPolyfill.min.js', - 'wp-polyfill-inert.min.js': 'wicg-inert/dist/inert.min.js', - 'moment.min.js': 'moment/min/moment.min.js', - 'react.min.js': 'react/umd/react.production.min.js', - 'react-dom.min.js': 'react-dom/umd/react-dom.production.min.js', - }; - - const minifyVendors = { - 'regenerator-runtime.min.js': 'regenerator-runtime/runtime.js', - 'wp-polyfill-fetch.min.js': 'whatwg-fetch/dist/fetch.umd.js', - 'wp-polyfill-node-contains.min.js': - 'polyfill-library/polyfills/__dist/Node.prototype.contains/raw.js', - 'wp-polyfill-dom-rect.min.js': - 'polyfill-library/polyfills/__dist/DOMRect/raw.js', - }; - - const phpFiles = { - 'block-serialization-default-parser/class-wp-block-parser.php': - 'wp-includes/class-wp-block-parser.php', - 'block-serialization-default-parser/class-wp-block-parser-frame.php': - 'wp-includes/class-wp-block-parser-frame.php', - 'block-serialization-default-parser/class-wp-block-parser-block.php': - 'wp-includes/class-wp-block-parser-block.php', - }; - - const developmentCopies = mapVendorCopies( vendors, buildTarget ); - const minifiedCopies = mapVendorCopies( minifiedVendors, buildTarget ); - const minifyCopies = mapVendorCopies( minifyVendors, buildTarget ).map( - ( copyCommand ) => { - return { - ...copyCommand, - transform: ( content ) => { - return UglifyJS.minify( content.toString() ).code; - }, - }; - } - ); - - let vendorCopies = - mode === 'development' - ? developmentCopies - : [ ...minifiedCopies, ...minifyCopies ]; - - let cssCopies = packages.map( ( packageName ) => ( { - from: normalizeJoin( - baseDir, - `node_modules/@wordpress/${ packageName }/build-style/*.css` - ), - to: normalizeJoin( - baseDir, - `${ buildTarget }/css/dist/${ packageName }/[name]${ suffix }.css` - ), - transform: stylesTransform( mode ), - noErrorOnMissing: true, - } ) ); - - const phpCopies = Object.keys( phpFiles ).map( ( filename ) => ( { - from: normalizeJoin( baseDir, `node_modules/@wordpress/${ filename }` ), - to: normalizeJoin( baseDir, `src/${ phpFiles[ filename ] }` ), - } ) ); - - const baseConfig = getBaseConfig( env ); - const config = { - ...baseConfig, - entry: packages.reduce( ( memo, packageName ) => { - memo[ packageName ] = { - import: normalizeJoin( - baseDir, - `node_modules/@wordpress/${ packageName }` - ), - library: { - name: [ 'wp', camelCaseDash( packageName ) ], - type: 'window', - export: exportDefaultPackages.includes( packageName ) - ? 'default' - : undefined, - }, - }; - - return memo; - }, {} ), - output: { - devtoolNamespace: 'wp', - filename: `[name]${ suffix }.js`, - path: normalizeJoin( baseDir, `${ buildTarget }/js/dist` ), - }, - plugins: [ - ...baseConfig.plugins, - new DependencyExtractionPlugin( { - injectPolyfill: false, - combineAssets: true, - combinedOutputFile: `../../assets/script-loader-packages${ suffix }.php`, - } ), - new CopyWebpackPlugin( { - patterns: [ ...vendorCopies, ...cssCopies, ...phpCopies ], - } ), - ], - }; - - if ( config.mode === 'development' ) { - config.plugins.push( - new LiveReloadPlugin( { - port: process.env.WORDPRESS_LIVE_RELOAD_PORT || 35729, - } ) - ); - } - - return config; -}; diff --git a/tools/webpack/script-modules.js b/tools/webpack/script-modules.js deleted file mode 100644 index 2c8ae75d01423..0000000000000 --- a/tools/webpack/script-modules.js +++ /dev/null @@ -1,126 +0,0 @@ -/** - * External dependencies - */ -const { createRequire } = require( 'node:module' ); -const { dirname } = require( 'node:path' ); - -/** - * WordPress dependencies - */ -const DependencyExtractionPlugin = require( '@wordpress/dependency-extraction-webpack-plugin' ); - -/** - * Internal dependencies - */ -const { - baseDir, - getBaseConfig, - normalizeJoin, - MODULES, - SCRIPT_AND_MODULE_DUAL_PACKAGES, - WORDPRESS_NAMESPACE, -} = require( './shared' ); - -/** @type {Map} */ -const scriptModules = new Map(); -for ( const packageName of MODULES.concat( SCRIPT_AND_MODULE_DUAL_PACKAGES ) ) { - const packageRequire = createRequire( - `${ dirname( require.resolve( `${ packageName }/package.json` ) ) }/` - ); - - const depPackageJson = packageRequire( './package.json' ); - if ( ! Object.hasOwn( depPackageJson, 'wpScriptModuleExports' ) ) { - continue; - } - - const moduleName = packageName.substring( WORDPRESS_NAMESPACE.length ); - let { wpScriptModuleExports } = depPackageJson; - - // Special handling for { "wpScriptModuleExports": "./build-module/index.js" }. - if ( typeof wpScriptModuleExports === 'string' ) { - wpScriptModuleExports = { '.': wpScriptModuleExports }; - } - - if ( Object.getPrototypeOf( wpScriptModuleExports ) !== Object.prototype ) { - throw new Error( 'wpScriptModuleExports must be an object' ); - } - - for ( const [ exportName, exportPath ] of Object.entries( - wpScriptModuleExports - ) ) { - // Exclude the experimental './full-page' export from @wordpress/interactivity-router. - // This export is defined in Gutenberg's package.json but should not be bundled in Core - // as the feature is still experimental and not ready for inclusion. - if ( moduleName === 'interactivity-router' && exportName === './full-page' ) { - continue; - } - - if ( typeof exportPath !== 'string' ) { - throw new Error( 'wpScriptModuleExports paths must be strings' ); - } - - if ( ! exportPath.startsWith( './' ) ) { - throw new Error( - 'wpScriptModuleExports paths must start with "./"' - ); - } - - const name = - exportName === '.' ? 'index' : exportName.replace( /^\.\/?/, '' ); - - scriptModules.set( - `${ moduleName }/${ name }`, - packageRequire.resolve( exportPath ) - ); - } -} - -module.exports = function ( - env = { environment: 'production', watch: false, buildTarget: false } -) { - const mode = env.environment; - const suffix = mode === 'production' ? '.min' : ''; - let buildTarget = env.buildTarget - ? env.buildTarget - : mode === 'production' - ? 'build' - : 'src'; - buildTarget = buildTarget + '/wp-includes'; - - const baseConfig = getBaseConfig( env ); - const config = { - ...baseConfig, - entry: Object.fromEntries( scriptModules.entries() ), - experiments: { - outputModule: true, - }, - output: { - devtoolNamespace: 'wp', - filename: `[name]${ suffix }.js`, - path: normalizeJoin( - baseDir, - `${ buildTarget }/js/dist/script-modules` - ), - library: { - type: 'module', - }, - environment: { module: true }, - module: true, - chunkFormat: 'module', - asyncChunks: false, - }, - plugins: [ - ...baseConfig.plugins, - new DependencyExtractionPlugin( { - injectPolyfill: false, - combineAssets: true, - combinedOutputFile: normalizeJoin( - baseDir, - `${ buildTarget }/assets/script-modules-packages${ suffix }.php` - ), - } ), - ], - }; - - return config; -}; diff --git a/tools/webpack/vendors.js b/tools/webpack/vendors.js deleted file mode 100644 index 1c1f0a187a176..0000000000000 --- a/tools/webpack/vendors.js +++ /dev/null @@ -1,53 +0,0 @@ -/** - * External dependencies - */ -const { join } = require( 'path' ); - -const importedVendors = { - 'react-jsx-runtime': { - import: 'react/jsx-runtime', - global: 'ReactJSXRuntime', - }, -}; - -module.exports = function ( - env = { environment: 'production', watch: false, buildTarget: false } -) { - const mode = env.environment; - let buildTarget = env.buildTarget - ? env.buildTarget - : mode === 'production' - ? 'build' - : 'src'; - buildTarget = buildTarget + '/wp-includes/js/dist/vendor/'; - return [ - ...Object.entries( importedVendors ).flatMap( ( [ name, config ] ) => { - return [ 'production', 'development' ].map( ( currentMode ) => { - return { - mode: currentMode, - target: 'browserslist', - output: { - filename: - currentMode === 'development' - ? `[name].js` - : `[name].min.js`, - path: join( __dirname, '..', '..', buildTarget ), - }, - entry: { - [ name ]: { - import: config.import, - library: { - name: config.global, - type: 'window', - }, - }, - }, - - externals: { - react: 'React', - }, - }; - } ); - } ), - ]; -}; diff --git a/webpack.config.js b/webpack.config.js index 53ef8bd9ac4d9..089c2d67dabec 100644 --- a/webpack.config.js +++ b/webpack.config.js @@ -1,27 +1,20 @@ -const blocksConfig = require( './tools/webpack/blocks' ); -const developmentConfig = require( './tools/webpack/development' ); const mediaConfig = require( './tools/webpack/media' ); -const packagesConfig = require( './tools/webpack/packages' ); -const scriptModulesConfig = require( './tools/webpack/script-modules' ); -const vendorsConfig = require( './tools/webpack/vendors' ); -module.exports = function( env = { environment: "production", watch: false, buildTarget: false } ) { +module.exports = function ( + env = { environment: 'production', watch: false, buildTarget: false } +) { if ( ! env.watch ) { env.watch = false; } if ( ! env.buildTarget ) { - env.buildTarget = ( env.mode === 'production' ? 'build/' : 'src/' ); + env.buildTarget = env.mode === 'production' ? 'build/' : 'src/'; } - const config = [ - blocksConfig( env ), - ...developmentConfig( env ), - mediaConfig( env ), - packagesConfig( env ), - scriptModulesConfig( env ), - ...vendorsConfig( env ), - ]; + // Only building Core-specific media files. + // Blocks, packages, script modules, and vendors are now sourced from + // the Gutenberg build (see tools/gutenberg/copy-gutenberg-build.js). + const config = [ mediaConfig( env ) ]; return config; }; From 3a99c943be586066dcdec891bfdc8b8c223bfc71 Mon Sep 17 00:00:00 2001 From: Riad Benguella Date: Mon, 5 Jan 2026 13:34:12 +0000 Subject: [PATCH 088/126] Build/Test Tools: Fix Gutenberg integration script prefixes and theme-i18n.json handling. This changeset addresses two issues in the Gutenberg integration workflow: * Sets `wpPlugin.name` to `wp` in `build-gutenberg.js` so generated PHP files use `wp_` prefixes instead of `gutenberg_`. * Persists `theme-i18n.json` in the repository for WP-CLI compatibility, as this file is required but was being ignored. Props youknowriad, swissspidy. See #64393. git-svn-id: https://develop.svn.wordpress.org/trunk@61439 602fd350-edb4-49c9-b593-d223f7449a82 --- .gitignore | 1 - src/wp-includes/theme-i18n.json | 137 +++++++++++++++++++++++++++++ tools/gutenberg/build-gutenberg.js | 5 ++ 3 files changed, 142 insertions(+), 1 deletion(-) create mode 100644 src/wp-includes/theme-i18n.json diff --git a/.gitignore b/.gitignore index f0e39849ee5df..901a775c5af23 100644 --- a/.gitignore +++ b/.gitignore @@ -42,7 +42,6 @@ wp-tests-config.php /src/wp-includes/class-wp-block-parser-block.php /src/wp-includes/class-wp-block-parser-frame.php /src/wp-includes/theme.json -/src/wp-includes/theme-i18n.json /packagehash.txt /artifacts /setup.log diff --git a/src/wp-includes/theme-i18n.json b/src/wp-includes/theme-i18n.json new file mode 100644 index 0000000000000..b7f46688e7f91 --- /dev/null +++ b/src/wp-includes/theme-i18n.json @@ -0,0 +1,137 @@ +{ + "title": "Style variation name", + "description": "Style variation description", + "settings": { + "typography": { + "fontSizes": [ + { + "name": "Font size name" + } + ], + "fontFamilies": [ + { + "name": "Font family name" + } + ] + }, + "color": { + "palette": [ + { + "name": "Color name" + } + ], + "gradients": [ + { + "name": "Gradient name" + } + ], + "duotone": [ + { + "name": "Duotone name" + } + ] + }, + "spacing": { + "spacingSizes": [ + { + "name": "Space size name" + } + ] + }, + "dimensions": { + "aspectRatios": [ + { + "name": "Aspect ratio name" + } + ], + "dimensionSizes": [ + { + "name": "Dimension size name" + } + ] + }, + "shadow": { + "presets": [ + { + "name": "Shadow name" + } + ] + }, + "border": { + "radiusSizes": [ + { + "name": "Border radius size name" + } + ] + }, + "blocks": { + "*": { + "typography": { + "fontSizes": [ + { + "name": "Font size name" + } + ], + "fontFamilies": [ + { + "name": "Font family name" + } + ] + }, + "color": { + "palette": [ + { + "name": "Color name" + } + ], + "gradients": [ + { + "name": "Gradient name" + } + ], + "duotone": [ + { + "name": "Duotone name" + } + ] + }, + "dimensions": { + "aspectRatios": [ + { + "name": "Aspect ratio name" + } + ], + "dimensionSizes": [ + { + "name": "Dimension size name" + } + ] + }, + "spacing": { + "spacingSizes": [ + { + "name": "Space size name" + } + ] + }, + "border": { + "radiusSizes": [ + { + "name": "Border radius size name" + } + ] + } + } + } + }, + "customTemplates": [ + { + "title": "Custom template name" + } + ], + "templateParts": [ + { + "title": "Template part name" + } + ] +} diff --git a/tools/gutenberg/build-gutenberg.js b/tools/gutenberg/build-gutenberg.js index 344f1b58bed47..8ba2689e77dcf 100644 --- a/tools/gutenberg/build-gutenberg.js +++ b/tools/gutenberg/build-gutenberg.js @@ -114,6 +114,10 @@ async function main() { gutenbergPackageJson.config.IS_GUTENBERG_PLUGIN = false; gutenbergPackageJson.config.IS_WORDPRESS_CORE = true; + // Set wpPlugin.name for Core naming convention + gutenbergPackageJson.wpPlugin = gutenbergPackageJson.wpPlugin || {}; + gutenbergPackageJson.wpPlugin.name = 'wp'; + fs.writeFileSync( gutenbergPackageJsonPath, JSON.stringify( gutenbergPackageJson, null, '\t' ) + '\n' @@ -121,6 +125,7 @@ async function main() { console.log( ' ✅ IS_GUTENBERG_PLUGIN = false' ); console.log( ' ✅ IS_WORDPRESS_CORE = true' ); + console.log( ' ✅ wpPlugin.name = wp' ); } catch ( error ) { console.error( '❌ Error modifying Gutenberg package.json:', From 80ae9e6dab3c815635fa27b25a37a1c2ea2fa1f6 Mon Sep 17 00:00:00 2001 From: Jon Surrell Date: Mon, 5 Jan 2026 16:02:03 +0000 Subject: [PATCH 089/126] Scripts: Remove default attributes from tags. `SCRIPT`, `STYLE`, and stylesheet `LINK` tags do not require a type attribute since the HTML5 standard was released in 2008. Removing the type attribute simplifies logic and normalizes the produced HTML content. Developed in https://github.com/WordPress/wordpress-develop/pull/10664. Follow-up to [61411], [46164]. Props jonsurrell, sabernhardt, westonruter. Fixes #64428. See #59883, #64442. git-svn-id: https://develop.svn.wordpress.org/trunk@61440 602fd350-edb4-49c9-b593-d223f7449a82 --- src/readme.html | 2 +- src/wp-admin/admin-footer.php | 2 +- src/wp-admin/admin-header.php | 4 ++-- src/wp-admin/customize.php | 2 +- src/wp-admin/edit-form-advanced.php | 2 +- src/wp-admin/edit-form-comment.php | 2 +- src/wp-admin/edit-tag-form.php | 2 +- src/wp-admin/edit-tags.php | 2 +- src/wp-admin/export.php | 2 +- .../includes/class-bulk-upgrader-skin.php | 8 +++---- .../includes/class-custom-image-header.php | 4 ++-- .../includes/class-wp-internal-pointers.php | 2 +- src/wp-admin/includes/class-wp-list-table.php | 2 +- .../includes/class-wp-themes-list-table.php | 2 +- .../includes/class-wp-upgrader-skin.php | 4 ++-- src/wp-admin/includes/deprecated.php | 2 +- src/wp-admin/includes/media.php | 22 +++++++++---------- src/wp-admin/includes/meta-boxes.php | 2 +- src/wp-admin/includes/misc.php | 2 +- src/wp-admin/includes/ms.php | 4 ++-- src/wp-admin/includes/options.php | 4 ++-- src/wp-admin/includes/post.php | 2 +- src/wp-admin/includes/template.php | 8 +++---- src/wp-admin/includes/update-core.php | 2 +- src/wp-admin/install.php | 4 ++-- src/wp-admin/media-new.php | 2 +- src/wp-admin/network/site-users.php | 2 +- src/wp-admin/network/upgrade.php | 2 +- src/wp-admin/update-core.php | 4 ++-- src/wp-admin/user-edit.php | 4 ++-- .../themes/twentyeleven/functions.php | 2 +- .../twentyfifteen/js/customize-preview.js | 2 +- .../twentyfourteen/inc/custom-header.php | 2 +- .../twentysixteen/js/customize-preview.js | 2 +- src/wp-content/themes/twentyten/404.php | 2 +- .../twentythirteen/inc/custom-header.php | 2 +- .../themes/twentytwelve/inc/custom-header.php | 2 +- src/wp-includes/class-wp-editor.php | 10 ++++----- src/wp-includes/class-wp-embed.php | 2 +- src/wp-includes/script-loader.php | 2 +- src/wp-includes/theme-previews.php | 2 +- src/wp-includes/theme.php | 13 +++-------- 42 files changed, 72 insertions(+), 79 deletions(-) diff --git a/src/readme.html b/src/readme.html index e1528c1ac6cea..8696b0505a913 100644 --- a/src/readme.html +++ b/src/readme.html @@ -5,7 +5,7 @@ WordPress › ReadMe - +

      diff --git a/src/wp-admin/admin-footer.php b/src/wp-admin/admin-footer.php index c688f1a891738..abb020e046459 100644 --- a/src/wp-admin/admin-footer.php +++ b/src/wp-admin/admin-footer.php @@ -114,6 +114,6 @@ ?>

    - + diff --git a/src/wp-admin/admin-header.php b/src/wp-admin/admin-header.php index ea0245fdb119c..0c075d68272a0 100644 --- a/src/wp-admin/admin-header.php +++ b/src/wp-admin/admin-header.php @@ -101,7 +101,7 @@ $admin_body_class = preg_replace( '/[^a-z0-9_-]+/i', '-', $hook_suffix ); ?> - diff --git a/src/wp-admin/customize.php b/src/wp-admin/customize.php index 141fb93dc3198..1f1a9d38b1a9e 100644 --- a/src/wp-admin/customize.php +++ b/src/wp-admin/customize.php @@ -159,7 +159,7 @@ ?> <?php echo esc_html( $admin_title ); ?> - diff --git a/src/wp-admin/edit-form-advanced.php b/src/wp-admin/edit-form-advanced.php index a22acd74cc240..c5092029543db 100644 --- a/src/wp-admin/edit-form-advanced.php +++ b/src/wp-admin/edit-form-advanced.php @@ -769,7 +769,7 @@ ?> post_title ) : ?> - diff --git a/src/wp-admin/edit-form-comment.php b/src/wp-admin/edit-form-comment.php index 47b44ee31dee9..cb6ab78e8f968 100644 --- a/src/wp-admin/edit-form-comment.php +++ b/src/wp-admin/edit-form-comment.php @@ -283,7 +283,7 @@ - - - -'; + echo ''; } /** @@ -172,7 +172,7 @@ public function bulk_footer() { public function before( $title = '' ) { $this->in_loop = true; printf( '

    ' . $this->upgrader->strings['skin_before_update_header'] . '

    ', $title, $this->upgrader->update_current, $this->upgrader->update_count ); - echo ''; + echo ''; // This progress messages div gets moved via JavaScript when clicking on "More details.". echo '

    '; $this->flush_output(); @@ -200,7 +200,7 @@ public function after( $title = '' ) { ) ); - echo ''; + echo ''; } if ( $this->result && ! is_wp_error( $this->result ) ) { if ( ! $this->error ) { @@ -210,7 +210,7 @@ public function after( $title = '' ) { '

    '; } - echo ''; + echo ''; } $this->reset(); diff --git a/src/wp-admin/includes/class-custom-image-header.php b/src/wp-admin/includes/class-custom-image-header.php index e8a16e47dc80a..d6a5e823c8421 100644 --- a/src/wp-admin/includes/class-custom-image-header.php +++ b/src/wp-admin/includes/class-custom-image-header.php @@ -376,7 +376,7 @@ public function js_1() { } } ?> -\n", wp_json_encode( $args, JSON_HEX_TAG | JSON_UNESCAPED_SLASHES ) ); + printf( "\n", wp_json_encode( $args, JSON_HEX_TAG | JSON_UNESCAPED_SLASHES ) ); } } diff --git a/src/wp-admin/includes/class-wp-themes-list-table.php b/src/wp-admin/includes/class-wp-themes-list-table.php index d7c491bd1c79e..c8cdbab8e43dc 100644 --- a/src/wp-admin/includes/class-wp-themes-list-table.php +++ b/src/wp-admin/includes/class-wp-themes-list-table.php @@ -357,7 +357,7 @@ public function _js_vars( $extra_args = array() ) { $args = array_merge( $args, $extra_args ); } - printf( "\n", wp_json_encode( $args, JSON_HEX_TAG | JSON_UNESCAPED_SLASHES ) ); + printf( "\n", wp_json_encode( $args, JSON_HEX_TAG | JSON_UNESCAPED_SLASHES ) ); parent::_js_vars(); } } diff --git a/src/wp-admin/includes/class-wp-upgrader-skin.php b/src/wp-admin/includes/class-wp-upgrader-skin.php index a5c80fad6dde6..831da3aebae2a 100644 --- a/src/wp-admin/includes/class-wp-upgrader-skin.php +++ b/src/wp-admin/includes/class-wp-upgrader-skin.php @@ -245,7 +245,7 @@ protected function decrement_update_count( $type ) { } if ( defined( 'IFRAME_REQUEST' ) ) { - echo ''; } else { - echo ' @@ -550,7 +550,7 @@ function wp_iframe( $content_func, ...$args ) { } ?> - - + - @@ -2070,7 +2070,7 @@ function get_compat_media_markup( $attachment_id, $args = null ) { function media_upload_header() { $post_id = isset( $_REQUEST['post_id'] ) ? (int) $_REQUEST['post_id'] : 0; - echo ''; + echo ''; if ( empty( $_GET['chromeless'] ) ) { echo '
    '; @@ -2219,7 +2219,7 @@ function media_upload_form( $errors = null ) { $plupload_init = apply_filters( 'plupload_init', $plupload_init ); ?> - + var _wpColorScheme = ' . wp_json_encode( array( 'icons' => $icon_colors ), JSON_HEX_TAG | JSON_UNESCAPED_SLASHES ) . ";\n"; + echo '\n"; } /** diff --git a/src/wp-admin/includes/ms.php b/src/wp-admin/includes/ms.php index 10ed2e27692e0..bef197410bb83 100644 --- a/src/wp-admin/includes/ms.php +++ b/src/wp-admin/includes/ms.php @@ -847,7 +847,7 @@ function can_edit_network( $network_id ) { */ function _thickbox_path_admin_subfolder() { ?> - -\n", trim( $script ) ); + printf( "\n", trim( $script ) ); } /* diff --git a/src/wp-admin/includes/template.php b/src/wp-admin/includes/template.php index adb12bc24bf62..2eaf67454394e 100644 --- a/src/wp-admin/includes/template.php +++ b/src/wp-admin/includes/template.php @@ -2138,7 +2138,7 @@ function iframe_header( $title = '', $deprecated = false ) { - + - - + - diff --git a/src/wp-admin/network/site-users.php b/src/wp-admin/network/site-users.php index 723a938250f08..070a8472e473d 100644 --- a/src/wp-admin/network/site-users.php +++ b/src/wp-admin/network/site-users.php @@ -236,7 +236,7 @@ require_once ABSPATH . 'wp-admin/admin-header.php'; ?> - diff --git a/src/wp-admin/network/upgrade.php b/src/wp-admin/network/upgrade.php index 79e40f45fbbc3..f4e65b2e9b5fe 100644 --- a/src/wp-admin/network/upgrade.php +++ b/src/wp-admin/network/upgrade.php @@ -124,7 +124,7 @@ } echo ''; ?>

    - diff --git a/src/wp-content/themes/twentythirteen/inc/custom-header.php b/src/wp-content/themes/twentythirteen/inc/custom-header.php index 6fb43f49c72d4..f293a46a46858 100644 --- a/src/wp-content/themes/twentythirteen/inc/custom-header.php +++ b/src/wp-content/themes/twentythirteen/inc/custom-header.php @@ -154,7 +154,7 @@ function twentythirteen_header_style() { function twentythirteen_admin_header_style() { $header_image = get_header_image(); ?> - ', $type_attr ); + echo ''; } return; } @@ -1951,7 +1949,7 @@ function _custom_background_cb() { $style .= $image . $position . $size . $repeat . $attachment; } - $processor = new WP_HTML_Tag_Processor( "" ); + $processor = new WP_HTML_Tag_Processor( '' ); $processor->next_tag(); $style_tag_content = 'body.custom-background { ' . trim( $style ) . ' }'; @@ -1972,9 +1970,6 @@ function wp_custom_css_cb() { $processor = new WP_HTML_Tag_Processor( '' ); $processor->next_tag(); - if ( ! current_theme_supports( 'html5', 'style' ) ) { - $processor->set_attribute( 'type', 'text/css' ); - } $processor->set_attribute( 'id', 'wp-custom-css' ); $processor->set_modifiable_text( "\n{$styles}\n" ); echo "{$processor->get_updated_html()}\n"; @@ -3006,11 +3001,9 @@ function _custom_logo_header_styles() { $classes = (array) get_theme_support( 'custom-logo', 'header-text' ); $classes = array_map( 'sanitize_html_class', $classes ); $classes = '.' . implode( ', .', $classes ); - - $type_attr = current_theme_supports( 'html5', 'style' ) ? '' : ' type="text/css"'; ?> - Date: Mon, 12 Jan 2026 12:18:12 +0000 Subject: [PATCH 122/126] Global Styles: Lift classic block restrictions. Enable Global Styles functionality in classic WordPress themes, allowing features like the Font Library to work without requiring a theme.json file. This change: - Removes restrictions that prevented classic themes from accessing Global Styles features. - Enables font functionality in classic themes through the Font Library. - Fixes Fonts menu not appearing in classic themes by changing its submenu index to avoid collision with Widgets. Props youknowriad, isabel_brison, ramonopoly. Fixes #64408. git-svn-id: https://develop.svn.wordpress.org/trunk@61473 602fd350-edb4-49c9-b593-d223f7449a82 --- src/wp-admin/menu.php | 2 +- src/wp-includes/block-editor.php | 59 +++++++--------- .../class-wp-theme-json-resolver.php | 11 --- src/wp-includes/class-wp-theme-json.php | 68 ++++++------------- .../global-styles-and-settings.php | 42 +++++------- src/wp-includes/script-loader.php | 56 ++++++++------- tests/phpunit/tests/template.php | 2 - tests/phpunit/tests/theme/wpThemeJson.php | 16 +++-- .../tests/theme/wpThemeJsonResolver.php | 22 +++--- 9 files changed, 115 insertions(+), 163 deletions(-) diff --git a/src/wp-admin/menu.php b/src/wp-admin/menu.php index c9187399cec7a..e544175d153b4 100644 --- a/src/wp-admin/menu.php +++ b/src/wp-admin/menu.php @@ -237,7 +237,7 @@ } // Font Library menu item. -$submenu['themes.php'][8] = array( __( 'Fonts' ), 'edit_theme_options', 'font-library.php' ); +$submenu['themes.php'][9] = array( __( 'Fonts' ), 'edit_theme_options', 'font-library.php' ); $customize_url = add_query_arg( 'return', urlencode( remove_query_arg( wp_removable_query_args(), wp_unslash( $_SERVER['REQUEST_URI'] ) ) ), 'customize.php' ); diff --git a/src/wp-includes/block-editor.php b/src/wp-includes/block-editor.php index 40575f048624e..af873178eb7aa 100644 --- a/src/wp-includes/block-editor.php +++ b/src/wp-includes/block-editor.php @@ -525,41 +525,34 @@ function get_block_editor_settings( array $custom_settings, $block_editor_contex } } - if ( wp_theme_has_theme_json() ) { - $block_classes = array( - 'css' => 'styles', - '__unstableType' => 'theme', - 'isGlobalStyles' => true, - ); - $actual_css = wp_get_global_stylesheet( array( $block_classes['css'] ) ); - if ( '' !== $actual_css ) { - $block_classes['css'] = $actual_css; - $global_styles[] = $block_classes; - } - - /* - * Add the custom CSS as a separate stylesheet so any invalid CSS - * entered by users does not break other global styles. - */ - $global_styles[] = array( - 'css' => wp_get_global_stylesheet( array( 'custom-css' ) ), - '__unstableType' => 'user', - 'isGlobalStyles' => true, - ); - } else { - // If there is no `theme.json` file, ensure base layout styles are still available. - $block_classes = array( - 'css' => 'base-layout-styles', - '__unstableType' => 'base-layout', - 'isGlobalStyles' => true, - ); - $actual_css = wp_get_global_stylesheet( array( $block_classes['css'] ) ); - if ( '' !== $actual_css ) { - $block_classes['css'] = $actual_css; - $global_styles[] = $block_classes; - } + $block_classes = array( + 'css' => 'styles', + '__unstableType' => 'theme', + 'isGlobalStyles' => true, + ); + $actual_css = wp_get_global_stylesheet( array( $block_classes['css'] ) ); + if ( '' !== $actual_css ) { + $block_classes['css'] = $actual_css; + $global_styles[] = $block_classes; } + // Get any additional css from the customizer and add it before global styles custom CSS. + $global_styles[] = array( + 'css' => wp_get_custom_css(), + '__unstableType' => 'user', + 'isGlobalStyles' => false, + ); + + /* + * Add the custom CSS as a separate stylesheet so any invalid CSS + * entered by users does not break other global styles. + */ + $global_styles[] = array( + 'css' => wp_get_global_stylesheet( array( 'custom-css' ) ), + '__unstableType' => 'user', + 'isGlobalStyles' => true, + ); + $editor_settings['styles'] = array_merge( $global_styles, get_block_editor_theme_styles() ); $editor_settings['__experimentalFeatures'] = wp_get_global_settings(); diff --git a/src/wp-includes/class-wp-theme-json-resolver.php b/src/wp-includes/class-wp-theme-json-resolver.php index e696eef894783..4d5bf3dce9ee3 100644 --- a/src/wp-includes/class-wp-theme-json-resolver.php +++ b/src/wp-includes/class-wp-theme-json-resolver.php @@ -480,17 +480,6 @@ public static function get_user_data_from_wp_global_styles( $theme, $create_post $theme = wp_get_theme(); } - /* - * Bail early if the theme does not support a theme.json. - * - * Since wp_theme_has_theme_json() only supports the active - * theme, the extra condition for whether $theme is the active theme is - * present here. - */ - if ( $theme->get_stylesheet() === get_stylesheet() && ! wp_theme_has_theme_json() ) { - return array(); - } - $user_cpt = array(); $post_type_filter = 'wp_global_styles'; $stylesheet = $theme->get_stylesheet(); diff --git a/src/wp-includes/class-wp-theme-json.php b/src/wp-includes/class-wp-theme-json.php index ba2020813aa39..f9965a754989a 100644 --- a/src/wp-includes/class-wp-theme-json.php +++ b/src/wp-includes/class-wp-theme-json.php @@ -1326,12 +1326,13 @@ public function get_settings() { * @since 6.3.0 Add fallback layout styles for Post Template when block gap support isn't available. * @since 6.6.0 Added boolean `skip_root_layout_styles` and `include_block_style_variations` options * to control styles output as desired. + * @since 7.0.0 Deprecated 'base-layout-styles' type; added `base_layout_styles` option for classic themes. * * @param string[] $types Types of styles to load. Will load all by default. It accepts: * - `variables`: only the CSS Custom Properties for presets & custom ones. * - `styles`: only the styles section in theme.json. * - `presets`: only the classes for the presets. - * - `base-layout-styles`: only the base layout styles. + * - `base-layout-styles`: only the base layout styles. Deprecated in 7.0.0. * - `custom-css`: only the custom CSS. * @param string[] $origins A list of origins to include. By default it includes VALID_ORIGINS. * @param array $options { @@ -1340,6 +1341,7 @@ public function get_settings() { * @type string $scope Makes sure all style are scoped to a given selector * @type string $root_selector Overwrites and forces a given selector to be used on the root node * @type bool $skip_root_layout_styles Omits root layout styles from the generated stylesheet. Default false. + * @type bool $base_layout_styles When true generates only base layout styles without alignment rules. Default false. * @type bool $include_block_style_variations Includes styles for block style variations in the generated stylesheet. Default false. * } * @return string The resulting stylesheet. @@ -1395,45 +1397,9 @@ public function get_stylesheet( $types = array( 'variables', 'styles', 'presets' if ( in_array( 'styles', $types, true ) ) { if ( false !== $root_style_key && empty( $options['skip_root_layout_styles'] ) ) { - $stylesheet .= $this->get_root_layout_rules( $style_nodes[ $root_style_key ]['selector'], $style_nodes[ $root_style_key ] ); + $stylesheet .= $this->get_root_layout_rules( $style_nodes[ $root_style_key ]['selector'], $style_nodes[ $root_style_key ], $options ); } $stylesheet .= $this->get_block_classes( $style_nodes ); - } elseif ( in_array( 'base-layout-styles', $types, true ) ) { - $root_selector = static::ROOT_BLOCK_SELECTOR; - $columns_selector = '.wp-block-columns'; - $post_template_selector = '.wp-block-post-template'; - if ( ! empty( $options['scope'] ) ) { - $root_selector = static::scope_selector( $options['scope'], $root_selector ); - $columns_selector = static::scope_selector( $options['scope'], $columns_selector ); - $post_template_selector = static::scope_selector( $options['scope'], $post_template_selector ); - } - if ( ! empty( $options['root_selector'] ) ) { - $root_selector = $options['root_selector']; - } - /* - * Base layout styles are provided as part of `styles`, so only output separately if explicitly requested. - * For backwards compatibility, the Columns block is explicitly included, to support a different default gap value. - */ - $base_styles_nodes = array( - array( - 'path' => array( 'styles' ), - 'selector' => $root_selector, - ), - array( - 'path' => array( 'styles', 'blocks', 'core/columns' ), - 'selector' => $columns_selector, - 'name' => 'core/columns', - ), - array( - 'path' => array( 'styles', 'blocks', 'core/post-template' ), - 'selector' => $post_template_selector, - 'name' => 'core/post-template', - ), - ); - - foreach ( $base_styles_nodes as $base_style_node ) { - $stylesheet .= $this->get_layout_styles( $base_style_node, $types ); - } } if ( in_array( 'presets', $types, true ) ) { @@ -1624,12 +1590,13 @@ protected function get_block_classes( $style_nodes ) { * @since 6.5.1 Only output rules referencing content and wide sizes when values exist. * @since 6.5.3 Add types parameter to check if only base layout styles are needed. * @since 6.6.0 Updated layout style specificity to be compatible with overall 0-1-0 specificity in global styles. + * @since 7.0.0 Replaced `$types` parameter with `$options` array; base layout styles controlled via `base_layout_styles` option. * * @param array $block_metadata Metadata about the block to get styles for. - * @param array $types Optional. Types of styles to output. If empty, all styles will be output. + * @param array $options Optional. An array of options for now used for internal purposes only. * @return string Layout styles for the block. */ - protected function get_layout_styles( $block_metadata, $types = array() ) { + protected function get_layout_styles( $block_metadata, $options = array() ) { $block_rules = ''; $block_type = null; @@ -1777,8 +1744,9 @@ protected function get_layout_styles( $block_metadata, $types = array() ) { foreach ( $base_style_rules as $base_style_rule ) { $declarations = array(); - // Skip outputting base styles for flow and constrained layout types if theme doesn't support theme.json. The 'base-layout-styles' type flags this. - if ( in_array( 'base-layout-styles', $types, true ) && ( 'default' === $layout_definition['name'] || 'constrained' === $layout_definition['name'] ) ) { + // Skip outputting base styles for flow and constrained layout types when base_layout_styles is enabled. + // These themes don't use .wp-site-blocks wrapper, so these layout-specific alignment styles aren't needed. + if ( ! empty( $options['base_layout_styles'] ) && ( 'default' === $layout_definition['name'] || 'constrained' === $layout_definition['name'] ) ) { continue; } @@ -3055,12 +3023,14 @@ static function ( $pseudo_selector ) use ( $selector ) { * @since 6.1.0 * @since 6.6.0 Use `ROOT_CSS_PROPERTIES_SELECTOR` for CSS custom properties and improved consistency of root padding rules. * Updated specificity of body margin reset and first/last child selectors. + * @since 7.0.0 Added `$options` parameter to control alignment styles output for classic themes. * * @param string $selector The root node selector. * @param array $block_metadata The metadata for the root block. + * @param array $options Optional. An array of options for now used for internal purposes only. * @return string The additional root rules CSS. */ - public function get_root_layout_rules( $selector, $block_metadata ) { + public function get_root_layout_rules( $selector, $block_metadata, $options = array() ) { $css = ''; $settings = $this->theme_json['settings'] ?? array(); $use_root_padding = isset( $this->theme_json['settings']['useRootPaddingAwareAlignments'] ) && true === $this->theme_json['settings']['useRootPaddingAwareAlignments']; @@ -3101,9 +3071,13 @@ public function get_root_layout_rules( $selector, $block_metadata ) { $css .= '.has-global-padding :where(:not(.alignfull.is-layout-flow) > .has-global-padding:not(.wp-block-block, .alignfull)) > .alignfull { margin-left: 0; margin-right: 0; }'; } - $css .= '.wp-site-blocks > .alignleft { float: left; margin-right: 2em; }'; - $css .= '.wp-site-blocks > .alignright { float: right; margin-left: 2em; }'; - $css .= '.wp-site-blocks > .aligncenter { justify-content: center; margin-left: auto; margin-right: auto; }'; + // Skip outputting alignment styles when base_layout_styles is enabled. + // These styles target .wp-site-blocks which is only used by block themes. + if ( empty( $options['base_layout_styles'] ) ) { + $css .= '.wp-site-blocks > .alignleft { float: left; margin-right: 2em; }'; + $css .= '.wp-site-blocks > .alignright { float: right; margin-left: 2em; }'; + $css .= '.wp-site-blocks > .aligncenter { justify-content: center; margin-left: auto; margin-right: auto; }'; + } // Block gap styles will be output unless explicitly set to `null`. See static::PROTECTED_PROPERTIES. if ( isset( $this->theme_json['settings']['spacing']['blockGap'] ) ) { @@ -3115,7 +3089,7 @@ public function get_root_layout_rules( $selector, $block_metadata ) { // For backwards compatibility, ensure the legacy block gap CSS variable is still available. $css .= static::ROOT_CSS_PROPERTIES_SELECTOR . " { --wp--style--block-gap: $block_gap_value; }"; } - $css .= $this->get_layout_styles( $block_metadata ); + $css .= $this->get_layout_styles( $block_metadata, $options ); return $css; } diff --git a/src/wp-includes/global-styles-and-settings.php b/src/wp-includes/global-styles-and-settings.php index 938648ad47fa2..d50ee14e22015 100644 --- a/src/wp-includes/global-styles-and-settings.php +++ b/src/wp-includes/global-styles-and-settings.php @@ -39,10 +39,7 @@ function wp_get_global_settings( $path = array(), $context = array() ) { * for clearing the cache appropriately. */ $origin = 'custom'; - if ( - ! wp_theme_has_theme_json() || - ( isset( $context['origin'] ) && 'base' === $context['origin'] ) - ) { + if ( isset( $context['origin'] ) && 'base' === $context['origin'] ) { $origin = 'theme'; } @@ -140,12 +137,12 @@ function wp_get_global_styles( $path = array(), $context = array() ) { * @since 5.9.0 * @since 6.1.0 Added 'base-layout-styles' support. * @since 6.6.0 Resolves relative paths in theme.json styles to theme absolute paths. + * @since 7.0.0 Deprecated 'base-layout-styles' type; classic themes now receive full styles + * with layout-specific alignment rules skipped via `base_layout_styles` option. * * @param array $types Optional. Types of styles to load. * See {@see 'WP_Theme_JSON::get_stylesheet'} for all valid types. - * If empty, it'll load the following: - * - for themes without theme.json: 'variables', 'presets', 'base-layout-styles'. - * - for themes with theme.json: 'variables', 'presets', 'styles'. + * If empty, will load: 'variables', 'presets', 'styles'. * @return string Stylesheet. */ function wp_get_global_stylesheet( $types = array() ) { @@ -180,15 +177,21 @@ function wp_get_global_stylesheet( $types = array() ) { } } - $tree = WP_Theme_JSON_Resolver::resolve_theme_file_uris( WP_Theme_JSON_Resolver::get_merged_data() ); - $supports_theme_json = wp_theme_has_theme_json(); + $tree = WP_Theme_JSON_Resolver::resolve_theme_file_uris( WP_Theme_JSON_Resolver::get_merged_data() ); - if ( empty( $types ) && ! $supports_theme_json ) { - $types = array( 'variables', 'presets', 'base-layout-styles' ); - } elseif ( empty( $types ) ) { + if ( empty( $types ) ) { $types = array( 'variables', 'styles', 'presets' ); } + /* + * Enable base layout styles only mode for classic themes without theme.json. + * This skips alignment styles that target .wp-site-blocks which is only used by block themes. + */ + $options = array(); + if ( ! wp_is_block_theme() && ! wp_theme_has_theme_json() ) { + $options['base_layout_styles'] = true; + } + /* * If variables are part of the stylesheet, then add them. * This is so themes without a theme.json still work as before 5.9: @@ -204,7 +207,7 @@ function wp_get_global_stylesheet( $types = array() ) { * @see wp_add_global_styles_for_blocks */ $origins = array( 'default', 'theme', 'custom' ); - $styles_variables = $tree->get_stylesheet( array( 'variables' ), $origins ); + $styles_variables = $tree->get_stylesheet( array( 'variables' ), $origins, $options ); $types = array_diff( $types, array( 'variables' ) ); } @@ -222,17 +225,8 @@ function wp_get_global_stylesheet( $types = array() ) { * (i.e. in the render cycle). Here, only the ones in use are rendered. * @see wp_add_global_styles_for_blocks */ - $origins = array( 'default', 'theme', 'custom' ); - /* - * If the theme doesn't have theme.json but supports both appearance tools and color palette, - * the 'theme' origin should be included so color palette presets are also output. - */ - if ( ! $supports_theme_json && ( current_theme_supports( 'appearance-tools' ) || current_theme_supports( 'border' ) ) && current_theme_supports( 'editor-color-palette' ) ) { - $origins = array( 'default', 'theme' ); - } elseif ( ! $supports_theme_json ) { - $origins = array( 'default' ); - } - $styles_rest = $tree->get_stylesheet( $types, $origins ); + $origins = array( 'default', 'theme', 'custom' ); + $styles_rest = $tree->get_stylesheet( $types, $origins, $options ); } $stylesheet = $styles_variables . $styles_rest; diff --git a/src/wp-includes/script-loader.php b/src/wp-includes/script-loader.php index 2946f19656d4c..32e3a70be11b6 100644 --- a/src/wp-includes/script-loader.php +++ b/src/wp-includes/script-loader.php @@ -2514,38 +2514,36 @@ function wp_enqueue_global_styles() { $stylesheet = wp_get_global_stylesheet(); - if ( $is_block_theme ) { - /* - * Dequeue the Customizer's custom CSS - * and add it before the global styles custom CSS. - */ - remove_action( 'wp_head', 'wp_custom_css_cb', 101 ); + /* + * Dequeue the Customizer's custom CSS + * and add it before the global styles custom CSS. + */ + remove_action( 'wp_head', 'wp_custom_css_cb', 101 ); - /* - * Get the custom CSS from the Customizer and add it to the global stylesheet. - * Always do this in Customizer preview for the sake of live preview since it be empty. - */ - $custom_css = trim( wp_get_custom_css() ); - if ( $custom_css || is_customize_preview() ) { - if ( is_customize_preview() ) { - /* - * When in the Customizer preview, wrap the Custom CSS in milestone comments to allow customize-preview.js - * to locate the CSS to replace for live previewing. Make sure that the milestone comments are omitted from - * the stored Custom CSS if by chance someone tried to add them, which would be highly unlikely, but it - * would break live previewing. - */ - $before_milestone = '/*BEGIN_CUSTOMIZER_CUSTOM_CSS*/'; - $after_milestone = '/*END_CUSTOMIZER_CUSTOM_CSS*/'; - $custom_css = str_replace( array( $before_milestone, $after_milestone ), '', $custom_css ); - $custom_css = $before_milestone . "\n" . $custom_css . "\n" . $after_milestone; - } - $custom_css = "\n" . $custom_css; + /* + * Get the custom CSS from the Customizer and add it to the global stylesheet. + * Always do this in Customizer preview for the sake of live preview since it be empty. + */ + $custom_css = trim( wp_get_custom_css() ); + if ( $custom_css || is_customize_preview() ) { + if ( is_customize_preview() ) { + /* + * When in the Customizer preview, wrap the Custom CSS in milestone comments to allow customize-preview.js + * to locate the CSS to replace for live previewing. Make sure that the milestone comments are omitted from + * the stored Custom CSS if by chance someone tried to add them, which would be highly unlikely, but it + * would break live previewing. + */ + $before_milestone = '/*BEGIN_CUSTOMIZER_CUSTOM_CSS*/'; + $after_milestone = '/*END_CUSTOMIZER_CUSTOM_CSS*/'; + $custom_css = str_replace( array( $before_milestone, $after_milestone ), '', $custom_css ); + $custom_css = $before_milestone . "\n" . $custom_css . "\n" . $after_milestone; } - $stylesheet .= $custom_css; - - // Add the global styles custom CSS at the end. - $stylesheet .= wp_get_global_stylesheet( array( 'custom-css' ) ); + $custom_css = "\n" . $custom_css; } + $stylesheet .= $custom_css; + + // Add the global styles custom CSS at the end. + $stylesheet .= wp_get_global_stylesheet( array( 'custom-css' ) ); if ( empty( $stylesheet ) ) { return; diff --git a/tests/phpunit/tests/template.php b/tests/phpunit/tests/template.php index dacc69fba6330..6c6f0fcd33aba 100644 --- a/tests/phpunit/tests/template.php +++ b/tests/phpunit/tests/template.php @@ -1561,7 +1561,6 @@ static function () { 'global-styles-inline-css', 'normal-css', 'normal-inline-css', - 'wp-custom-css', ), 'BODY' => array( 'late-css', @@ -1623,7 +1622,6 @@ function (): void { 'global-styles-inline-css', 'normal-css', 'normal-inline-css', - 'wp-custom-css', ), 'BODY' => array( 'late-css', diff --git a/tests/phpunit/tests/theme/wpThemeJson.php b/tests/phpunit/tests/theme/wpThemeJson.php index 2bf0e7d84f266..45bc0681b0223 100644 --- a/tests/phpunit/tests/theme/wpThemeJson.php +++ b/tests/phpunit/tests/theme/wpThemeJson.php @@ -1216,14 +1216,20 @@ public function test_get_stylesheet_generates_base_fallback_gap_layout_styles() 'blockGap' => null, ), ), + 'styles' => array( + 'spacing' => array( + 'blockGap' => '1em', + ), + ), ), 'default' ); - $stylesheet = $theme_json->get_stylesheet( array( 'base-layout-styles' ) ); + // Set base_layout_styles to true to generate only base layout styles without alignment rules. + $stylesheet = $theme_json->get_stylesheet( array( 'styles' ), null, array( 'base_layout_styles' => true ) ); - // Note the `base-layout-styles` includes a fallback gap for the Columns block for backwards compatibility. + // Verify that layout styles are still generated, but without .wp-site-blocks alignment rules and flow/constrained base styles. $this->assertSame( - ':where(.is-layout-flex){gap: 0.5em;}:where(.is-layout-grid){gap: 0.5em;}body .is-layout-flex{display: flex;}.is-layout-flex{flex-wrap: wrap;align-items: center;}.is-layout-flex > :is(*, div){margin: 0;}body .is-layout-grid{display: grid;}.is-layout-grid > :is(*, div){margin: 0;}:where(.wp-block-columns.is-layout-flex){gap: 2em;}:where(.wp-block-columns.is-layout-grid){gap: 2em;}:where(.wp-block-post-template.is-layout-flex){gap: 1.25em;}:where(.wp-block-post-template.is-layout-grid){gap: 1.25em;}', + ':where(body) { margin: 0; }:where(.is-layout-flex){gap: 0.5em;}:where(.is-layout-grid){gap: 0.5em;}body .is-layout-flex{display: flex;}.is-layout-flex{flex-wrap: wrap;align-items: center;}.is-layout-flex > :is(*, div){margin: 0;}body .is-layout-grid{display: grid;}.is-layout-grid > :is(*, div){margin: 0;}', $stylesheet ); } @@ -1245,10 +1251,10 @@ public function test_get_stylesheet_skips_layout_styles() { ), 'default' ); - $stylesheet = $theme_json->get_stylesheet( array( 'base-layout-styles' ) ); + $stylesheet = $theme_json->get_stylesheet( array( 'styles' ), null ); remove_theme_support( 'disable-layout-styles' ); - // All Layout styles should be skipped. + // All Layout styles should be skipped when disable-layout-styles theme support is added. $this->assertSame( '', $stylesheet diff --git a/tests/phpunit/tests/theme/wpThemeJsonResolver.php b/tests/phpunit/tests/theme/wpThemeJsonResolver.php index 599224270649d..ce5609a396f18 100644 --- a/tests/phpunit/tests/theme/wpThemeJsonResolver.php +++ b/tests/phpunit/tests/theme/wpThemeJsonResolver.php @@ -734,22 +734,22 @@ public function test_get_user_data_from_wp_global_styles_does_not_use_uncached_q * @ticket 56945 * @covers WP_Theme_JSON_Resolver::get_user_data_from_wp_global_styles */ - public function test_get_user_data_from_wp_global_styles_does_not_run_for_theme_without_support() { - // The 'default' theme does not support theme.json. + public function test_get_user_data_from_wp_global_styles_runs_for_classic_themes() { + // The 'default' theme does not support theme.json (classic theme). switch_theme( 'default' ); wp_set_current_user( self::$administrator_id ); $theme = wp_get_theme(); - $start_queries = get_num_queries(); - - // When theme.json is not supported, the method should not run a query and always return an empty result. - $user_cpt = WP_Theme_JSON_Resolver::get_user_data_from_wp_global_styles( $theme ); - $this->assertEmpty( $user_cpt, 'User CPT is expected to be empty.' ); - $this->assertSame( 0, get_num_queries() - $start_queries, 'Unexpected SQL query detected for theme without theme.json support.' ); - + // Classic themes should now be able to access user global styles data. + // When should_create_post is true, it should create a post. $user_cpt = WP_Theme_JSON_Resolver::get_user_data_from_wp_global_styles( $theme, true ); - $this->assertEmpty( $user_cpt, 'User CPT is expected to be empty.' ); - $this->assertSame( 0, get_num_queries() - $start_queries, 'Unexpected SQL query detected for theme without theme.json support.' ); + $this->assertIsArray( $user_cpt, 'User CPT should be an array for classic themes.' ); + $this->assertArrayHasKey( 'ID', $user_cpt, 'User CPT should have an ID for classic themes.' ); + + // Clean up the created post. + if ( isset( $user_cpt['ID'] ) ) { + wp_delete_post( $user_cpt['ID'], true ); + } } /** From 7d020b2f9eb4f5949a8069547a96a2c7b24ca02e Mon Sep 17 00:00:00 2001 From: Weston Ruter Date: Mon, 12 Jan 2026 21:15:00 +0000 Subject: [PATCH 123/126] Code Modernization: Utilize spaceship operator `<=>` in sort comparison logic. Some replaced instances also fix a bug where the comparison function should have returned `0` as opposed to `1` or `-1` as used in ternaries. This results in a performance improvement. Developed in https://github.com/WordPress/wordpress-develop/pull/10717 Props soean, mukesh27, westonruter. Fixes #64497. git-svn-id: https://develop.svn.wordpress.org/trunk@61474 602fd350-edb4-49c9-b593-d223f7449a82 --- .../includes/class-wp-ms-themes-list-table.php | 12 +++--------- .../includes/class-wp-plugin-install-list-table.php | 12 +++--------- src/wp-admin/includes/menu.php | 7 ++----- .../interactivity-api/class-wp-interactivity-api.php | 7 ++----- src/wp-includes/script-loader.php | 2 +- 5 files changed, 11 insertions(+), 29 deletions(-) diff --git a/src/wp-admin/includes/class-wp-ms-themes-list-table.php b/src/wp-admin/includes/class-wp-ms-themes-list-table.php index dd95834e91cc8..37caa4b361dbf 100644 --- a/src/wp-admin/includes/class-wp-ms-themes-list-table.php +++ b/src/wp-admin/includes/class-wp-ms-themes-list-table.php @@ -302,15 +302,9 @@ public function _order_callback( $theme_a, $theme_b ) { $a = $theme_a[ $orderby ]; $b = $theme_b[ $orderby ]; - if ( $a === $b ) { - return 0; - } - - if ( 'DESC' === $order ) { - return ( $a < $b ) ? 1 : -1; - } else { - return ( $a < $b ) ? -1 : 1; - } + return 'DESC' === $order ? + $b <=> $a : + $a <=> $b; } /** diff --git a/src/wp-admin/includes/class-wp-plugin-install-list-table.php b/src/wp-admin/includes/class-wp-plugin-install-list-table.php index 1976dfa8aed28..a029d725d7b75 100644 --- a/src/wp-admin/includes/class-wp-plugin-install-list-table.php +++ b/src/wp-admin/includes/class-wp-plugin-install-list-table.php @@ -458,15 +458,9 @@ private function order_callback( $plugin_a, $plugin_b ) { $a = $plugin_a->$orderby; $b = $plugin_b->$orderby; - if ( $a === $b ) { - return 0; - } - - if ( 'DESC' === $this->order ) { - return ( $a < $b ) ? 1 : -1; - } else { - return ( $a < $b ) ? -1 : 1; - } + return 'DESC' === $this->order ? + $b <=> $a : + $a <=> $b; } /** diff --git a/src/wp-admin/includes/menu.php b/src/wp-admin/includes/menu.php index 3cf4a5fdd6c17..7b87e60604c82 100644 --- a/src/wp-admin/includes/menu.php +++ b/src/wp-admin/includes/menu.php @@ -327,12 +327,9 @@ function sort_menu( $a, $b ) { } elseif ( ! isset( $menu_order[ $a ] ) && isset( $menu_order[ $b ] ) ) { return 1; } elseif ( isset( $menu_order[ $a ] ) && isset( $menu_order[ $b ] ) ) { - if ( $menu_order[ $a ] === $menu_order[ $b ] ) { - return 0; - } - return ( $menu_order[ $a ] < $menu_order[ $b ] ) ? -1 : 1; + return $menu_order[ $a ] <=> $menu_order[ $b ]; } else { - return ( $default_menu_order[ $a ] <= $default_menu_order[ $b ] ) ? -1 : 1; + return $default_menu_order[ $a ] <=> $default_menu_order[ $b ]; } } diff --git a/src/wp-includes/interactivity-api/class-wp-interactivity-api.php b/src/wp-includes/interactivity-api/class-wp-interactivity-api.php index 539242e211b13..f2c66b07fcbb5 100644 --- a/src/wp-includes/interactivity-api/class-wp-interactivity-api.php +++ b/src/wp-includes/interactivity-api/class-wp-interactivity-api.php @@ -904,14 +904,11 @@ function ( $a, $b ) { $a_suffix = $a['suffix'] ?? ''; $b_suffix = $b['suffix'] ?? ''; if ( $a_suffix !== $b_suffix ) { - return $a_suffix < $b_suffix ? -1 : 1; + return $a_suffix <=> $b_suffix; } $a_id = $a['unique_id'] ?? ''; $b_id = $b['unique_id'] ?? ''; - if ( $a_id === $b_id ) { - return 0; - } - return $a_id > $b_id ? 1 : -1; + return $a_id <=> $b_id; } ); return $entries; diff --git a/src/wp-includes/script-loader.php b/src/wp-includes/script-loader.php index 32e3a70be11b6..8cd3301ff6fdd 100644 --- a/src/wp-includes/script-loader.php +++ b/src/wp-includes/script-loader.php @@ -2999,7 +2999,7 @@ function wp_maybe_inline_styles() { usort( $styles, static function ( $a, $b ) { - return ( $a['size'] <= $b['size'] ) ? -1 : 1; + return $a['size'] <=> $b['size']; } ); From 39c73314c5ba2f93f1511057f8853f0dde8aef97 Mon Sep 17 00:00:00 2001 From: Aaron Jorbin <622599+aaronjorbin@users.noreply.github.com> Date: Tue, 2 Dec 2025 15:13:52 -0600 Subject: [PATCH 124/126] bump workflows for 6.9 --- .github/workflows/upgrade-develop-testing.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/upgrade-develop-testing.yml b/.github/workflows/upgrade-develop-testing.yml index b5851f247b5c4..d65057cdab5d4 100644 --- a/.github/workflows/upgrade-develop-testing.yml +++ b/.github/workflows/upgrade-develop-testing.yml @@ -67,7 +67,7 @@ jobs: db-type: [ 'mysql' ] db-version: [ '5.7', '8.4' ] # WordPress 5.3 is the oldest version that supports PHP 7.4. - wp: [ '5.3', '6.7', '6.8', '6.9' ] + wp: [ '5.3', '6.8', '6.9' ] multisite: [ false, true ] with: os: ${{ matrix.os }} From c3bc87a3e876931eabd4b8634a177e23dd9ba528 Mon Sep 17 00:00:00 2001 From: Aaron Jorbin <622599+aaronjorbin@users.noreply.github.com> Date: Mon, 12 Jan 2026 15:25:02 -0600 Subject: [PATCH 125/126] add docblock --- .github/workflows/upgrade-develop-testing.yml | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/.github/workflows/upgrade-develop-testing.yml b/.github/workflows/upgrade-develop-testing.yml index d65057cdab5d4..a99b307af7b74 100644 --- a/.github/workflows/upgrade-develop-testing.yml +++ b/.github/workflows/upgrade-develop-testing.yml @@ -51,7 +51,15 @@ jobs: permissions: contents: read - # Run upgrade tests for the current branch. +# Because the number of jobs spawned can quickly balloon out of control, the following methodology is applied when +# building out the matrix below: +# +# - The two most recent releases of WordPress are always tested. +# - After a branch is created, the pre-release version is also added. +# - The oldest version of WordPress receiving security updates as a courtesy that also runs on a PHP version supported by trunk +# should always be tested. +# - PHP and DB are kept to a minimum. In general this should be the highest and lowest supported versions of each with excludes being +# updated to keep the matrix as small as is reasonable. upgrade-tests-develop: name: Upgrade from ${{ matrix.wp }} uses: ./.github/workflows/reusable-upgrade-testing.yml From edaf0bcb6eebd0015a694fb7d416df3489c7920e Mon Sep 17 00:00:00 2001 From: Aaron Jorbin <622599+aaronjorbin@users.noreply.github.com> Date: Mon, 12 Jan 2026 15:49:42 -0600 Subject: [PATCH 126/126] remove no logner necessary comment --- .github/workflows/upgrade-develop-testing.yml | 1 - 1 file changed, 1 deletion(-) diff --git a/.github/workflows/upgrade-develop-testing.yml b/.github/workflows/upgrade-develop-testing.yml index a99b307af7b74..91abd0cd05849 100644 --- a/.github/workflows/upgrade-develop-testing.yml +++ b/.github/workflows/upgrade-develop-testing.yml @@ -101,7 +101,6 @@ jobs: php: [ '7.4', '8.4' ] db-type: [ 'mysql' ] db-version: [ '8.4' ] - # WordPress 4.9 is the oldest version that supports PHP 7.2. wp: [ '6.8', '6.9' ] multisite: [ false, true ] with: