[ Index ] |
PHP Cross Reference of WordPress |
[Summary view] [Print] [Text view]
1 <?php 2 /** 3 * REST API: WP_REST_Users_Controller class 4 * 5 * @package WordPress 6 * @subpackage REST_API 7 * @since 4.7.0 8 */ 9 10 /** 11 * Core class used to manage users via the REST API. 12 * 13 * @since 4.7.0 14 * 15 * @see WP_REST_Controller 16 */ 17 class WP_REST_Users_Controller extends WP_REST_Controller { 18 19 /** 20 * Instance of a user meta fields object. 21 * 22 * @since 4.7.0 23 * @var WP_REST_User_Meta_Fields 24 */ 25 protected $meta; 26 27 /** 28 * Constructor. 29 * 30 * @since 4.7.0 31 */ 32 public function __construct() { 33 $this->namespace = 'wp/v2'; 34 $this->rest_base = 'users'; 35 36 $this->meta = new WP_REST_User_Meta_Fields(); 37 } 38 39 /** 40 * Registers the routes for the objects of the controller. 41 * 42 * @since 4.7.0 43 * 44 * @see register_rest_route() 45 */ 46 public function register_routes() { 47 48 register_rest_route( 49 $this->namespace, 50 '/' . $this->rest_base, 51 array( 52 array( 53 'methods' => WP_REST_Server::READABLE, 54 'callback' => array( $this, 'get_items' ), 55 'permission_callback' => array( $this, 'get_items_permissions_check' ), 56 'args' => $this->get_collection_params(), 57 ), 58 array( 59 'methods' => WP_REST_Server::CREATABLE, 60 'callback' => array( $this, 'create_item' ), 61 'permission_callback' => array( $this, 'create_item_permissions_check' ), 62 'args' => $this->get_endpoint_args_for_item_schema( WP_REST_Server::CREATABLE ), 63 ), 64 'schema' => array( $this, 'get_public_item_schema' ), 65 ) 66 ); 67 68 register_rest_route( 69 $this->namespace, 70 '/' . $this->rest_base . '/(?P<id>[\d]+)', 71 array( 72 'args' => array( 73 'id' => array( 74 'description' => __( 'Unique identifier for the user.' ), 75 'type' => 'integer', 76 ), 77 ), 78 array( 79 'methods' => WP_REST_Server::READABLE, 80 'callback' => array( $this, 'get_item' ), 81 'permission_callback' => array( $this, 'get_item_permissions_check' ), 82 'args' => array( 83 'context' => $this->get_context_param( array( 'default' => 'view' ) ), 84 ), 85 ), 86 array( 87 'methods' => WP_REST_Server::EDITABLE, 88 'callback' => array( $this, 'update_item' ), 89 'permission_callback' => array( $this, 'update_item_permissions_check' ), 90 'args' => $this->get_endpoint_args_for_item_schema( WP_REST_Server::EDITABLE ), 91 ), 92 array( 93 'methods' => WP_REST_Server::DELETABLE, 94 'callback' => array( $this, 'delete_item' ), 95 'permission_callback' => array( $this, 'delete_item_permissions_check' ), 96 'args' => array( 97 'force' => array( 98 'type' => 'boolean', 99 'default' => false, 100 'description' => __( 'Required to be true, as users do not support trashing.' ), 101 ), 102 'reassign' => array( 103 'type' => 'integer', 104 'description' => __( 'Reassign the deleted user\'s posts and links to this user ID.' ), 105 'required' => true, 106 'sanitize_callback' => array( $this, 'check_reassign' ), 107 ), 108 ), 109 ), 110 'schema' => array( $this, 'get_public_item_schema' ), 111 ) 112 ); 113 114 register_rest_route( 115 $this->namespace, 116 '/' . $this->rest_base . '/me', 117 array( 118 array( 119 'methods' => WP_REST_Server::READABLE, 120 'permission_callback' => '__return_true', 121 'callback' => array( $this, 'get_current_item' ), 122 'args' => array( 123 'context' => $this->get_context_param( array( 'default' => 'view' ) ), 124 ), 125 ), 126 array( 127 'methods' => WP_REST_Server::EDITABLE, 128 'callback' => array( $this, 'update_current_item' ), 129 'permission_callback' => array( $this, 'update_current_item_permissions_check' ), 130 'args' => $this->get_endpoint_args_for_item_schema( WP_REST_Server::EDITABLE ), 131 ), 132 array( 133 'methods' => WP_REST_Server::DELETABLE, 134 'callback' => array( $this, 'delete_current_item' ), 135 'permission_callback' => array( $this, 'delete_current_item_permissions_check' ), 136 'args' => array( 137 'force' => array( 138 'type' => 'boolean', 139 'default' => false, 140 'description' => __( 'Required to be true, as users do not support trashing.' ), 141 ), 142 'reassign' => array( 143 'type' => 'integer', 144 'description' => __( 'Reassign the deleted user\'s posts and links to this user ID.' ), 145 'required' => true, 146 'sanitize_callback' => array( $this, 'check_reassign' ), 147 ), 148 ), 149 ), 150 'schema' => array( $this, 'get_public_item_schema' ), 151 ) 152 ); 153 } 154 155 /** 156 * Checks for a valid value for the reassign parameter when deleting users. 157 * 158 * The value can be an integer, 'false', false, or ''. 159 * 160 * @since 4.7.0 161 * 162 * @param int|bool $value The value passed to the reassign parameter. 163 * @param WP_REST_Request $request Full details about the request. 164 * @param string $param The parameter that is being sanitized. 165 * @return int|bool|WP_Error 166 */ 167 public function check_reassign( $value, $request, $param ) { 168 if ( is_numeric( $value ) ) { 169 return $value; 170 } 171 172 if ( empty( $value ) || false === $value || 'false' === $value ) { 173 return false; 174 } 175 176 return new WP_Error( 177 'rest_invalid_param', 178 __( 'Invalid user parameter(s).' ), 179 array( 'status' => 400 ) 180 ); 181 } 182 183 /** 184 * Permissions check for getting all users. 185 * 186 * @since 4.7.0 187 * 188 * @param WP_REST_Request $request Full details about the request. 189 * @return true|WP_Error True if the request has read access, otherwise WP_Error object. 190 */ 191 public function get_items_permissions_check( $request ) { 192 // Check if roles is specified in GET request and if user can list users. 193 if ( ! empty( $request['roles'] ) && ! current_user_can( 'list_users' ) ) { 194 return new WP_Error( 195 'rest_user_cannot_view', 196 __( 'Sorry, you are not allowed to filter users by role.' ), 197 array( 'status' => rest_authorization_required_code() ) 198 ); 199 } 200 201 if ( 'edit' === $request['context'] && ! current_user_can( 'list_users' ) ) { 202 return new WP_Error( 203 'rest_forbidden_context', 204 __( 'Sorry, you are not allowed to list users.' ), 205 array( 'status' => rest_authorization_required_code() ) 206 ); 207 } 208 209 if ( in_array( $request['orderby'], array( 'email', 'registered_date' ), true ) && ! current_user_can( 'list_users' ) ) { 210 return new WP_Error( 211 'rest_forbidden_orderby', 212 __( 'Sorry, you are not allowed to order users by this parameter.' ), 213 array( 'status' => rest_authorization_required_code() ) 214 ); 215 } 216 217 if ( 'authors' === $request['who'] ) { 218 $types = get_post_types( array( 'show_in_rest' => true ), 'objects' ); 219 220 foreach ( $types as $type ) { 221 if ( post_type_supports( $type->name, 'author' ) 222 && current_user_can( $type->cap->edit_posts ) ) { 223 return true; 224 } 225 } 226 227 return new WP_Error( 228 'rest_forbidden_who', 229 __( 'Sorry, you are not allowed to query users by this parameter.' ), 230 array( 'status' => rest_authorization_required_code() ) 231 ); 232 } 233 234 return true; 235 } 236 237 /** 238 * Retrieves all users. 239 * 240 * @since 4.7.0 241 * 242 * @param WP_REST_Request $request Full details about the request. 243 * @return WP_REST_Response|WP_Error Response object on success, or WP_Error object on failure. 244 */ 245 public function get_items( $request ) { 246 247 // Retrieve the list of registered collection query parameters. 248 $registered = $this->get_collection_params(); 249 250 /* 251 * This array defines mappings between public API query parameters whose 252 * values are accepted as-passed, and their internal WP_Query parameter 253 * name equivalents (some are the same). Only values which are also 254 * present in $registered will be set. 255 */ 256 $parameter_mappings = array( 257 'exclude' => 'exclude', 258 'include' => 'include', 259 'order' => 'order', 260 'per_page' => 'number', 261 'search' => 'search', 262 'roles' => 'role__in', 263 'slug' => 'nicename__in', 264 ); 265 266 $prepared_args = array(); 267 268 /* 269 * For each known parameter which is both registered and present in the request, 270 * set the parameter's value on the query $prepared_args. 271 */ 272 foreach ( $parameter_mappings as $api_param => $wp_param ) { 273 if ( isset( $registered[ $api_param ], $request[ $api_param ] ) ) { 274 $prepared_args[ $wp_param ] = $request[ $api_param ]; 275 } 276 } 277 278 if ( isset( $registered['offset'] ) && ! empty( $request['offset'] ) ) { 279 $prepared_args['offset'] = $request['offset']; 280 } else { 281 $prepared_args['offset'] = ( $request['page'] - 1 ) * $prepared_args['number']; 282 } 283 284 if ( isset( $registered['orderby'] ) ) { 285 $orderby_possibles = array( 286 'id' => 'ID', 287 'include' => 'include', 288 'name' => 'display_name', 289 'registered_date' => 'registered', 290 'slug' => 'user_nicename', 291 'include_slugs' => 'nicename__in', 292 'email' => 'user_email', 293 'url' => 'user_url', 294 ); 295 $prepared_args['orderby'] = $orderby_possibles[ $request['orderby'] ]; 296 } 297 298 if ( isset( $registered['who'] ) && ! empty( $request['who'] ) && 'authors' === $request['who'] ) { 299 $prepared_args['who'] = 'authors'; 300 } elseif ( ! current_user_can( 'list_users' ) ) { 301 $prepared_args['has_published_posts'] = get_post_types( array( 'show_in_rest' => true ), 'names' ); 302 } 303 304 if ( ! empty( $prepared_args['search'] ) ) { 305 $prepared_args['search'] = '*' . $prepared_args['search'] . '*'; 306 } 307 /** 308 * Filters WP_User_Query arguments when querying users via the REST API. 309 * 310 * @link https://developer.wordpress.org/reference/classes/wp_user_query/ 311 * 312 * @since 4.7.0 313 * 314 * @param array $prepared_args Array of arguments for WP_User_Query. 315 * @param WP_REST_Request $request The REST API request. 316 */ 317 $prepared_args = apply_filters( 'rest_user_query', $prepared_args, $request ); 318 319 $query = new WP_User_Query( $prepared_args ); 320 321 $users = array(); 322 323 foreach ( $query->results as $user ) { 324 $data = $this->prepare_item_for_response( $user, $request ); 325 $users[] = $this->prepare_response_for_collection( $data ); 326 } 327 328 $response = rest_ensure_response( $users ); 329 330 // Store pagination values for headers then unset for count query. 331 $per_page = (int) $prepared_args['number']; 332 $page = ceil( ( ( (int) $prepared_args['offset'] ) / $per_page ) + 1 ); 333 334 $prepared_args['fields'] = 'ID'; 335 336 $total_users = $query->get_total(); 337 338 if ( $total_users < 1 ) { 339 // Out-of-bounds, run the query again without LIMIT for total count. 340 unset( $prepared_args['number'], $prepared_args['offset'] ); 341 $count_query = new WP_User_Query( $prepared_args ); 342 $total_users = $count_query->get_total(); 343 } 344 345 $response->header( 'X-WP-Total', (int) $total_users ); 346 347 $max_pages = ceil( $total_users / $per_page ); 348 349 $response->header( 'X-WP-TotalPages', (int) $max_pages ); 350 351 $base = add_query_arg( urlencode_deep( $request->get_query_params() ), rest_url( sprintf( '%s/%s', $this->namespace, $this->rest_base ) ) ); 352 if ( $page > 1 ) { 353 $prev_page = $page - 1; 354 355 if ( $prev_page > $max_pages ) { 356 $prev_page = $max_pages; 357 } 358 359 $prev_link = add_query_arg( 'page', $prev_page, $base ); 360 $response->link_header( 'prev', $prev_link ); 361 } 362 if ( $max_pages > $page ) { 363 $next_page = $page + 1; 364 $next_link = add_query_arg( 'page', $next_page, $base ); 365 366 $response->link_header( 'next', $next_link ); 367 } 368 369 return $response; 370 } 371 372 /** 373 * Get the user, if the ID is valid. 374 * 375 * @since 4.7.2 376 * 377 * @param int $id Supplied ID. 378 * @return WP_User|WP_Error True if ID is valid, WP_Error otherwise. 379 */ 380 protected function get_user( $id ) { 381 $error = new WP_Error( 382 'rest_user_invalid_id', 383 __( 'Invalid user ID.' ), 384 array( 'status' => 404 ) 385 ); 386 387 if ( (int) $id <= 0 ) { 388 return $error; 389 } 390 391 $user = get_userdata( (int) $id ); 392 if ( empty( $user ) || ! $user->exists() ) { 393 return $error; 394 } 395 396 if ( is_multisite() && ! is_user_member_of_blog( $user->ID ) ) { 397 return $error; 398 } 399 400 return $user; 401 } 402 403 /** 404 * Checks if a given request has access to read a user. 405 * 406 * @since 4.7.0 407 * 408 * @param WP_REST_Request $request Full details about the request. 409 * @return true|WP_Error True if the request has read access for the item, otherwise WP_Error object. 410 */ 411 public function get_item_permissions_check( $request ) { 412 $user = $this->get_user( $request['id'] ); 413 if ( is_wp_error( $user ) ) { 414 return $user; 415 } 416 417 $types = get_post_types( array( 'show_in_rest' => true ), 'names' ); 418 419 if ( get_current_user_id() === $user->ID ) { 420 return true; 421 } 422 423 if ( 'edit' === $request['context'] && ! current_user_can( 'list_users' ) ) { 424 return new WP_Error( 425 'rest_user_cannot_view', 426 __( 'Sorry, you are not allowed to list users.' ), 427 array( 'status' => rest_authorization_required_code() ) 428 ); 429 } elseif ( ! count_user_posts( $user->ID, $types ) && ! current_user_can( 'edit_user', $user->ID ) && ! current_user_can( 'list_users' ) ) { 430 return new WP_Error( 431 'rest_user_cannot_view', 432 __( 'Sorry, you are not allowed to list users.' ), 433 array( 'status' => rest_authorization_required_code() ) 434 ); 435 } 436 437 return true; 438 } 439 440 /** 441 * Retrieves a single user. 442 * 443 * @since 4.7.0 444 * 445 * @param WP_REST_Request $request Full details about the request. 446 * @return WP_REST_Response|WP_Error Response object on success, or WP_Error object on failure. 447 */ 448 public function get_item( $request ) { 449 $user = $this->get_user( $request['id'] ); 450 if ( is_wp_error( $user ) ) { 451 return $user; 452 } 453 454 $user = $this->prepare_item_for_response( $user, $request ); 455 $response = rest_ensure_response( $user ); 456 457 return $response; 458 } 459 460 /** 461 * Retrieves the current user. 462 * 463 * @since 4.7.0 464 * 465 * @param WP_REST_Request $request Full details about the request. 466 * @return WP_REST_Response|WP_Error Response object on success, or WP_Error object on failure. 467 */ 468 public function get_current_item( $request ) { 469 $current_user_id = get_current_user_id(); 470 471 if ( empty( $current_user_id ) ) { 472 return new WP_Error( 473 'rest_not_logged_in', 474 __( 'You are not currently logged in.' ), 475 array( 'status' => 401 ) 476 ); 477 } 478 479 $user = wp_get_current_user(); 480 $response = $this->prepare_item_for_response( $user, $request ); 481 $response = rest_ensure_response( $response ); 482 483 return $response; 484 } 485 486 /** 487 * Checks if a given request has access create users. 488 * 489 * @since 4.7.0 490 * 491 * @param WP_REST_Request $request Full details about the request. 492 * @return true|WP_Error True if the request has access to create items, WP_Error object otherwise. 493 */ 494 public function create_item_permissions_check( $request ) { 495 496 if ( ! current_user_can( 'create_users' ) ) { 497 return new WP_Error( 498 'rest_cannot_create_user', 499 __( 'Sorry, you are not allowed to create new users.' ), 500 array( 'status' => rest_authorization_required_code() ) 501 ); 502 } 503 504 return true; 505 } 506 507 /** 508 * Creates a single user. 509 * 510 * @since 4.7.0 511 * 512 * @param WP_REST_Request $request Full details about the request. 513 * @return WP_REST_Response|WP_Error Response object on success, or WP_Error object on failure. 514 */ 515 public function create_item( $request ) { 516 if ( ! empty( $request['id'] ) ) { 517 return new WP_Error( 518 'rest_user_exists', 519 __( 'Cannot create existing user.' ), 520 array( 'status' => 400 ) 521 ); 522 } 523 524 $schema = $this->get_item_schema(); 525 526 if ( ! empty( $request['roles'] ) && ! empty( $schema['properties']['roles'] ) ) { 527 $check_permission = $this->check_role_update( $request['id'], $request['roles'] ); 528 529 if ( is_wp_error( $check_permission ) ) { 530 return $check_permission; 531 } 532 } 533 534 $user = $this->prepare_item_for_database( $request ); 535 536 if ( is_multisite() ) { 537 $ret = wpmu_validate_user_signup( $user->user_login, $user->user_email ); 538 539 if ( is_wp_error( $ret['errors'] ) && $ret['errors']->has_errors() ) { 540 $error = new WP_Error( 541 'rest_invalid_param', 542 __( 'Invalid user parameter(s).' ), 543 array( 'status' => 400 ) 544 ); 545 546 foreach ( $ret['errors']->errors as $code => $messages ) { 547 foreach ( $messages as $message ) { 548 $error->add( $code, $message ); 549 } 550 551 $error_data = $error->get_error_data( $code ); 552 553 if ( $error_data ) { 554 $error->add_data( $error_data, $code ); 555 } 556 } 557 return $error; 558 } 559 } 560 561 if ( is_multisite() ) { 562 $user_id = wpmu_create_user( $user->user_login, $user->user_pass, $user->user_email ); 563 564 if ( ! $user_id ) { 565 return new WP_Error( 566 'rest_user_create', 567 __( 'Error creating new user.' ), 568 array( 'status' => 500 ) 569 ); 570 } 571 572 $user->ID = $user_id; 573 $user_id = wp_update_user( wp_slash( (array) $user ) ); 574 575 if ( is_wp_error( $user_id ) ) { 576 return $user_id; 577 } 578 579 $result = add_user_to_blog( get_site()->id, $user_id, '' ); 580 if ( is_wp_error( $result ) ) { 581 return $result; 582 } 583 } else { 584 $user_id = wp_insert_user( wp_slash( (array) $user ) ); 585 586 if ( is_wp_error( $user_id ) ) { 587 return $user_id; 588 } 589 } 590 591 $user = get_user_by( 'id', $user_id ); 592 593 /** 594 * Fires immediately after a user is created or updated via the REST API. 595 * 596 * @since 4.7.0 597 * 598 * @param WP_User $user Inserted or updated user object. 599 * @param WP_REST_Request $request Request object. 600 * @param bool $creating True when creating a user, false when updating. 601 */ 602 do_action( 'rest_insert_user', $user, $request, true ); 603 604 if ( ! empty( $request['roles'] ) && ! empty( $schema['properties']['roles'] ) ) { 605 array_map( array( $user, 'add_role' ), $request['roles'] ); 606 } 607 608 if ( ! empty( $schema['properties']['meta'] ) && isset( $request['meta'] ) ) { 609 $meta_update = $this->meta->update_value( $request['meta'], $user_id ); 610 611 if ( is_wp_error( $meta_update ) ) { 612 return $meta_update; 613 } 614 } 615 616 $user = get_user_by( 'id', $user_id ); 617 $fields_update = $this->update_additional_fields_for_object( $user, $request ); 618 619 if ( is_wp_error( $fields_update ) ) { 620 return $fields_update; 621 } 622 623 $request->set_param( 'context', 'edit' ); 624 625 /** 626 * Fires after a user is completely created or updated via the REST API. 627 * 628 * @since 5.0.0 629 * 630 * @param WP_User $user Inserted or updated user object. 631 * @param WP_REST_Request $request Request object. 632 * @param bool $creating True when creating a user, false when updating. 633 */ 634 do_action( 'rest_after_insert_user', $user, $request, true ); 635 636 $response = $this->prepare_item_for_response( $user, $request ); 637 $response = rest_ensure_response( $response ); 638 639 $response->set_status( 201 ); 640 $response->header( 'Location', rest_url( sprintf( '%s/%s/%d', $this->namespace, $this->rest_base, $user_id ) ) ); 641 642 return $response; 643 } 644 645 /** 646 * Checks if a given request has access to update a user. 647 * 648 * @since 4.7.0 649 * 650 * @param WP_REST_Request $request Full details about the request. 651 * @return true|WP_Error True if the request has access to update the item, WP_Error object otherwise. 652 */ 653 public function update_item_permissions_check( $request ) { 654 $user = $this->get_user( $request['id'] ); 655 if ( is_wp_error( $user ) ) { 656 return $user; 657 } 658 659 if ( ! empty( $request['roles'] ) ) { 660 if ( ! current_user_can( 'promote_user', $user->ID ) ) { 661 return new WP_Error( 662 'rest_cannot_edit_roles', 663 __( 'Sorry, you are not allowed to edit roles of this user.' ), 664 array( 'status' => rest_authorization_required_code() ) 665 ); 666 } 667 668 $request_params = array_keys( $request->get_params() ); 669 sort( $request_params ); 670 // If only 'id' and 'roles' are specified (we are only trying to 671 // edit roles), then only the 'promote_user' cap is required. 672 if ( array( 'id', 'roles' ) === $request_params ) { 673 return true; 674 } 675 } 676 677 if ( ! current_user_can( 'edit_user', $user->ID ) ) { 678 return new WP_Error( 679 'rest_cannot_edit', 680 __( 'Sorry, you are not allowed to edit this user.' ), 681 array( 'status' => rest_authorization_required_code() ) 682 ); 683 } 684 685 return true; 686 } 687 688 /** 689 * Updates a single user. 690 * 691 * @since 4.7.0 692 * 693 * @param WP_REST_Request $request Full details about the request. 694 * @return WP_REST_Response|WP_Error Response object on success, or WP_Error object on failure. 695 */ 696 public function update_item( $request ) { 697 $user = $this->get_user( $request['id'] ); 698 if ( is_wp_error( $user ) ) { 699 return $user; 700 } 701 702 $id = $user->ID; 703 704 if ( ! $user ) { 705 return new WP_Error( 706 'rest_user_invalid_id', 707 __( 'Invalid user ID.' ), 708 array( 'status' => 404 ) 709 ); 710 } 711 712 $owner_id = email_exists( $request['email'] ); 713 714 if ( $owner_id && $owner_id !== $id ) { 715 return new WP_Error( 716 'rest_user_invalid_email', 717 __( 'Invalid email address.' ), 718 array( 'status' => 400 ) 719 ); 720 } 721 722 if ( ! empty( $request['username'] ) && $request['username'] !== $user->user_login ) { 723 return new WP_Error( 724 'rest_user_invalid_argument', 725 __( "Username isn't editable." ), 726 array( 'status' => 400 ) 727 ); 728 } 729 730 if ( ! empty( $request['slug'] ) && $request['slug'] !== $user->user_nicename && get_user_by( 'slug', $request['slug'] ) ) { 731 return new WP_Error( 732 'rest_user_invalid_slug', 733 __( 'Invalid slug.' ), 734 array( 'status' => 400 ) 735 ); 736 } 737 738 if ( ! empty( $request['roles'] ) ) { 739 $check_permission = $this->check_role_update( $id, $request['roles'] ); 740 741 if ( is_wp_error( $check_permission ) ) { 742 return $check_permission; 743 } 744 } 745 746 $user = $this->prepare_item_for_database( $request ); 747 748 // Ensure we're operating on the same user we already checked. 749 $user->ID = $id; 750 751 $user_id = wp_update_user( wp_slash( (array) $user ) ); 752 753 if ( is_wp_error( $user_id ) ) { 754 return $user_id; 755 } 756 757 $user = get_user_by( 'id', $user_id ); 758 759 /** This action is documented in wp-includes/rest-api/endpoints/class-wp-rest-users-controller.php */ 760 do_action( 'rest_insert_user', $user, $request, false ); 761 762 if ( ! empty( $request['roles'] ) ) { 763 array_map( array( $user, 'add_role' ), $request['roles'] ); 764 } 765 766 $schema = $this->get_item_schema(); 767 768 if ( ! empty( $schema['properties']['meta'] ) && isset( $request['meta'] ) ) { 769 $meta_update = $this->meta->update_value( $request['meta'], $id ); 770 771 if ( is_wp_error( $meta_update ) ) { 772 return $meta_update; 773 } 774 } 775 776 $user = get_user_by( 'id', $user_id ); 777 $fields_update = $this->update_additional_fields_for_object( $user, $request ); 778 779 if ( is_wp_error( $fields_update ) ) { 780 return $fields_update; 781 } 782 783 $request->set_param( 'context', 'edit' ); 784 785 /** This action is documented in wp-includes/rest-api/endpoints/class-wp-rest-users-controller.php */ 786 do_action( 'rest_after_insert_user', $user, $request, false ); 787 788 $response = $this->prepare_item_for_response( $user, $request ); 789 $response = rest_ensure_response( $response ); 790 791 return $response; 792 } 793 794 /** 795 * Checks if a given request has access to update the current user. 796 * 797 * @since 4.7.0 798 * 799 * @param WP_REST_Request $request Full details about the request. 800 * @return true|WP_Error True if the request has access to update the item, WP_Error object otherwise. 801 */ 802 public function update_current_item_permissions_check( $request ) { 803 $request['id'] = get_current_user_id(); 804 805 return $this->update_item_permissions_check( $request ); 806 } 807 808 /** 809 * Updates the current user. 810 * 811 * @since 4.7.0 812 * 813 * @param WP_REST_Request $request Full details about the request. 814 * @return WP_REST_Response|WP_Error Response object on success, or WP_Error object on failure. 815 */ 816 public function update_current_item( $request ) { 817 $request['id'] = get_current_user_id(); 818 819 return $this->update_item( $request ); 820 } 821 822 /** 823 * Checks if a given request has access delete a user. 824 * 825 * @since 4.7.0 826 * 827 * @param WP_REST_Request $request Full details about the request. 828 * @return true|WP_Error True if the request has access to delete the item, WP_Error object otherwise. 829 */ 830 public function delete_item_permissions_check( $request ) { 831 $user = $this->get_user( $request['id'] ); 832 if ( is_wp_error( $user ) ) { 833 return $user; 834 } 835 836 if ( ! current_user_can( 'delete_user', $user->ID ) ) { 837 return new WP_Error( 838 'rest_user_cannot_delete', 839 __( 'Sorry, you are not allowed to delete this user.' ), 840 array( 'status' => rest_authorization_required_code() ) 841 ); 842 } 843 844 return true; 845 } 846 847 /** 848 * Deletes a single user. 849 * 850 * @since 4.7.0 851 * 852 * @param WP_REST_Request $request Full details about the request. 853 * @return WP_REST_Response|WP_Error Response object on success, or WP_Error object on failure. 854 */ 855 public function delete_item( $request ) { 856 // We don't support delete requests in multisite. 857 if ( is_multisite() ) { 858 return new WP_Error( 859 'rest_cannot_delete', 860 __( 'The user cannot be deleted.' ), 861 array( 'status' => 501 ) 862 ); 863 } 864 865 $user = $this->get_user( $request['id'] ); 866 867 if ( is_wp_error( $user ) ) { 868 return $user; 869 } 870 871 $id = $user->ID; 872 $reassign = false === $request['reassign'] ? null : absint( $request['reassign'] ); 873 $force = isset( $request['force'] ) ? (bool) $request['force'] : false; 874 875 // We don't support trashing for users. 876 if ( ! $force ) { 877 return new WP_Error( 878 'rest_trash_not_supported', 879 /* translators: %s: force=true */ 880 sprintf( __( "Users do not support trashing. Set '%s' to delete." ), 'force=true' ), 881 array( 'status' => 501 ) 882 ); 883 } 884 885 if ( ! empty( $reassign ) ) { 886 if ( $reassign === $id || ! get_userdata( $reassign ) ) { 887 return new WP_Error( 888 'rest_user_invalid_reassign', 889 __( 'Invalid user ID for reassignment.' ), 890 array( 'status' => 400 ) 891 ); 892 } 893 } 894 895 $request->set_param( 'context', 'edit' ); 896 897 $previous = $this->prepare_item_for_response( $user, $request ); 898 899 // Include user admin functions to get access to wp_delete_user(). 900 require_once ABSPATH . 'wp-admin/includes/user.php'; 901 902 $result = wp_delete_user( $id, $reassign ); 903 904 if ( ! $result ) { 905 return new WP_Error( 906 'rest_cannot_delete', 907 __( 'The user cannot be deleted.' ), 908 array( 'status' => 500 ) 909 ); 910 } 911 912 $response = new WP_REST_Response(); 913 $response->set_data( 914 array( 915 'deleted' => true, 916 'previous' => $previous->get_data(), 917 ) 918 ); 919 920 /** 921 * Fires immediately after a user is deleted via the REST API. 922 * 923 * @since 4.7.0 924 * 925 * @param WP_User $user The user data. 926 * @param WP_REST_Response $response The response returned from the API. 927 * @param WP_REST_Request $request The request sent to the API. 928 */ 929 do_action( 'rest_delete_user', $user, $response, $request ); 930 931 return $response; 932 } 933 934 /** 935 * Checks if a given request has access to delete the current user. 936 * 937 * @since 4.7.0 938 * 939 * @param WP_REST_Request $request Full details about the request. 940 * @return true|WP_Error True if the request has access to delete the item, WP_Error object otherwise. 941 */ 942 public function delete_current_item_permissions_check( $request ) { 943 $request['id'] = get_current_user_id(); 944 945 return $this->delete_item_permissions_check( $request ); 946 } 947 948 /** 949 * Deletes the current user. 950 * 951 * @since 4.7.0 952 * 953 * @param WP_REST_Request $request Full details about the request. 954 * @return WP_REST_Response|WP_Error Response object on success, or WP_Error object on failure. 955 */ 956 public function delete_current_item( $request ) { 957 $request['id'] = get_current_user_id(); 958 959 return $this->delete_item( $request ); 960 } 961 962 /** 963 * Prepares a single user output for response. 964 * 965 * @since 4.7.0 966 * 967 * @param WP_User $user User object. 968 * @param WP_REST_Request $request Request object. 969 * @return WP_REST_Response Response object. 970 */ 971 public function prepare_item_for_response( $user, $request ) { 972 973 $data = array(); 974 $fields = $this->get_fields_for_response( $request ); 975 976 if ( in_array( 'id', $fields, true ) ) { 977 $data['id'] = $user->ID; 978 } 979 980 if ( in_array( 'username', $fields, true ) ) { 981 $data['username'] = $user->user_login; 982 } 983 984 if ( in_array( 'name', $fields, true ) ) { 985 $data['name'] = $user->display_name; 986 } 987 988 if ( in_array( 'first_name', $fields, true ) ) { 989 $data['first_name'] = $user->first_name; 990 } 991 992 if ( in_array( 'last_name', $fields, true ) ) { 993 $data['last_name'] = $user->last_name; 994 } 995 996 if ( in_array( 'email', $fields, true ) ) { 997 $data['email'] = $user->user_email; 998 } 999 1000 if ( in_array( 'url', $fields, true ) ) { 1001 $data['url'] = $user->user_url; 1002 } 1003 1004 if ( in_array( 'description', $fields, true ) ) { 1005 $data['description'] = $user->description; 1006 } 1007 1008 if ( in_array( 'link', $fields, true ) ) { 1009 $data['link'] = get_author_posts_url( $user->ID, $user->user_nicename ); 1010 } 1011 1012 if ( in_array( 'locale', $fields, true ) ) { 1013 $data['locale'] = get_user_locale( $user ); 1014 } 1015 1016 if ( in_array( 'nickname', $fields, true ) ) { 1017 $data['nickname'] = $user->nickname; 1018 } 1019 1020 if ( in_array( 'slug', $fields, true ) ) { 1021 $data['slug'] = $user->user_nicename; 1022 } 1023 1024 if ( in_array( 'roles', $fields, true ) ) { 1025 // Defensively call array_values() to ensure an array is returned. 1026 $data['roles'] = array_values( $user->roles ); 1027 } 1028 1029 if ( in_array( 'registered_date', $fields, true ) ) { 1030 $data['registered_date'] = gmdate( 'c', strtotime( $user->user_registered ) ); 1031 } 1032 1033 if ( in_array( 'capabilities', $fields, true ) ) { 1034 $data['capabilities'] = (object) $user->allcaps; 1035 } 1036 1037 if ( in_array( 'extra_capabilities', $fields, true ) ) { 1038 $data['extra_capabilities'] = (object) $user->caps; 1039 } 1040 1041 if ( in_array( 'avatar_urls', $fields, true ) ) { 1042 $data['avatar_urls'] = rest_get_avatar_urls( $user ); 1043 } 1044 1045 if ( in_array( 'meta', $fields, true ) ) { 1046 $data['meta'] = $this->meta->get_value( $user->ID, $request ); 1047 } 1048 1049 $context = ! empty( $request['context'] ) ? $request['context'] : 'embed'; 1050 1051 $data = $this->add_additional_fields_to_object( $data, $request ); 1052 $data = $this->filter_response_by_context( $data, $context ); 1053 1054 // Wrap the data in a response object. 1055 $response = rest_ensure_response( $data ); 1056 1057 $response->add_links( $this->prepare_links( $user ) ); 1058 1059 /** 1060 * Filters user data returned from the REST API. 1061 * 1062 * @since 4.7.0 1063 * 1064 * @param WP_REST_Response $response The response object. 1065 * @param WP_User $user User object used to create response. 1066 * @param WP_REST_Request $request Request object. 1067 */ 1068 return apply_filters( 'rest_prepare_user', $response, $user, $request ); 1069 } 1070 1071 /** 1072 * Prepares links for the user request. 1073 * 1074 * @since 4.7.0 1075 * 1076 * @param WP_User $user User object. 1077 * @return array Links for the given user. 1078 */ 1079 protected function prepare_links( $user ) { 1080 $links = array( 1081 'self' => array( 1082 'href' => rest_url( sprintf( '%s/%s/%d', $this->namespace, $this->rest_base, $user->ID ) ), 1083 ), 1084 'collection' => array( 1085 'href' => rest_url( sprintf( '%s/%s', $this->namespace, $this->rest_base ) ), 1086 ), 1087 ); 1088 1089 return $links; 1090 } 1091 1092 /** 1093 * Prepares a single user for creation or update. 1094 * 1095 * @since 4.7.0 1096 * 1097 * @param WP_REST_Request $request Request object. 1098 * @return object User object. 1099 */ 1100 protected function prepare_item_for_database( $request ) { 1101 $prepared_user = new stdClass; 1102 1103 $schema = $this->get_item_schema(); 1104 1105 // Required arguments. 1106 if ( isset( $request['email'] ) && ! empty( $schema['properties']['email'] ) ) { 1107 $prepared_user->user_email = $request['email']; 1108 } 1109 1110 if ( isset( $request['username'] ) && ! empty( $schema['properties']['username'] ) ) { 1111 $prepared_user->user_login = $request['username']; 1112 } 1113 1114 if ( isset( $request['password'] ) && ! empty( $schema['properties']['password'] ) ) { 1115 $prepared_user->user_pass = $request['password']; 1116 } 1117 1118 // Optional arguments. 1119 if ( isset( $request['id'] ) ) { 1120 $prepared_user->ID = absint( $request['id'] ); 1121 } 1122 1123 if ( isset( $request['name'] ) && ! empty( $schema['properties']['name'] ) ) { 1124 $prepared_user->display_name = $request['name']; 1125 } 1126 1127 if ( isset( $request['first_name'] ) && ! empty( $schema['properties']['first_name'] ) ) { 1128 $prepared_user->first_name = $request['first_name']; 1129 } 1130 1131 if ( isset( $request['last_name'] ) && ! empty( $schema['properties']['last_name'] ) ) { 1132 $prepared_user->last_name = $request['last_name']; 1133 } 1134 1135 if ( isset( $request['nickname'] ) && ! empty( $schema['properties']['nickname'] ) ) { 1136 $prepared_user->nickname = $request['nickname']; 1137 } 1138 1139 if ( isset( $request['slug'] ) && ! empty( $schema['properties']['slug'] ) ) { 1140 $prepared_user->user_nicename = $request['slug']; 1141 } 1142 1143 if ( isset( $request['description'] ) && ! empty( $schema['properties']['description'] ) ) { 1144 $prepared_user->description = $request['description']; 1145 } 1146 1147 if ( isset( $request['url'] ) && ! empty( $schema['properties']['url'] ) ) { 1148 $prepared_user->user_url = $request['url']; 1149 } 1150 1151 if ( isset( $request['locale'] ) && ! empty( $schema['properties']['locale'] ) ) { 1152 $prepared_user->locale = $request['locale']; 1153 } 1154 1155 // Setting roles will be handled outside of this function. 1156 if ( isset( $request['roles'] ) ) { 1157 $prepared_user->role = false; 1158 } 1159 1160 /** 1161 * Filters user data before insertion via the REST API. 1162 * 1163 * @since 4.7.0 1164 * 1165 * @param object $prepared_user User object. 1166 * @param WP_REST_Request $request Request object. 1167 */ 1168 return apply_filters( 'rest_pre_insert_user', $prepared_user, $request ); 1169 } 1170 1171 /** 1172 * Determines if the current user is allowed to make the desired roles change. 1173 * 1174 * @since 4.7.0 1175 * 1176 * @param int $user_id User ID. 1177 * @param array $roles New user roles. 1178 * @return true|WP_Error True if the current user is allowed to make the role change, 1179 * otherwise a WP_Error object. 1180 */ 1181 protected function check_role_update( $user_id, $roles ) { 1182 global $wp_roles; 1183 1184 foreach ( $roles as $role ) { 1185 1186 if ( ! isset( $wp_roles->role_objects[ $role ] ) ) { 1187 return new WP_Error( 1188 'rest_user_invalid_role', 1189 /* translators: %s: Role key. */ 1190 sprintf( __( 'The role %s does not exist.' ), $role ), 1191 array( 'status' => 400 ) 1192 ); 1193 } 1194 1195 $potential_role = $wp_roles->role_objects[ $role ]; 1196 1197 /* 1198 * Don't let anyone with 'edit_users' (admins) edit their own role to something without it. 1199 * Multisite super admins can freely edit their blog roles -- they possess all caps. 1200 */ 1201 if ( ! ( is_multisite() 1202 && current_user_can( 'manage_sites' ) ) 1203 && get_current_user_id() === $user_id 1204 && ! $potential_role->has_cap( 'edit_users' ) 1205 ) { 1206 return new WP_Error( 1207 'rest_user_invalid_role', 1208 __( 'Sorry, you are not allowed to give users that role.' ), 1209 array( 'status' => rest_authorization_required_code() ) 1210 ); 1211 } 1212 1213 // Include user admin functions to get access to get_editable_roles(). 1214 require_once ABSPATH . 'wp-admin/includes/user.php'; 1215 1216 // The new role must be editable by the logged-in user. 1217 $editable_roles = get_editable_roles(); 1218 1219 if ( empty( $editable_roles[ $role ] ) ) { 1220 return new WP_Error( 1221 'rest_user_invalid_role', 1222 __( 'Sorry, you are not allowed to give users that role.' ), 1223 array( 'status' => 403 ) 1224 ); 1225 } 1226 } 1227 1228 return true; 1229 } 1230 1231 /** 1232 * Check a username for the REST API. 1233 * 1234 * Performs a couple of checks like edit_user() in wp-admin/includes/user.php. 1235 * 1236 * @since 4.7.0 1237 * 1238 * @param string $value The username submitted in the request. 1239 * @param WP_REST_Request $request Full details about the request. 1240 * @param string $param The parameter name. 1241 * @return string|WP_Error The sanitized username, if valid, otherwise an error. 1242 */ 1243 public function check_username( $value, $request, $param ) { 1244 $username = (string) $value; 1245 1246 if ( ! validate_username( $username ) ) { 1247 return new WP_Error( 1248 'rest_user_invalid_username', 1249 __( 'This username is invalid because it uses illegal characters. Please enter a valid username.' ), 1250 array( 'status' => 400 ) 1251 ); 1252 } 1253 1254 /** This filter is documented in wp-includes/user.php */ 1255 $illegal_logins = (array) apply_filters( 'illegal_user_logins', array() ); 1256 1257 if ( in_array( strtolower( $username ), array_map( 'strtolower', $illegal_logins ), true ) ) { 1258 return new WP_Error( 1259 'rest_user_invalid_username', 1260 __( 'Sorry, that username is not allowed.' ), 1261 array( 'status' => 400 ) 1262 ); 1263 } 1264 1265 return $username; 1266 } 1267 1268 /** 1269 * Check a user password for the REST API. 1270 * 1271 * Performs a couple of checks like edit_user() in wp-admin/includes/user.php. 1272 * 1273 * @since 4.7.0 1274 * 1275 * @param string $value The password submitted in the request. 1276 * @param WP_REST_Request $request Full details about the request. 1277 * @param string $param The parameter name. 1278 * @return string|WP_Error The sanitized password, if valid, otherwise an error. 1279 */ 1280 public function check_user_password( $value, $request, $param ) { 1281 $password = (string) $value; 1282 1283 if ( empty( $password ) ) { 1284 return new WP_Error( 1285 'rest_user_invalid_password', 1286 __( 'Passwords cannot be empty.' ), 1287 array( 'status' => 400 ) 1288 ); 1289 } 1290 1291 if ( false !== strpos( $password, '\\' ) ) { 1292 return new WP_Error( 1293 'rest_user_invalid_password', 1294 sprintf( 1295 /* translators: %s: The '\' character. */ 1296 __( 'Passwords cannot contain the "%s" character.' ), 1297 '\\' 1298 ), 1299 array( 'status' => 400 ) 1300 ); 1301 } 1302 1303 return $password; 1304 } 1305 1306 /** 1307 * Retrieves the user's schema, conforming to JSON Schema. 1308 * 1309 * @since 4.7.0 1310 * 1311 * @return array Item schema data. 1312 */ 1313 public function get_item_schema() { 1314 if ( $this->schema ) { 1315 return $this->add_additional_fields_schema( $this->schema ); 1316 } 1317 1318 $schema = array( 1319 '$schema' => 'http://json-schema.org/draft-04/schema#', 1320 'title' => 'user', 1321 'type' => 'object', 1322 'properties' => array( 1323 'id' => array( 1324 'description' => __( 'Unique identifier for the user.' ), 1325 'type' => 'integer', 1326 'context' => array( 'embed', 'view', 'edit' ), 1327 'readonly' => true, 1328 ), 1329 'username' => array( 1330 'description' => __( 'Login name for the user.' ), 1331 'type' => 'string', 1332 'context' => array( 'edit' ), 1333 'required' => true, 1334 'arg_options' => array( 1335 'sanitize_callback' => array( $this, 'check_username' ), 1336 ), 1337 ), 1338 'name' => array( 1339 'description' => __( 'Display name for the user.' ), 1340 'type' => 'string', 1341 'context' => array( 'embed', 'view', 'edit' ), 1342 'arg_options' => array( 1343 'sanitize_callback' => 'sanitize_text_field', 1344 ), 1345 ), 1346 'first_name' => array( 1347 'description' => __( 'First name for the user.' ), 1348 'type' => 'string', 1349 'context' => array( 'edit' ), 1350 'arg_options' => array( 1351 'sanitize_callback' => 'sanitize_text_field', 1352 ), 1353 ), 1354 'last_name' => array( 1355 'description' => __( 'Last name for the user.' ), 1356 'type' => 'string', 1357 'context' => array( 'edit' ), 1358 'arg_options' => array( 1359 'sanitize_callback' => 'sanitize_text_field', 1360 ), 1361 ), 1362 'email' => array( 1363 'description' => __( 'The email address for the user.' ), 1364 'type' => 'string', 1365 'format' => 'email', 1366 'context' => array( 'edit' ), 1367 'required' => true, 1368 ), 1369 'url' => array( 1370 'description' => __( 'URL of the user.' ), 1371 'type' => 'string', 1372 'format' => 'uri', 1373 'context' => array( 'embed', 'view', 'edit' ), 1374 ), 1375 'description' => array( 1376 'description' => __( 'Description of the user.' ), 1377 'type' => 'string', 1378 'context' => array( 'embed', 'view', 'edit' ), 1379 ), 1380 'link' => array( 1381 'description' => __( 'Author URL of the user.' ), 1382 'type' => 'string', 1383 'format' => 'uri', 1384 'context' => array( 'embed', 'view', 'edit' ), 1385 'readonly' => true, 1386 ), 1387 'locale' => array( 1388 'description' => __( 'Locale for the user.' ), 1389 'type' => 'string', 1390 'enum' => array_merge( array( '', 'en_US' ), get_available_languages() ), 1391 'context' => array( 'edit' ), 1392 ), 1393 'nickname' => array( 1394 'description' => __( 'The nickname for the user.' ), 1395 'type' => 'string', 1396 'context' => array( 'edit' ), 1397 'arg_options' => array( 1398 'sanitize_callback' => 'sanitize_text_field', 1399 ), 1400 ), 1401 'slug' => array( 1402 'description' => __( 'An alphanumeric identifier for the user.' ), 1403 'type' => 'string', 1404 'context' => array( 'embed', 'view', 'edit' ), 1405 'arg_options' => array( 1406 'sanitize_callback' => array( $this, 'sanitize_slug' ), 1407 ), 1408 ), 1409 'registered_date' => array( 1410 'description' => __( 'Registration date for the user.' ), 1411 'type' => 'string', 1412 'format' => 'date-time', 1413 'context' => array( 'edit' ), 1414 'readonly' => true, 1415 ), 1416 'roles' => array( 1417 'description' => __( 'Roles assigned to the user.' ), 1418 'type' => 'array', 1419 'items' => array( 1420 'type' => 'string', 1421 ), 1422 'context' => array( 'edit' ), 1423 ), 1424 'password' => array( 1425 'description' => __( 'Password for the user (never included).' ), 1426 'type' => 'string', 1427 'context' => array(), // Password is never displayed. 1428 'required' => true, 1429 'arg_options' => array( 1430 'sanitize_callback' => array( $this, 'check_user_password' ), 1431 ), 1432 ), 1433 'capabilities' => array( 1434 'description' => __( 'All capabilities assigned to the user.' ), 1435 'type' => 'object', 1436 'context' => array( 'edit' ), 1437 'readonly' => true, 1438 ), 1439 'extra_capabilities' => array( 1440 'description' => __( 'Any extra capabilities assigned to the user.' ), 1441 'type' => 'object', 1442 'context' => array( 'edit' ), 1443 'readonly' => true, 1444 ), 1445 ), 1446 ); 1447 1448 if ( get_option( 'show_avatars' ) ) { 1449 $avatar_properties = array(); 1450 1451 $avatar_sizes = rest_get_avatar_sizes(); 1452 1453 foreach ( $avatar_sizes as $size ) { 1454 $avatar_properties[ $size ] = array( 1455 /* translators: %d: Avatar image size in pixels. */ 1456 'description' => sprintf( __( 'Avatar URL with image size of %d pixels.' ), $size ), 1457 'type' => 'string', 1458 'format' => 'uri', 1459 'context' => array( 'embed', 'view', 'edit' ), 1460 ); 1461 } 1462 1463 $schema['properties']['avatar_urls'] = array( 1464 'description' => __( 'Avatar URLs for the user.' ), 1465 'type' => 'object', 1466 'context' => array( 'embed', 'view', 'edit' ), 1467 'readonly' => true, 1468 'properties' => $avatar_properties, 1469 ); 1470 } 1471 1472 $schema['properties']['meta'] = $this->meta->get_field_schema(); 1473 1474 $this->schema = $schema; 1475 1476 return $this->add_additional_fields_schema( $this->schema ); 1477 } 1478 1479 /** 1480 * Retrieves the query params for collections. 1481 * 1482 * @since 4.7.0 1483 * 1484 * @return array Collection parameters. 1485 */ 1486 public function get_collection_params() { 1487 $query_params = parent::get_collection_params(); 1488 1489 $query_params['context']['default'] = 'view'; 1490 1491 $query_params['exclude'] = array( 1492 'description' => __( 'Ensure result set excludes specific IDs.' ), 1493 'type' => 'array', 1494 'items' => array( 1495 'type' => 'integer', 1496 ), 1497 'default' => array(), 1498 ); 1499 1500 $query_params['include'] = array( 1501 'description' => __( 'Limit result set to specific IDs.' ), 1502 'type' => 'array', 1503 'items' => array( 1504 'type' => 'integer', 1505 ), 1506 'default' => array(), 1507 ); 1508 1509 $query_params['offset'] = array( 1510 'description' => __( 'Offset the result set by a specific number of items.' ), 1511 'type' => 'integer', 1512 ); 1513 1514 $query_params['order'] = array( 1515 'default' => 'asc', 1516 'description' => __( 'Order sort attribute ascending or descending.' ), 1517 'enum' => array( 'asc', 'desc' ), 1518 'type' => 'string', 1519 ); 1520 1521 $query_params['orderby'] = array( 1522 'default' => 'name', 1523 'description' => __( 'Sort collection by object attribute.' ), 1524 'enum' => array( 1525 'id', 1526 'include', 1527 'name', 1528 'registered_date', 1529 'slug', 1530 'include_slugs', 1531 'email', 1532 'url', 1533 ), 1534 'type' => 'string', 1535 ); 1536 1537 $query_params['slug'] = array( 1538 'description' => __( 'Limit result set to users with one or more specific slugs.' ), 1539 'type' => 'array', 1540 'items' => array( 1541 'type' => 'string', 1542 ), 1543 ); 1544 1545 $query_params['roles'] = array( 1546 'description' => __( 'Limit result set to users matching at least one specific role provided. Accepts csv list or single role.' ), 1547 'type' => 'array', 1548 'items' => array( 1549 'type' => 'string', 1550 ), 1551 ); 1552 1553 $query_params['who'] = array( 1554 'description' => __( 'Limit result set to users who are considered authors.' ), 1555 'type' => 'string', 1556 'enum' => array( 1557 'authors', 1558 ), 1559 ); 1560 1561 /** 1562 * Filters REST API collection parameters for the users controller. 1563 * 1564 * This filter registers the collection parameter, but does not map the 1565 * collection parameter to an internal WP_User_Query parameter. Use the 1566 * `rest_user_query` filter to set WP_User_Query arguments. 1567 * 1568 * @since 4.7.0 1569 * 1570 * @param array $query_params JSON Schema-formatted collection parameters. 1571 */ 1572 return apply_filters( 'rest_user_collection_params', $query_params ); 1573 } 1574 }
title
Description
Body
title
Description
Body
title
Description
Body
title
Body
Generated: Thu Feb 25 01:00:09 2021 | Cross-referenced by PHPXref 0.7.1 |