[wp-trac] [WordPress Trac] #64926: REST API: GET requests fail object/array schema validation when params are JSON-serialized strings
WordPress Trac
noreply at wordpress.org
Thu Apr 2 11:52:07 UTC 2026
#64926: REST API: GET requests fail object/array schema validation when params are
JSON-serialized strings
-------------------------+-------------------------------------------------
Reporter: dsmy | Owner: (none)
Type: defect | Status: new
(bug) |
Priority: normal | Milestone: Awaiting Review
Component: REST API | Version:
Severity: normal | Resolution:
Keywords: has-patch | Focuses: javascript, rest-api, php-
| compatibility
-------------------------+-------------------------------------------------
Comment (by abcd95):
This is what I came up wtih -
{{{
diff --git a/src/wp-includes/rest-api.php b/src/wp-includes/rest-api.php
index c524f9e22a..e62c1f2586 100644
--- a/src/wp-includes/rest-api.php
+++ b/src/wp-includes/rest-api.php
@@ -2243,9 +2243,32 @@ function rest_validate_value_from_schema( $value,
$args, $param = '' ) {
$is_valid =
rest_validate_boolean_value_from_schema( $value, $param );
break;
case 'object':
+ /*
+ * A JSON-encoded string (e.g. from a GET query
parameter) should be
+ * decoded before validation, mirroring what
parse_json_params() does
+ * for application/json request bodies.
+ */
+ if ( is_string( $value ) ) {
+ $decoded = json_decode( $value, true );
+ if ( null !== $decoded && JSON_ERROR_NONE
=== json_last_error() ) {
+ $value = $decoded;
+ }
+ }
$is_valid =
rest_validate_object_value_from_schema( $value, $args, $param );
break;
case 'array':
+ /*
+ * A JSON-encoded string (e.g. ?ids=[1,2,3])
should be decoded before
+ * validation. This takes priority over the comma-
separated-value
+ * fallback in rest_is_array() / wp_parse_list(),
which cannot
+ * preserve value types.
+ */
+ if ( is_string( $value ) && str_starts_with(
ltrim( $value ), '[' ) ) {
+ $decoded = json_decode( $value, true );
+ if ( is_array( $decoded ) &&
JSON_ERROR_NONE === json_last_error() ) {
+ $value = $decoded;
+ }
+ }
$is_valid = rest_validate_array_value_from_schema(
$value, $args, $param );
break;
case 'number':
@@ -2833,6 +2856,19 @@ function rest_sanitize_value_from_schema( $value,
$args, $param = '' ) {
}
if ( 'array' === $args['type'] ) {
+ /*
+ * A JSON-encoded string (e.g. ?ids=[1,2,3]) should be
decoded before
+ * sanitization. This takes priority over the comma-
separated-value
+ * fallback in rest_sanitize_array() / wp_parse_list(),
which cannot
+ * preserve value types.
+ */
+ if ( is_string( $value ) && str_starts_with( ltrim( $value
), '[' ) ) {
+ $decoded = json_decode( $value, true );
+ if ( is_array( $decoded ) && JSON_ERROR_NONE ===
json_last_error() ) {
+ $value = $decoded;
+ }
+ }
+
$value = rest_sanitize_array( $value );
if ( ! empty( $args['items'] ) ) {
@@ -2850,6 +2886,18 @@ function rest_sanitize_value_from_schema( $value,
$args, $param = '' ) {
}
if ( 'object' === $args['type'] ) {
+ /*
+ * A JSON-encoded string (e.g. from a GET query parameter)
should be
+ * decoded before sanitization, mirroring what
parse_json_params() does
+ * for application/json request bodies.
+ */
+ if ( is_string( $value ) ) {
+ $decoded = json_decode( $value, true );
+ if ( null !== $decoded && JSON_ERROR_NONE ===
json_last_error() ) {
+ $value = $decoded;
+ }
+ }
+
$value = rest_sanitize_object( $value );
foreach ( $value as $property => $v ) {
}}}
--
Ticket URL: <https://core.trac.wordpress.org/ticket/64926#comment:23>
WordPress Trac <https://core.trac.wordpress.org/>
WordPress publishing platform
More information about the wp-trac
mailing list