diff --git a/.wp-env.json b/.wp-env.json index 9fcd523a6a..b99ff44f2f 100644 --- a/.wp-env.json +++ b/.wp-env.json @@ -47,7 +47,7 @@ "wp-content/plugins/multiple-required-features.php": "./tests/e2e/src/wordpress-files/test-plugins/multiple-required-features.php", "wp-content/uploads/content-example.xml": "./tests/e2e/src/wordpress-files/test-docs/content-example.xml", "wp-content/plugins/echo-shortcode.php": "./tests/e2e/src/wordpress-files/test-plugins/echo-shortcode.php", - "wp-content/plugins/simulate-setting-dependency.php": "./tests/e2e/src/wordpress-files/test-plugins/simulate-setting-dependency.php" + "wp-content/plugins/simulate-setting-dependency.php": "./tests/e2e/src/wordpress-files/test-plugins/simulate-setting-dependency.php" } } } diff --git a/assets/js/autosuggest/index.js b/assets/js/autosuggest/index.js index 8566f032d1..e68a0607d8 100644 --- a/assets/js/autosuggest/index.js +++ b/assets/js/autosuggest/index.js @@ -675,9 +675,11 @@ function init() { if (response && response._shards && response._shards.successful > 0) { const hits = checkForOrderedPosts(response.hits.hits, searchText); - cachedAutosuggestResults = hits; + const resultsLimit = parseInt(epas.resultsLimit, 10); + const limitedHits = resultsLimit > 0 ? hits.slice(0, resultsLimit) : hits; + cachedAutosuggestResults = limitedHits; - toggleAutosuggest(hits, input); + toggleAutosuggest(limitedHits, input); } else { hideAutosuggestBox(); } diff --git a/includes/classes/Feature/Autosuggest/Autosuggest.php b/includes/classes/Feature/Autosuggest/Autosuggest.php index 044f115939..27aae452ae 100644 --- a/includes/classes/Feature/Autosuggest/Autosuggest.php +++ b/includes/classes/Feature/Autosuggest/Autosuggest.php @@ -337,6 +337,7 @@ public function enqueue_scripts() { 'query' => $query['body'], 'placeholder' => $query['placeholder'], 'endpointUrl' => esc_url( untrailingslashit( $endpoint_url ) ), + 'resultsLimit' => $query['results_limit'], 'selector' => empty( $settings['autosuggest_selector'] ) ? 'ep-autosuggest' : esc_html( $settings['autosuggest_selector'] ), /** * Filter autosuggest default selectors. @@ -488,6 +489,34 @@ public function generate_search_query() { ] ); + $results_limit = isset( $args['posts_per_page'] ) ? (int) $args['posts_per_page'] : (int) get_option( 'posts_per_page' ); + $search_ordering_feature = $features->get_registered_feature( 'searchordering' ); + + if ( $results_limit > 0 && $search_ordering_feature && $search_ordering_feature->is_active() ) { + /** + * Filter the number of Autosuggest candidates requested when Custom Search Results is active. + * + * Autosuggest displays the number of results configured by `ep_autosuggest_query_args`, but Custom + * Search Results need a larger candidate set so posts ordered beyond that display limit can still be + * moved into their configured positions. + * + * @since 5.4.0 + * @hook ep_autosuggest_custom_results_query_size + * @param {int} $query_size Number of candidates to request. + * @param {int} $results_limit Number of results to display. + * @param {array} $args Autosuggest query args. + * @return {int} New candidate query size. + */ + $query_size = (int) apply_filters( + 'ep_autosuggest_custom_results_query_size', + max( $results_limit, 10 ), + $results_limit, + $args + ); + + $args['posts_per_page'] = max( $results_limit, $query_size ); + } + new \WP_Query( $args ); remove_filter( 'posts_pre_query', [ $features->get_registered_feature( $this->slug ), 'return_empty_posts' ], 100 ); @@ -497,9 +526,10 @@ public function generate_search_query() { remove_filter( 'ep_weighting_configuration', [ $features->get_registered_feature( $this->slug ), 'apply_autosuggest_weighting' ] ); return [ - 'body' => $this->autosuggest_query, - 'placeholder' => $placeholder, - 'query_vars' => $args, + 'body' => $this->autosuggest_query, + 'placeholder' => $placeholder, + 'query_vars' => $args, + 'results_limit' => $results_limit, ]; } diff --git a/tests/php/features/TestAutosuggest.php b/tests/php/features/TestAutosuggest.php index a41e518c45..69ea76a463 100644 --- a/tests/php/features/TestAutosuggest.php +++ b/tests/php/features/TestAutosuggest.php @@ -237,6 +237,29 @@ public function testGenerateSearchQueryFilters() { $query = $this->get_feature()->generate_search_query(); $this->assertStringContainsString( '1234', $query['body'] ); + $this->assertEquals( 1234, $query['results_limit'] ); + } + + /** + * Test Custom Search Results can request more Autosuggest candidates than are displayed. + */ + public function testGenerateSearchQueryWithSearchOrdering() { + ElasticPress\Features::factory()->activate_feature( 'search' ); + ElasticPress\Features::factory()->activate_feature( 'searchordering' ); + + $test_args_filter = function ( $args ) { + $args['posts_per_page'] = 4; + return $args; + }; + + add_filter( 'ep_autosuggest_query_args', $test_args_filter ); + + $query = $this->get_feature()->generate_search_query(); + $this->assertStringContainsString( '10', $query['body'] ); + $this->assertEquals( 4, $query['results_limit'] ); + $this->assertEquals( 10, $query['query_vars']['posts_per_page'] ); + + remove_filter( 'ep_autosuggest_query_args', $test_args_filter ); } /**