Skip to content

Commit f71d5f0

Browse files
committed
REST API: Add support for the ignore_sticky_posts argument.
Introduce `ignore_sticky` as a boolean argument for the posts endpoint for requests without the sticky posts being stuck. The new argument defaults to `false` with the value of the argument passed to `WP_Query`'s `ignore_sticky_posts` parameter. Props audrasjb, danielbachhuber, joemcgill, johnbillion, jorbin, mamaduka, rmccue. Fixes #35907. git-svn-id: https://develop.svn.wordpress.org/trunk@59801 602fd350-edb4-49c9-b593-d223f7449a82
1 parent 9160fbd commit f71d5f0

File tree

3 files changed

+87
-0
lines changed

3 files changed

+87
-0
lines changed

src/wp-includes/rest-api/endpoints/class-wp-rest-posts-controller.php

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -247,6 +247,7 @@ public function get_items( $request ) {
247247
'author_exclude' => 'author__not_in',
248248
'exclude' => 'post__not_in',
249249
'include' => 'post__in',
250+
'ignore_sticky' => 'ignore_sticky_posts',
250251
'menu_order' => 'menu_order',
251252
'offset' => 'offset',
252253
'order' => 'order',
@@ -337,6 +338,14 @@ public function get_items( $request ) {
337338
}
338339
}
339340

341+
/*
342+
* Honor the original REST API `post__in` behavior. Don't prepend sticky posts
343+
* when `post__in` has been specified.
344+
*/
345+
if ( ! empty( $args['post__in'] ) ) {
346+
unset( $args['ignore_sticky_posts'] );
347+
}
348+
340349
if (
341350
isset( $registered['search_semantics'], $request['search_semantics'] )
342351
&& 'exact' === $request['search_semantics']
@@ -3045,6 +3054,12 @@ public function get_collection_params() {
30453054
'description' => __( 'Limit result set to items that are sticky.' ),
30463055
'type' => 'boolean',
30473056
);
3057+
3058+
$query_params['ignore_sticky'] = array(
3059+
'description' => __( 'Whether to ignore sticky posts or not.' ),
3060+
'type' => 'boolean',
3061+
'default' => false,
3062+
);
30483063
}
30493064

30503065
if ( post_type_supports( $this->post_type, 'post-formats' ) ) {

tests/phpunit/tests/rest-api/rest-posts-controller.php

Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -197,6 +197,7 @@ public function test_registered_query_params() {
197197
'context',
198198
'exclude',
199199
'format',
200+
'ignore_sticky',
200201
'include',
201202
'modified_after',
202203
'modified_before',
@@ -5715,6 +5716,71 @@ public function test_get_posts_with_pagination() {
57155716
$this->assertErrorResponse( 'rest_post_invalid_page_number', $response, 400 );
57165717
}
57175718

5719+
/**
5720+
* Test the REST API support for `ignore_sticky_posts`.
5721+
*
5722+
* @ticket 35907
5723+
*
5724+
* @covers WP_REST_Posts_Controller::get_items
5725+
*/
5726+
public function test_get_posts_ignore_sticky_default_prepends_sticky_posts() {
5727+
$id1 = self::$post_id;
5728+
// Create more recent post to avoid automatically placing other at the top.
5729+
$id2 = self::factory()->post->create( array( 'post_status' => 'publish' ) );
5730+
5731+
update_option( 'sticky_posts', array( $id1 ) );
5732+
5733+
$request = new WP_REST_Request( 'GET', '/wp/v2/posts' );
5734+
$response = rest_get_server()->dispatch( $request );
5735+
$data = $response->get_data();
5736+
5737+
$this->assertSame( $data[0]['id'], $id1, 'Response has sticky post at the top.' );
5738+
$this->assertSame( $data[1]['id'], $id2, 'It is followed by most recent post.' );
5739+
}
5740+
5741+
/**
5742+
* Test the REST API support for `ignore_sticky_posts`.
5743+
*
5744+
* @ticket 35907
5745+
*
5746+
* @covers WP_REST_Posts_Controller::get_items
5747+
*/
5748+
public function test_get_posts_ignore_sticky_ignores_post_stickiness() {
5749+
$id1 = self::$post_id;
5750+
$id2 = self::factory()->post->create( array( 'post_status' => 'publish' ) );
5751+
5752+
update_option( 'sticky_posts', array( $id1 ) );
5753+
5754+
$request = new WP_REST_Request( 'GET', '/wp/v2/posts' );
5755+
$request->set_param( 'ignore_sticky', true );
5756+
$response = rest_get_server()->dispatch( $request );
5757+
$data = $response->get_data();
5758+
5759+
$this->assertSame( $data[0]['id'], $id2, 'Response has no sticky post at the top.' );
5760+
}
5761+
5762+
/**
5763+
* Test the REST API support for `ignore_sticky_posts`.
5764+
*
5765+
* @ticket 35907
5766+
*
5767+
* @covers WP_REST_Posts_Controller::get_items
5768+
*/
5769+
public function test_get_posts_ignore_sticky_honors_include() {
5770+
$id1 = self::$post_id;
5771+
$id2 = self::factory()->post->create( array( 'post_status' => 'publish' ) );
5772+
5773+
update_option( 'sticky_posts', array( $id1 ) );
5774+
5775+
$request = new WP_REST_Request( 'GET', '/wp/v2/posts' );
5776+
$request->set_param( 'include', array( $id2 ) );
5777+
$response = rest_get_server()->dispatch( $request );
5778+
$data = $response->get_data();
5779+
5780+
$this->assertCount( 1, $data, 'Only one post is expected to be returned.' );
5781+
$this->assertSame( $data[0]['id'], $id2, 'Returns the included post.' );
5782+
}
5783+
57185784
/**
57195785
* Internal function used to disable an insert query which
57205786
* will trigger a wpdb error for testing purposes.

tests/qunit/fixtures/wp-api-generated.js

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -627,6 +627,12 @@ mockedApiResponse.Schema = {
627627
"type": "boolean",
628628
"required": false
629629
},
630+
"ignore_sticky": {
631+
"description": "Whether to ignore sticky posts or not.",
632+
"type": "boolean",
633+
"default": false,
634+
"required": false
635+
},
630636
"format": {
631637
"description": "Limit result set to items assigned one or more given formats.",
632638
"type": "array",

0 commit comments

Comments
 (0)