From 07dabda0282d89b1a2cb5ab3c0d03d90d6f8b885 Mon Sep 17 00:00:00 2001 From: Aki Hamano Date: Thu, 11 Jun 2026 11:47:04 +0900 Subject: [PATCH 1/3] Icons: Rename icon manifest key `filePath` to `file_path`. Align the icon registry and generated manifest with WordPress core's snake_case array-key convention, which is the dominant style across core PHP. This updates the manifest entries, the registry validation and `get_content()` lookup, the allowed property keys, and the related docblocks and error messages. Mirrors the same rename made on the Gutenberg side in https://github.com/WordPress/gutenberg/pull/79100. Co-Authored-By: Claude --- .../assets/icon-library-manifest.php | 352 +++++++++--------- src/wp-includes/class-wp-icons-registry.php | 6 +- 2 files changed, 179 insertions(+), 179 deletions(-) diff --git a/src/wp-includes/assets/icon-library-manifest.php b/src/wp-includes/assets/icon-library-manifest.php index af72a1c00499c..c1ec198904265 100644 --- a/src/wp-includes/assets/icon-library-manifest.php +++ b/src/wp-includes/assets/icon-library-manifest.php @@ -6,355 +6,355 @@ return array( 'arrow-down-left' => array( - 'label' => _x( 'Arrow Down Left', 'icon label' ), - 'filePath' => 'arrow-down-left.svg', + 'label' => _x( 'Arrow Down Left', 'icon label' ), + 'file_path' => 'arrow-down-left.svg', ), 'arrow-down-right' => array( - 'label' => _x( 'Arrow Down Right', 'icon label' ), - 'filePath' => 'arrow-down-right.svg', + 'label' => _x( 'Arrow Down Right', 'icon label' ), + 'file_path' => 'arrow-down-right.svg', ), 'arrow-down' => array( - 'label' => _x( 'Arrow Down', 'icon label' ), - 'filePath' => 'arrow-down.svg', + 'label' => _x( 'Arrow Down', 'icon label' ), + 'file_path' => 'arrow-down.svg', ), 'arrow-left' => array( - 'label' => _x( 'Arrow Left', 'icon label' ), - 'filePath' => 'arrow-left.svg', + 'label' => _x( 'Arrow Left', 'icon label' ), + 'file_path' => 'arrow-left.svg', ), 'arrow-right' => array( - 'label' => _x( 'Arrow Right', 'icon label' ), - 'filePath' => 'arrow-right.svg', + 'label' => _x( 'Arrow Right', 'icon label' ), + 'file_path' => 'arrow-right.svg', ), 'arrow-up-left' => array( - 'label' => _x( 'Arrow Up Left', 'icon label' ), - 'filePath' => 'arrow-up-left.svg', + 'label' => _x( 'Arrow Up Left', 'icon label' ), + 'file_path' => 'arrow-up-left.svg', ), 'arrow-up-right' => array( - 'label' => _x( 'Arrow Up Right', 'icon label' ), - 'filePath' => 'arrow-up-right.svg', + 'label' => _x( 'Arrow Up Right', 'icon label' ), + 'file_path' => 'arrow-up-right.svg', ), 'arrow-up' => array( - 'label' => _x( 'Arrow Up', 'icon label' ), - 'filePath' => 'arrow-up.svg', + 'label' => _x( 'Arrow Up', 'icon label' ), + 'file_path' => 'arrow-up.svg', ), 'at-symbol' => array( - 'label' => _x( 'At Symbol (@)', 'icon label' ), - 'filePath' => 'at-symbol.svg', + 'label' => _x( 'At Symbol (@)', 'icon label' ), + 'file_path' => 'at-symbol.svg', ), 'audio' => array( - 'label' => _x( 'Audio', 'icon label' ), - 'filePath' => 'audio.svg', + 'label' => _x( 'Audio', 'icon label' ), + 'file_path' => 'audio.svg', ), 'bell' => array( - 'label' => _x( 'Bell', 'icon label' ), - 'filePath' => 'bell.svg', + 'label' => _x( 'Bell', 'icon label' ), + 'file_path' => 'bell.svg', ), 'block-default' => array( - 'label' => _x( 'Block Default', 'icon label' ), - 'filePath' => 'block-default.svg', + 'label' => _x( 'Block Default', 'icon label' ), + 'file_path' => 'block-default.svg', ), 'block-meta' => array( - 'label' => _x( 'Block Meta', 'icon label' ), - 'filePath' => 'block-meta.svg', + 'label' => _x( 'Block Meta', 'icon label' ), + 'file_path' => 'block-meta.svg', ), 'block-table' => array( - 'label' => _x( 'Block Table', 'icon label' ), - 'filePath' => 'block-table.svg', + 'label' => _x( 'Block Table', 'icon label' ), + 'file_path' => 'block-table.svg', ), 'calendar' => array( - 'label' => _x( 'Calendar', 'icon label' ), - 'filePath' => 'calendar.svg', + 'label' => _x( 'Calendar', 'icon label' ), + 'file_path' => 'calendar.svg', ), 'capture-photo' => array( - 'label' => _x( 'Capture Photo', 'icon label' ), - 'filePath' => 'capture-photo.svg', + 'label' => _x( 'Capture Photo', 'icon label' ), + 'file_path' => 'capture-photo.svg', ), 'capture-video' => array( - 'label' => _x( 'Capture Video', 'icon label' ), - 'filePath' => 'capture-video.svg', + 'label' => _x( 'Capture Video', 'icon label' ), + 'file_path' => 'capture-video.svg', ), 'cart' => array( - 'label' => _x( 'Cart', 'icon label' ), - 'filePath' => 'cart.svg', + 'label' => _x( 'Cart', 'icon label' ), + 'file_path' => 'cart.svg', ), 'category' => array( - 'label' => _x( 'Category', 'icon label' ), - 'filePath' => 'category.svg', + 'label' => _x( 'Category', 'icon label' ), + 'file_path' => 'category.svg', ), 'caution' => array( - 'label' => _x( 'Caution', 'icon label' ), - 'filePath' => 'caution.svg', + 'label' => _x( 'Caution', 'icon label' ), + 'file_path' => 'caution.svg', ), 'chart-bar' => array( - 'label' => _x( 'Chart Bar', 'icon label' ), - 'filePath' => 'chart-bar.svg', + 'label' => _x( 'Chart Bar', 'icon label' ), + 'file_path' => 'chart-bar.svg', ), 'check' => array( - 'label' => _x( 'Check', 'icon label' ), - 'filePath' => 'check.svg', + 'label' => _x( 'Check', 'icon label' ), + 'file_path' => 'check.svg', ), 'chevron-down' => array( - 'label' => _x( 'Chevron Down', 'icon label' ), - 'filePath' => 'chevron-down.svg', + 'label' => _x( 'Chevron Down', 'icon label' ), + 'file_path' => 'chevron-down.svg', ), 'chevron-down-small' => array( - 'label' => _x( 'Chevron Down Small', 'icon label' ), - 'filePath' => 'chevron-down-small.svg', + 'label' => _x( 'Chevron Down Small', 'icon label' ), + 'file_path' => 'chevron-down-small.svg', ), 'chevron-left' => array( - 'label' => _x( 'Chevron Left', 'icon label' ), - 'filePath' => 'chevron-left.svg', + 'label' => _x( 'Chevron Left', 'icon label' ), + 'file_path' => 'chevron-left.svg', ), 'chevron-left-small' => array( - 'label' => _x( 'Chevron Left Small', 'icon label' ), - 'filePath' => 'chevron-left-small.svg', + 'label' => _x( 'Chevron Left Small', 'icon label' ), + 'file_path' => 'chevron-left-small.svg', ), 'chevron-right' => array( - 'label' => _x( 'Chevron Right', 'icon label' ), - 'filePath' => 'chevron-right.svg', + 'label' => _x( 'Chevron Right', 'icon label' ), + 'file_path' => 'chevron-right.svg', ), 'chevron-right-small' => array( - 'label' => _x( 'Chevron Right Small', 'icon label' ), - 'filePath' => 'chevron-right-small.svg', + 'label' => _x( 'Chevron Right Small', 'icon label' ), + 'file_path' => 'chevron-right-small.svg', ), 'chevron-up' => array( - 'label' => _x( 'Chevron Up', 'icon label' ), - 'filePath' => 'chevron-up.svg', + 'label' => _x( 'Chevron Up', 'icon label' ), + 'file_path' => 'chevron-up.svg', ), 'chevron-up-down' => array( - 'label' => _x( 'Chevron Up Down', 'icon label' ), - 'filePath' => 'chevron-up-down.svg', + 'label' => _x( 'Chevron Up Down', 'icon label' ), + 'file_path' => 'chevron-up-down.svg', ), 'chevron-up-small' => array( - 'label' => _x( 'Chevron Up Small', 'icon label' ), - 'filePath' => 'chevron-up-small.svg', + 'label' => _x( 'Chevron Up Small', 'icon label' ), + 'file_path' => 'chevron-up-small.svg', ), 'comment' => array( - 'label' => _x( 'Comment', 'icon label' ), - 'filePath' => 'comment.svg', + 'label' => _x( 'Comment', 'icon label' ), + 'file_path' => 'comment.svg', ), 'cover' => array( - 'label' => _x( 'Cover', 'icon label' ), - 'filePath' => 'cover.svg', + 'label' => _x( 'Cover', 'icon label' ), + 'file_path' => 'cover.svg', ), 'create' => array( - 'label' => _x( 'Create', 'icon label' ), - 'filePath' => 'create.svg', + 'label' => _x( 'Create', 'icon label' ), + 'file_path' => 'create.svg', ), 'desktop' => array( - 'label' => _x( 'Desktop', 'icon label' ), - 'filePath' => 'desktop.svg', + 'label' => _x( 'Desktop', 'icon label' ), + 'file_path' => 'desktop.svg', ), 'download' => array( - 'label' => _x( 'Download', 'icon label' ), - 'filePath' => 'download.svg', + 'label' => _x( 'Download', 'icon label' ), + 'file_path' => 'download.svg', ), 'drawer-left' => array( - 'label' => _x( 'Drawer Left', 'icon label' ), - 'filePath' => 'drawer-left.svg', + 'label' => _x( 'Drawer Left', 'icon label' ), + 'file_path' => 'drawer-left.svg', ), 'drawer-right' => array( - 'label' => _x( 'Drawer Right', 'icon label' ), - 'filePath' => 'drawer-right.svg', + 'label' => _x( 'Drawer Right', 'icon label' ), + 'file_path' => 'drawer-right.svg', ), 'envelope' => array( - 'label' => _x( 'Envelope', 'icon label' ), - 'filePath' => 'envelope.svg', + 'label' => _x( 'Envelope', 'icon label' ), + 'file_path' => 'envelope.svg', ), 'error' => array( - 'label' => _x( 'Error', 'icon label' ), - 'filePath' => 'error.svg', + 'label' => _x( 'Error', 'icon label' ), + 'file_path' => 'error.svg', ), 'external' => array( - 'label' => _x( 'External', 'icon label' ), - 'filePath' => 'external.svg', + 'label' => _x( 'External', 'icon label' ), + 'file_path' => 'external.svg', ), 'file' => array( - 'label' => _x( 'File', 'icon label' ), - 'filePath' => 'file.svg', + 'label' => _x( 'File', 'icon label' ), + 'file_path' => 'file.svg', ), 'gallery' => array( - 'label' => _x( 'Gallery', 'icon label' ), - 'filePath' => 'gallery.svg', + 'label' => _x( 'Gallery', 'icon label' ), + 'file_path' => 'gallery.svg', ), 'group' => array( - 'label' => _x( 'Group', 'icon label' ), - 'filePath' => 'group.svg', + 'label' => _x( 'Group', 'icon label' ), + 'file_path' => 'group.svg', ), 'heading' => array( - 'label' => _x( 'Heading', 'icon label' ), - 'filePath' => 'heading.svg', + 'label' => _x( 'Heading', 'icon label' ), + 'file_path' => 'heading.svg', ), 'help' => array( - 'label' => _x( 'Help', 'icon label' ), - 'filePath' => 'help.svg', + 'label' => _x( 'Help', 'icon label' ), + 'file_path' => 'help.svg', ), 'home' => array( - 'label' => _x( 'Home', 'icon label' ), - 'filePath' => 'home.svg', + 'label' => _x( 'Home', 'icon label' ), + 'file_path' => 'home.svg', ), 'image' => array( - 'label' => _x( 'Image', 'icon label' ), - 'filePath' => 'image.svg', + 'label' => _x( 'Image', 'icon label' ), + 'file_path' => 'image.svg', ), 'info' => array( - 'label' => _x( 'Info', 'icon label' ), - 'filePath' => 'info.svg', + 'label' => _x( 'Info', 'icon label' ), + 'file_path' => 'info.svg', ), 'key' => array( - 'label' => _x( 'Key', 'icon label' ), - 'filePath' => 'key.svg', + 'label' => _x( 'Key', 'icon label' ), + 'file_path' => 'key.svg', ), 'language' => array( - 'label' => _x( 'Language', 'icon label' ), - 'filePath' => 'language.svg', + 'label' => _x( 'Language', 'icon label' ), + 'file_path' => 'language.svg', ), 'map-marker' => array( - 'label' => _x( 'Map Marker', 'icon label' ), - 'filePath' => 'map-marker.svg', + 'label' => _x( 'Map Marker', 'icon label' ), + 'file_path' => 'map-marker.svg', ), 'menu' => array( - 'label' => _x( 'Menu', 'icon label' ), - 'filePath' => 'menu.svg', + 'label' => _x( 'Menu', 'icon label' ), + 'file_path' => 'menu.svg', ), 'mobile' => array( - 'label' => _x( 'Mobile', 'icon label' ), - 'filePath' => 'mobile.svg', + 'label' => _x( 'Mobile', 'icon label' ), + 'file_path' => 'mobile.svg', ), 'more-horizontal' => array( - 'label' => _x( 'More Horizontal', 'icon label' ), - 'filePath' => 'more-horizontal.svg', + 'label' => _x( 'More Horizontal', 'icon label' ), + 'file_path' => 'more-horizontal.svg', ), 'more-vertical' => array( - 'label' => _x( 'More Vertical', 'icon label' ), - 'filePath' => 'more-vertical.svg', + 'label' => _x( 'More Vertical', 'icon label' ), + 'file_path' => 'more-vertical.svg', ), 'next' => array( - 'label' => _x( 'Next', 'icon label' ), - 'filePath' => 'next.svg', + 'label' => _x( 'Next', 'icon label' ), + 'file_path' => 'next.svg', ), 'paragraph' => array( - 'label' => _x( 'Paragraph', 'icon label' ), - 'filePath' => 'paragraph.svg', + 'label' => _x( 'Paragraph', 'icon label' ), + 'file_path' => 'paragraph.svg', ), 'payment' => array( - 'label' => _x( 'Payment', 'icon label' ), - 'filePath' => 'payment.svg', + 'label' => _x( 'Payment', 'icon label' ), + 'file_path' => 'payment.svg', ), 'pencil' => array( - 'label' => _x( 'Pencil', 'icon label' ), - 'filePath' => 'pencil.svg', + 'label' => _x( 'Pencil', 'icon label' ), + 'file_path' => 'pencil.svg', ), 'people' => array( - 'label' => _x( 'People', 'icon label' ), - 'filePath' => 'people.svg', + 'label' => _x( 'People', 'icon label' ), + 'file_path' => 'people.svg', ), 'plus' => array( - 'label' => _x( 'Plus', 'icon label' ), - 'filePath' => 'plus.svg', + 'label' => _x( 'Plus', 'icon label' ), + 'file_path' => 'plus.svg', ), 'plus-circle' => array( - 'label' => _x( 'Plus Circle', 'icon label' ), - 'filePath' => 'plus-circle.svg', + 'label' => _x( 'Plus Circle', 'icon label' ), + 'file_path' => 'plus-circle.svg', ), 'previous' => array( - 'label' => _x( 'Previous', 'icon label' ), - 'filePath' => 'previous.svg', + 'label' => _x( 'Previous', 'icon label' ), + 'file_path' => 'previous.svg', ), 'published' => array( - 'label' => _x( 'Published', 'icon label' ), - 'filePath' => 'published.svg', + 'label' => _x( 'Published', 'icon label' ), + 'file_path' => 'published.svg', ), 'quote' => array( - 'label' => _x( 'Quote', 'icon label' ), - 'filePath' => 'quote.svg', + 'label' => _x( 'Quote', 'icon label' ), + 'file_path' => 'quote.svg', ), 'receipt' => array( - 'label' => _x( 'Receipt', 'icon label' ), - 'filePath' => 'receipt.svg', + 'label' => _x( 'Receipt', 'icon label' ), + 'file_path' => 'receipt.svg', ), 'rss' => array( - 'label' => _x( 'RSS', 'icon label' ), - 'filePath' => 'rss.svg', + 'label' => _x( 'RSS', 'icon label' ), + 'file_path' => 'rss.svg', ), 'scheduled' => array( - 'label' => _x( 'Scheduled', 'icon label' ), - 'filePath' => 'scheduled.svg', + 'label' => _x( 'Scheduled', 'icon label' ), + 'file_path' => 'scheduled.svg', ), 'search' => array( - 'label' => _x( 'Search', 'icon label' ), - 'filePath' => 'search.svg', + 'label' => _x( 'Search', 'icon label' ), + 'file_path' => 'search.svg', ), 'settings' => array( - 'label' => _x( 'Settings', 'icon label' ), - 'filePath' => 'settings.svg', + 'label' => _x( 'Settings', 'icon label' ), + 'file_path' => 'settings.svg', ), 'shadow' => array( - 'label' => _x( 'Shadow', 'icon label' ), - 'filePath' => 'shadow.svg', + 'label' => _x( 'Shadow', 'icon label' ), + 'file_path' => 'shadow.svg', ), 'share' => array( - 'label' => _x( 'Share', 'icon label' ), - 'filePath' => 'share.svg', + 'label' => _x( 'Share', 'icon label' ), + 'file_path' => 'share.svg', ), 'shield' => array( - 'label' => _x( 'Shield', 'icon label' ), - 'filePath' => 'shield.svg', + 'label' => _x( 'Shield', 'icon label' ), + 'file_path' => 'shield.svg', ), 'shuffle' => array( - 'label' => _x( 'Shuffle', 'icon label' ), - 'filePath' => 'shuffle.svg', + 'label' => _x( 'Shuffle', 'icon label' ), + 'file_path' => 'shuffle.svg', ), 'star-empty' => array( - 'label' => _x( 'Star Empty', 'icon label' ), - 'filePath' => 'star-empty.svg', + 'label' => _x( 'Star Empty', 'icon label' ), + 'file_path' => 'star-empty.svg', ), 'star-filled' => array( - 'label' => _x( 'Star Filled', 'icon label' ), - 'filePath' => 'star-filled.svg', + 'label' => _x( 'Star Filled', 'icon label' ), + 'file_path' => 'star-filled.svg', ), 'star-half' => array( - 'label' => _x( 'Star Half', 'icon label' ), - 'filePath' => 'star-half.svg', + 'label' => _x( 'Star Half', 'icon label' ), + 'file_path' => 'star-half.svg', ), 'store' => array( - 'label' => _x( 'Store', 'icon label' ), - 'filePath' => 'store.svg', + 'label' => _x( 'Store', 'icon label' ), + 'file_path' => 'store.svg', ), 'styles' => array( - 'label' => _x( 'Styles', 'icon label' ), - 'filePath' => 'styles.svg', + 'label' => _x( 'Styles', 'icon label' ), + 'file_path' => 'styles.svg', ), 'symbol' => array( - 'label' => _x( 'Symbol', 'icon label' ), - 'filePath' => 'symbol.svg', + 'label' => _x( 'Symbol', 'icon label' ), + 'file_path' => 'symbol.svg', ), 'symbol-filled' => array( - 'label' => _x( 'Symbol Filled', 'icon label' ), - 'filePath' => 'symbol-filled.svg', + 'label' => _x( 'Symbol Filled', 'icon label' ), + 'file_path' => 'symbol-filled.svg', ), 'table' => array( - 'label' => _x( 'Table', 'icon label' ), - 'filePath' => 'table.svg', + 'label' => _x( 'Table', 'icon label' ), + 'file_path' => 'table.svg', ), 'tablet' => array( - 'label' => _x( 'Tablet', 'icon label' ), - 'filePath' => 'tablet.svg', + 'label' => _x( 'Tablet', 'icon label' ), + 'file_path' => 'tablet.svg', ), 'tag' => array( - 'label' => _x( 'Tag', 'icon label' ), - 'filePath' => 'tag.svg', + 'label' => _x( 'Tag', 'icon label' ), + 'file_path' => 'tag.svg', ), 'tip' => array( - 'label' => _x( 'Tip', 'icon label' ), - 'filePath' => 'tip.svg', + 'label' => _x( 'Tip', 'icon label' ), + 'file_path' => 'tip.svg', ), 'upload' => array( - 'label' => _x( 'Upload', 'icon label' ), - 'filePath' => 'upload.svg', + 'label' => _x( 'Upload', 'icon label' ), + 'file_path' => 'upload.svg', ), 'verse' => array( - 'label' => _x( 'Verse', 'icon label' ), - 'filePath' => 'verse.svg', + 'label' => _x( 'Verse', 'icon label' ), + 'file_path' => 'verse.svg', ), ); diff --git a/src/wp-includes/class-wp-icons-registry.php b/src/wp-includes/class-wp-icons-registry.php index a442a2f99af94..d09f1afb9f507 100644 --- a/src/wp-includes/class-wp-icons-registry.php +++ b/src/wp-includes/class-wp-icons-registry.php @@ -67,12 +67,12 @@ protected function __construct() { foreach ( $collection as $icon_name => $icon_data ) { if ( - empty( $icon_data['filePath'] ) - || ! is_string( $icon_data['filePath'] ) + empty( $icon_data['file_path'] ) + || ! is_string( $icon_data['file_path'] ) ) { _doing_it_wrong( __METHOD__, - __( 'Core icon collection manifest must provide valid a "filePath" for each icon.' ), + __( 'Core icon collection manifest must provide valid a "file_path" for each icon.' ), '7.0.0' ); return; From 97e9c82de0ba147d12b14ec1449e3f8e05f73969 Mon Sep 17 00:00:00 2001 From: Aki Hamano Date: Thu, 11 Jun 2026 12:20:13 +0900 Subject: [PATCH 2/3] Icons: Update manifest copy task for the renamed file_path key. Following the upstream Gutenberg rename of the icon manifest key from filePath to file_path (WordPress/gutenberg#79100), adjust the copy:icon-library-manifest Grunt task to match the new file_path key when stripping the 'library/' path prefix, so regeneration keeps producing valid icon paths. Co-Authored-By: Claude --- Gruntfile.js | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/Gruntfile.js b/Gruntfile.js index 815ccce3af535..5b84076941a40 100644 --- a/Gruntfile.js +++ b/Gruntfile.js @@ -763,11 +763,11 @@ module.exports = function(grunt) { /_x\(\s*([^,]+),\s*([^,]+),\s*['"]gutenberg['"]\s*\)/g, '_x( $1, $2 )' ) - // Strip the 'library/' prefix from filePath values so they + // Strip the 'library/' prefix from file_path values so they // resolve correctly relative to wp-includes/images/icon-library/. .replace( - /'filePath' => 'library\//g, - '\'filePath\' => \'' + /'file_path' => 'library\//g, + '\'file_path\' => \'' ); } }, From df1868a1839b854e43c988812ac56ad417736926 Mon Sep 17 00:00:00 2001 From: Aki Hamano Date: Thu, 11 Jun 2026 15:54:39 +0900 Subject: [PATCH 3/3] Icons: Add show_in_rest support to gate REST API exposure. Introduce a `show_in_rest` icon property so that REST visibility can be controlled independently from registry membership. The registry accepts and validates the boolean property, while the REST controller filters listings and single-icon requests to icons flagged for REST exposure. This allows all manifest icons to be registered for internal use while exposing only a subset through the public REST API. Co-Authored-By: Claude --- src/wp-includes/class-wp-icons-registry.php | 23 ++++++++++++++----- .../class-wp-rest-icons-controller.php | 5 +++- 2 files changed, 21 insertions(+), 7 deletions(-) diff --git a/src/wp-includes/class-wp-icons-registry.php b/src/wp-includes/class-wp-icons-registry.php index d09f1afb9f507..fbc9cbd734222 100644 --- a/src/wp-includes/class-wp-icons-registry.php +++ b/src/wp-includes/class-wp-icons-registry.php @@ -83,6 +83,7 @@ protected function __construct() { array( 'label' => $icon_data['label'], 'file_path' => $icons_directory . $icon_data['filePath'], + 'show_in_rest' => ! empty( $icon_data['show_in_rest'] ), ) ); } @@ -97,11 +98,12 @@ protected function __construct() { * @param array $icon_properties { * List of properties for the icon. * - * @type string $label Required. A human-readable label for the icon. - * @type string $content Optional. SVG markup for the icon. - * 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 string $label Required. A human-readable label for the icon. + * @type string $content Optional. SVG markup for the icon. + * 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 $show_in_rest Optional. Whether the icon is available via the REST API. Default false. * } * @return bool True if the icon was registered with success and false otherwise. */ @@ -115,7 +117,7 @@ protected function register( $icon_name, $icon_properties ) { return false; } - $allowed_keys = array_fill_keys( array( 'label', 'content', 'file_path' ), 1 ); + $allowed_keys = array_fill_keys( array( 'label', 'content', 'file_path', 'show_in_rest' ), 1 ); foreach ( array_keys( $icon_properties ) as $key ) { if ( ! array_key_exists( $key, $allowed_keys ) ) { _doing_it_wrong( @@ -140,6 +142,15 @@ protected function register( $icon_name, $icon_properties ) { return false; } + if ( isset( $icon_properties['show_in_rest'] ) && ! is_bool( $icon_properties['show_in_rest'] ) ) { + _doing_it_wrong( + __METHOD__, + __( 'Icon "show_in_rest" property must be a boolean.' ), + '7.0.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/src/wp-includes/rest-api/endpoints/class-wp-rest-icons-controller.php b/src/wp-includes/rest-api/endpoints/class-wp-rest-icons-controller.php index 91126b498d338..6fcdd3128d1d0 100644 --- a/src/wp-includes/rest-api/endpoints/class-wp-rest-icons-controller.php +++ b/src/wp-includes/rest-api/endpoints/class-wp-rest-icons-controller.php @@ -131,6 +131,9 @@ public function get_items( $request ) { $search = $request->get_param( 'search' ); $icons = WP_Icons_Registry::get_instance()->get_registered_icons( $search ); foreach ( $icons as $icon ) { + if ( empty( $icon['show_in_rest'] ) ) { + continue; + } $prepared_icon = $this->prepare_item_for_response( $icon, $request ); $response[] = $this->prepare_response_for_collection( $prepared_icon ); } @@ -167,7 +170,7 @@ public function get_icon( $name ) { $registry = WP_Icons_Registry::get_instance(); $icon = $registry->get_registered_icon( $name ); - if ( null === $icon ) { + if ( null === $icon || empty( $icon['show_in_rest'] ) ) { return new WP_Error( 'rest_icon_not_found', sprintf(