From c023479b13e35beaf7a195ee97d201a4b2f69ca1 Mon Sep 17 00:00:00 2001 From: Oli I Date: Thu, 19 Dec 2024 15:56:58 -0600 Subject: [PATCH] My Jetpack: Fix - Update getting raw post type count (#40635) * Update raw post type breakdown for sites with high post count Updating the function get_raw_post_type_breakdown for sites with high post counts as the query can cause backend issues for sites with a lot of post. If the sites total post count exceeds a million posts the query will be handled remotely and the results of a remote request used for My Jetpack * Create fix-update-raw-post-type-count Add changelog * Update class-search-stats.php Check the result of the remote request for raw post type breakdown * Update class-search-stats.php Always queue the remote post count query if the post count is over the local query limit. * Update class-search-stats.php Update the query limit to 100k vs 1 million * Update fix-update-raw-post-type-count Update the changelog for the updated query limit --- .../changelog/fix-update-raw-post-type-count | 4 ++ .../src/products/class-search-stats.php | 44 ++++++++++++++++++- 2 files changed, 47 insertions(+), 1 deletion(-) create mode 100644 projects/packages/my-jetpack/changelog/fix-update-raw-post-type-count diff --git a/projects/packages/my-jetpack/changelog/fix-update-raw-post-type-count b/projects/packages/my-jetpack/changelog/fix-update-raw-post-type-count new file mode 100644 index 0000000000000..78071c4b44a95 --- /dev/null +++ b/projects/packages/my-jetpack/changelog/fix-update-raw-post-type-count @@ -0,0 +1,4 @@ +Significance: patch +Type: fixed + +Fix an issue where high posts counts would cause backend issues for the get_raw_post_type_breakdown function used in My Jetpack. Sites with over 100,000 posts can now have this query managed remotely. diff --git a/projects/packages/my-jetpack/src/products/class-search-stats.php b/projects/packages/my-jetpack/src/products/class-search-stats.php index 8d363a3bc82e0..a6ea54368e3ae 100644 --- a/projects/packages/my-jetpack/src/products/class-search-stats.php +++ b/projects/packages/my-jetpack/src/products/class-search-stats.php @@ -36,6 +36,8 @@ class Search_Stats { const CACHE_EXPIRY = 1 * MINUTE_IN_SECONDS; const CACHE_GROUP = 'jetpack_search'; const POST_TYPE_BREAKDOWN_CACHE_KEY = 'post_type_break_down'; + const TOTAL_POSTS_COUNT_CACHE_KEY = 'total-post-count'; + const POST_COUNT_QUERY_LIMIT = 1e5; /** * Get stats from the WordPress.com API for the current blog ID. @@ -58,6 +60,25 @@ public function get_stats_from_wpcom() { return $response; } + /** + * Queue querying the post type breakdown from WordPress.com API for the current blog ID. + */ + public function queue_post_count_query_from_wpcom() { + $blog_id = Jetpack_Options::get_option( 'id' ); + + if ( ! is_numeric( $blog_id ) ) { + return null; + } + + Client::wpcom_json_api_request_as_blog( + '/sites/' . (int) $blog_id . '/jetpack-search/queue-post-count', + '2', + array(), + null, + 'wpcom' + ); + } + /** * Estimate record counts via a local database query. */ @@ -127,7 +148,7 @@ public static function get_post_type_breakdown_with( $raw_posts_counts, $indexab } /** - * Get raw post type breakdown from the database. + * Get raw post type breakdown from the database or a remote request if posts count is high. */ protected static function get_raw_post_type_breakdown() { global $wpdb; @@ -137,6 +158,27 @@ protected static function get_raw_post_type_breakdown() { return $results; } + $total_posts_count = wp_cache_get( self::TOTAL_POSTS_COUNT_CACHE_KEY, self::CACHE_GROUP ); + if ( false === $total_posts_count ) { + // phpcs:ignore WordPress.DB.DirectDatabaseQuery */ + $total_posts_counts = $wpdb->get_var( "SELECT COUNT(*) FROM {$wpdb->posts}" ); + wp_cache_set( self::TOTAL_POSTS_COUNT_CACHE_KEY, $total_posts_counts, self::CACHE_GROUP, self::CACHE_EXPIRY ); + } + + // Get post type breakdown from a remote request if the post count is high + if ( $total_posts_count > self::POST_COUNT_QUERY_LIMIT ) { + $search_stats = new Search_Stats(); + $search_stats->queue_post_count_query_from_wpcom(); + $wpcom_stats = json_decode( wp_remote_retrieve_body( $search_stats->get_stats_from_wpcom() ), true ); + if ( ! empty( $wpcom_stats['raw_post_type_breakdown'] ) ) { + $results = $wpcom_stats['raw_post_type_breakdown']; + wp_cache_set( self::POST_TYPE_BREAKDOWN_CACHE_KEY, $results, self::CACHE_GROUP, self::CACHE_EXPIRY ); + return $results; + } else { + return array(); + } + } + $query = "SELECT post_type, post_status, COUNT( * ) AS num_posts FROM {$wpdb->posts} WHERE post_password = ''