By default, WordPress does not cache WP_Query
queries. Doing so can greatly improve performance. The way I do this is via the Advanced Post Cache plugin:
By running this plugin (hopefully as an mu-plugin
) with a persistent object cache, WP_Query
calls, along with get_post()
calls (only if suppress_filters
is false
) will be cached.
Bonus!
Now that we’re caching queries, here’s how I do a little extra caching to squeeze out a tiny bit more performance:
<?php
// By default Jetpack does not cache responses from Instagram oembeds.
add_filter( 'instagram_cache_oembed_api_response_body', '__return_true' );
// Cache WP Dashboard Recent Posts Query
add_filter( 'dashboard_recent_posts_query_args', 'cache_dashboard_recent_posts_query_args', 10, 1 );
function cache_dashboard_recent_posts_query_args( $query_args ) {
$query_args['cache_results'] = true;
$query_args['suppress_filters'] = false;
return $query_args;
}
// Cache WP Dashboard Recent Drafts Query
add_filter( 'dashboard_recent_drafts_query_args', 'cache_dashboard_recent_drafts_query_args', 10, 1 );
function cache_dashboard_recent_drafts_query_args( $query_args ) {
$query_args['suppress_filters'] = false;
return $query_args;
}
// Cache comment counts, https://github.com/Automattic/vip-code-performance/blob/master/core-fix-comment-counts-caching.php
add_filter( 'wp_count_comments', 'wpcom_vip_cache_full_comment_counts', 10, 2 );
function wpcom_vip_cache_full_comment_counts( $counts = false , $post_id = 0 ){
//We are only caching the global comment counts for now since those are often in the millions while the per page one is usually more reasonable.
if ( 0 !== $post_id ) {
return $counts;
}
$cache_key = "vip-comments-{$post_id}";
$stats_object = wp_cache_get( $cache_key );
//retrieve comments in the same way wp_count_comments() does
if ( false === $stats_object ) {
$stats = get_comment_count( $post_id );
$stats['moderated'] = $stats['awaiting_moderation'];
unset( $stats['awaiting_moderation'] );
$stats_object = (object) $stats;
wp_cache_set( $cache_key, $stats_object, 'default', 30 * MINUTE_IN_SECONDS );
}
return $stats_object;
}
// Cache monthly media array.
add_filter( 'media_library_months_with_files', 'wpcom_vip_media_library_months_with_files' );
function wpcom_vip_media_library_months_with_files() {
$months = wp_cache_get( 'media_library_months_with_files', 'extra-caching' );
if ( false === $months ) {
global $wpdb;
$months = $wpdb->get_results( $wpdb->prepare( "
SELECT DISTINCT YEAR( post_date ) AS year, MONTH( post_date ) AS month
FROM $wpdb->posts
WHERE post_type = %s
ORDER BY post_date DESC
", 'attachment' )
);
wp_cache_set( 'media_library_months_with_files', $months, 'extra-caching' );
}
return $months;
}
add_action( 'add_attachment', 'media_library_months_with_files_bust_cache' );
function media_library_months_with_files_bust_cache( $post_id ) {
if ( defined( 'WP_IMPORTING' ) && WP_IMPORTING ) {
return;
}
// What month/year is the most recent attachment?
global $wpdb;
$months = $wpdb->get_results( $wpdb->prepare( "
SELECT DISTINCT YEAR( post_date ) AS year, MONTH( post_date ) AS month
FROM $wpdb->posts
WHERE post_type = %s
ORDER BY post_date DESC
LIMIT 1
", 'attachment' )
);
// Simplify by assigning the object to $months
$months = array_shift( array_values( $months ) );
// Compare the dates of the new, and most recent, attachment
if (
! $months->year == get_the_time( 'Y', $post_id ) &&
! $months->month == get_the_time( 'm', $post_id )
) {
// the new attachment is not in the same month/year as the
// most recent attachment, so we need to refresh the transient
wp_cache_delete( 'media_library_months_with_files', 'extra-caching' );
}
}
Code language: HTML, XML (xml)
Leave a Reply