Make WordPress Core


Ignore:
Timestamp:
10/13/2015 03:06:27 AM (11 years ago)
Author:
boonebgorges
Message:

Use a more reliable method for generating get_terms() cache key.

Previously, the cache key included a serialization of list_terms_exclusions
callbacks, to ensure that the cache was differentiated properly for different
uses of the list_terms_exclusions filter. This strategy was flawed in a
couple of ways: serialization doesn't work equally well for all callable types;
the serialization required reaching into the $wp_filter global; serializing
the callback itself didn't properly account for the possibility that the
callback might return different values in different contexts; the cache key
didn't account for other filters that similarly affect the cached values, such
as terms_clauses.

We skirt all these issues by concatenating the cache key using the SQL query
string, which will reflect all filters applied earlier in get_terms().

Props boonebgorges, wonderboymusic.
Fixes #21267.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/wp-includes/taxonomy-functions.php

    r35117 r35120  
    11451145        }
    11461146
    1147         // $args can be whatever, only use the args defined in defaults to compute the key.
    1148         $filter_key = ( has_filter('list_terms_exclusions') ) ? serialize($GLOBALS['wp_filter']['list_terms_exclusions']) : '';
    1149         $key = md5( serialize( wp_array_slice_assoc( $args, array_keys( $defaults ) ) ) . serialize( $taxonomies ) . $filter_key );
    1150         $last_changed = wp_cache_get( 'last_changed', 'terms' );
    1151         if ( ! $last_changed ) {
    1152                 $last_changed = microtime();
    1153                 wp_cache_set( 'last_changed', $last_changed, 'terms' );
    1154         }
    1155         $cache_key = "get_terms:$key:$last_changed";
    1156         $cache = wp_cache_get( $cache_key, 'terms' );
    1157         if ( false !== $cache ) {
    1158                 if ( 'all' === $args['fields'] ) {
    1159                         $cache = array_map( 'get_term', $cache );
    1160                 }
    1161 
    1162                 /**
    1163                  * Filter the given taxonomy's terms cache.
    1164                  *
    1165                  * @since 2.3.0
    1166                  *
    1167                  * @param array $cache      Cached array of terms for the given taxonomy.
    1168                  * @param array $taxonomies An array of taxonomies.
    1169                  * @param array $args       An array of get_terms() arguments.
    1170                  */
    1171                 return apply_filters( 'get_terms', $cache, $taxonomies, $args );
    1172         }
    1173 
    11741147        $_orderby = strtolower( $args['orderby'] );
    11751148        if ( 'count' == $_orderby ) {
     
    14191392        $query = "SELECT $fields FROM $wpdb->terms AS t $join WHERE $where $orderby $order $limits";
    14201393
     1394        // $args can be anything. Only use the args defined in defaults to compute the key.
     1395        $key = md5( serialize( wp_array_slice_assoc( $args, array_keys( $defaults ) ) ) . serialize( $taxonomies ) . $query );
     1396        $last_changed = wp_cache_get( 'last_changed', 'terms' );
     1397        if ( ! $last_changed ) {
     1398                $last_changed = microtime();
     1399                wp_cache_set( 'last_changed', $last_changed, 'terms' );
     1400        }
     1401        $cache_key = "get_terms:$key:$last_changed";
     1402        $cache = wp_cache_get( $cache_key, 'terms' );
     1403        if ( false !== $cache ) {
     1404                if ( 'all' === $_fields ) {
     1405                        $cache = array_map( 'get_term', $cache );
     1406                }
     1407
     1408                /**
     1409                 * Filter the given taxonomy's terms cache.
     1410                 *
     1411                 * @since 2.3.0
     1412                 *
     1413                 * @param array $cache      Cached array of terms for the given taxonomy.
     1414                 * @param array $taxonomies An array of taxonomies.
     1415                 * @param array $args       An array of get_terms() arguments.
     1416                 */
     1417                return apply_filters( 'get_terms', $cache, $taxonomies, $args );
     1418        }
     1419
    14211420        if ( 'count' == $_fields ) {
    14221421                return $wpdb->get_var( $query );
Note: See TracChangeset for help on using the changeset viewer.