From b80ba269f6cf0b0600be49b89b9a926421af88ee Mon Sep 17 00:00:00 2001 From: Timothy Jacobs Date: Sun, 11 Sep 2022 23:28:39 +0000 Subject: [PATCH] REST API: Add support for settings to specify their own additionalProperties. This switches the Settings Controller to use `rest_default_additional_properties_to_false` and deprecates its own method. Props anna.bansaghi. Fixes #56493. git-svn-id: https://develop.svn.wordpress.org/trunk@54131 602fd350-edb4-49c9-b593-d223f7449a82 --- .../class-wp-rest-settings-controller.php | 23 +++------- .../rest-api/rest-settings-controller.php | 46 +++++++++++++++++++ 2 files changed, 53 insertions(+), 16 deletions(-) diff --git a/src/wp-includes/rest-api/endpoints/class-wp-rest-settings-controller.php b/src/wp-includes/rest-api/endpoints/class-wp-rest-settings-controller.php index 157c49acbe..1c83f5caea 100644 --- a/src/wp-includes/rest-api/endpoints/class-wp-rest-settings-controller.php +++ b/src/wp-includes/rest-api/endpoints/class-wp-rest-settings-controller.php @@ -258,7 +258,7 @@ class WP_REST_Settings_Controller extends WP_REST_Controller { continue; } - $rest_args['schema'] = $this->set_additional_properties_to_false( $rest_args['schema'] ); + $rest_args['schema'] = rest_default_additional_properties_to_false( $rest_args['schema'] ); $rest_options[ $rest_args['name'] ] = $rest_args; } @@ -322,31 +322,22 @@ class WP_REST_Settings_Controller extends WP_REST_Controller { } /** - * Recursively add additionalProperties = false to all objects in a schema. + * Recursively add additionalProperties = false to all objects in a schema + * if no additionalProperties setting is specified. * - * This is need to restrict properties of objects in settings values to only + * This is needed to restrict properties of objects in settings values to only * registered items, as the REST API will allow additional properties by * default. * * @since 4.9.0 + * @deprecated 6.1.0 Use {@see rest_default_additional_properties_to_false()} instead. * * @param array $schema The schema array. * @return array */ protected function set_additional_properties_to_false( $schema ) { - switch ( $schema['type'] ) { - case 'object': - foreach ( $schema['properties'] as $key => $child_schema ) { - $schema['properties'][ $key ] = $this->set_additional_properties_to_false( $child_schema ); - } + _deprecated_function( __METHOD__, '6.1.0', 'rest_default_additional_properties_to_false()' ); - $schema['additionalProperties'] = false; - break; - case 'array': - $schema['items'] = $this->set_additional_properties_to_false( $schema['items'] ); - break; - } - - return $schema; + return rest_default_additional_properties_to_false( $schema ); } } diff --git a/tests/phpunit/tests/rest-api/rest-settings-controller.php b/tests/phpunit/tests/rest-api/rest-settings-controller.php index b054236270..60a5f28c8d 100644 --- a/tests/phpunit/tests/rest-api/rest-settings-controller.php +++ b/tests/phpunit/tests/rest-api/rest-settings-controller.php @@ -737,4 +737,50 @@ class WP_Test_REST_Settings_Controller extends WP_Test_REST_Controller_Testcase ) ); } + + /** + * @ticket 56493 + */ + public function test_register_setting_with_custom_additional_properties_value() { + wp_set_current_user( self::$administrator ); + + register_setting( + 'somegroup', + 'mycustomsetting', + array( + 'type' => 'object', + 'show_in_rest' => array( + 'schema' => array( + 'type' => 'object', + 'properties' => array( + 'test1' => array( + 'type' => 'string', + ), + ), + 'additionalProperties' => array( + 'type' => 'integer', + ), + ), + ), + ) + ); + + $data = array( + 'mycustomsetting' => array( + 'test1' => 'my-string', + 'test2' => '2', + 'test3' => 3, + ), + ); + $request = new WP_REST_Request( 'PUT', '/wp/v2/settings' ); + $request->add_header( 'content-type', 'application/json' ); + $request->set_body( wp_json_encode( $data ) ); + + $response = rest_do_request( $request ); + + $this->assertSame( 200, $response->get_status() ); + $this->assertSame( 'my-string', $response->data['mycustomsetting']['test1'] ); + $this->assertSame( 2, $response->data['mycustomsetting']['test2'] ); + $this->assertSame( 3, $response->data['mycustomsetting']['test3'] ); + } }