Commit 7f1fd25a8c for wordpress.org

commit 7f1fd25a8c42adc94fda7ceef72b32e57a805e57
Author: mcsf <mcsf@git.wordpress.org>
Date:   Tue Sep 15 17:17:52 2026 +0000

    Icons: Add `public` property to hide registered icons from REST API.

    Expand the signature of `WP_Icons_Registry::register` and `wp_register_icon` to accept an optional boolean property, `public`, which controls whether a given icon should be exposed in the REST API. It defaults to true.

    An icon registered with `public` set to `false` will nevertheless remain accessible to `wp_get_icon` and other direct consumers of `WP_Icons_Registry`.

    Developed in: https://github.com/WordPress/gutenberg/pull/82634
    Developed in: https://github.com/WordPress/wordpress-develop/pull/13453

    Props fushar.

    Fixes #66087.


    Built from https://develop.svn.wordpress.org/trunk@63625


    git-svn-id: http://core.svn.wordpress.org/trunk@62801 1a063a9b-81f0-0310-95a4-ce76da25c4cd

diff --git a/wp-includes/class-wp-icons-registry.php b/wp-includes/class-wp-icons-registry.php
index a10960da9a..b40c5ec124 100644
--- a/wp-includes/class-wp-icons-registry.php
+++ b/wp-includes/class-wp-icons-registry.php
@@ -46,6 +46,7 @@ class WP_Icons_Registry {
 	 *
 	 * @since 7.0.0
 	 * @since 7.1.0 The icon name must be namespaced in the form "collection/icon-name".
+	 * @since 7.2.0 Added the `public` property.
 	 *
 	 * @param string $icon_name       Namespaced icon name in the form "collection/icon-name"
 	 *                                (e.g. "core/arrow-left").
@@ -57,6 +58,10 @@ class WP_Icons_Registry {
 	 *                             If not provided, the content will be retrieved from the `file_path` if set.
 	 *                             If both `content` and `file_path` are not set, the icon will not be registered.
 	 *     @type string $file_path Optional. The full path to the file containing the icon content.
+	 *     @type bool   $public    Optional. Whether the icon is exposed through the REST API, and
+	 *                             therefore selectable in the editor's icon picker. Non-public icons
+	 *                             stay available to server-side code via {@see wp_get_icon()}.
+	 *                             Default true.
 	 * }
 	 * @return bool True if the icon was registered with success and false otherwise.
 	 */
@@ -101,7 +106,7 @@ class WP_Icons_Registry {
 			return false;
 		}

-		$allowed_keys = array_fill_keys( array( 'label', 'content', 'file_path' ), 1 );
+		$allowed_keys = array_fill_keys( array( 'label', 'content', 'file_path', 'public' ), 1 );
 		foreach ( array_keys( $icon_properties ) as $key ) {
 			if ( ! array_key_exists( $key, $allowed_keys ) ) {
 				_doing_it_wrong(
@@ -139,6 +144,15 @@ class WP_Icons_Registry {
 			return false;
 		}

+		if ( isset( $icon_properties['public'] ) && ! is_bool( $icon_properties['public'] ) ) {
+			_doing_it_wrong(
+				__METHOD__,
+				__( 'Icon public property must be a boolean.' ),
+				'7.2.0'
+			);
+			return false;
+		}
+
 		if (
 			( ! isset( $icon_properties['content'] ) && ! isset( $icon_properties['file_path'] ) ) ||
 			( isset( $icon_properties['content'] ) && isset( $icon_properties['file_path'] ) )
diff --git a/wp-includes/icons.php b/wp-includes/icons.php
index a00b8a7560..4c906ad939 100644
--- a/wp-includes/icons.php
+++ b/wp-includes/icons.php
@@ -41,6 +41,7 @@ function wp_unregister_icon_collection( $slug ) {
  * Registers a new icon.
  *
  * @since 7.1.0
+ * @since 7.2.0 Added the `public` property.
  *
  * @param string $icon_name Namespaced icon name in the form "collection/icon-name"
  *                          (e.g. "my-plugin/arrow-left"). The "core" collection is
@@ -55,6 +56,10 @@ function wp_unregister_icon_collection( $slug ) {
  *                             If not provided, the content will be retrieved from the `file_path` if set.
  *                             If both `content` and `file_path` are not set, the icon will not be registered.
  *     @type string $file_path Optional. The full path to the file containing the icon content.
+ *     @type bool   $public    Optional. Whether the icon is exposed through the REST API, and
+ *                             therefore selectable in the editor's icon picker. Non-public icons
+ *                             stay available to server-side code via {@see wp_get_icon()}.
+ *                             Default true.
  * }
  * @return bool True if the icon was registered successfully, else false.
  */
@@ -132,13 +137,16 @@ function _wp_register_default_icons() {
 			return;
 		}

-		wp_register_icon(
-			'core/' . $icon_name,
-			array(
-				'label'     => $icon_data['label'],
-				'file_path' => $icons_directory . $icon_data['filePath'],
-			)
+		$icon_args = array(
+			'label'     => $icon_data['label'],
+			'file_path' => $icons_directory . $icon_data['filePath'],
 		);
+
+		if ( isset( $icon_data['public'] ) ) {
+			$icon_args['public'] = $icon_data['public'];
+		}
+
+		wp_register_icon( 'core/' . $icon_name, $icon_args );
 	}
 }

diff --git a/wp-includes/rest-api/endpoints/class-wp-rest-icons-controller.php b/wp-includes/rest-api/endpoints/class-wp-rest-icons-controller.php
index b896cd758e..4578df9d28 100644
--- a/wp-includes/rest-api/endpoints/class-wp-rest-icons-controller.php
+++ b/wp-includes/rest-api/endpoints/class-wp-rest-icons-controller.php
@@ -143,6 +143,7 @@ class WP_REST_Icons_Controller extends WP_REST_Controller {
 	 *
 	 * @since 7.0.0
 	 * @since 7.1.0 Supports filtering by collection.
+	 * @since 7.2.0 Icons registered as non-public are omitted.
 	 *
 	 * @param WP_REST_Request $request Full details about the request.
 	 * @return WP_REST_Response|WP_Error Response object on success, or WP_Error object on failure.
@@ -167,6 +168,9 @@ class WP_REST_Icons_Controller extends WP_REST_Controller {
 		$icons    = WP_Icons_Registry::get_instance()->get_registered_icons( $search );

 		foreach ( $icons as $icon ) {
+			if ( false === ( $icon['public'] ?? true ) ) {
+				continue;
+			}
 			if ( null !== $collection && ( ! isset( $icon['collection'] ) || $icon['collection'] !== $collection ) ) {
 				continue;
 			}
@@ -198,6 +202,7 @@ class WP_REST_Icons_Controller extends WP_REST_Controller {
 	 * Retrieves a specific icon from the registry.
 	 *
 	 * @since 7.0.0
+	 * @since 7.2.0 Icons registered as non-public are reported as not found.
 	 *
 	 * @param string $name Icon name.
 	 * @return array|WP_Error Icon data on success, or WP_Error object on failure.
@@ -206,7 +211,7 @@ class WP_REST_Icons_Controller extends WP_REST_Controller {
 		$registry = WP_Icons_Registry::get_instance();
 		$icon     = $registry->get_registered_icon( $name );

-		if ( null === $icon ) {
+		if ( null === $icon || false === ( $icon['public'] ?? true ) ) {
 			return new WP_Error(
 				'rest_icon_not_found',
 				sprintf(
diff --git a/wp-includes/version.php b/wp-includes/version.php
index 980aacef74..f42a4f30c4 100644
--- a/wp-includes/version.php
+++ b/wp-includes/version.php
@@ -16,7 +16,7 @@
  *
  * @global string $wp_version
  */
-$wp_version = '7.2-alpha-63624';
+$wp_version = '7.2-alpha-63625';

 /**
  * Holds the WordPress DB revision, increments when changes are made to the WordPress DB schema.