Make WordPress Core

Changeset 55608


Ignore:
Timestamp:
03/29/2023 10:48:34 AM (2 years ago)
Author:
spacedmonkey
Message:

Options, Meta APIs: Improve the lazy loading meta API to include current object id.

The existing lazy loading meta api, creates a queue of ids, to be primed, if the get_comment_meta or get_term_meta functions are called. However, it did not check to see if the requested id was in the queue, before prime all the ids in the queue. Now, it adds the id to the queue, is not already in the queue, saving a cache lookup / database query.

Props spacedmonkey, peterwilsoncc, mukesh27, flixos90.
Fixes #57901.

Location:
trunk
Files:
1 added
2 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/wp-includes/class-wp-metadata-lazyloader.php

    r54133 r55608  
    5656            'term'    => array(
    5757                'filter'   => 'get_term_metadata',
    58                 'callback' => array( $this, 'lazyload_term_meta' ),
     58                'callback' => array( $this, 'lazyload_meta_callback' ),
    5959            ),
    6060            'comment' => array(
    6161                'filter'   => 'get_comment_metadata',
    62                 'callback' => array( $this, 'lazyload_comment_meta' ),
     62                'callback' => array( $this, 'lazyload_meta_callback' ),
    6363            ),
    6464        );
     
    9292        }
    9393
    94         add_filter( $type_settings['filter'], $type_settings['callback'] );
     94        add_filter( $type_settings['filter'], $type_settings['callback'], 10, 5 );
    9595
    9696        /**
     
    132132     *
    133133     * @since 4.5.0
     134     * @deprecated 6.3.0 Use WP_Metadata_Lazyloader::lazyload_meta_callback() instead.
    134135     *
    135136     * @param mixed $check The `$check` param passed from the 'get_term_metadata' hook.
     
    138139     */
    139140    public function lazyload_term_meta( $check ) {
    140         if ( ! empty( $this->pending_objects['term'] ) ) {
    141             update_termmeta_cache( array_keys( $this->pending_objects['term'] ) );
    142 
    143             // No need to run again for this set of terms.
    144             $this->reset_queue( 'term' );
    145         }
    146 
    147         return $check;
     141        _deprecated_function( __METHOD__, '6.3.0', 'WP_Metadata_Lazyloader::lazyload_meta_callback' );
     142        return $this->lazyload_meta_callback( $check, 0, '', false, 'term' );
    148143    }
    149144
     
    155150     *
    156151     * @since 4.5.0
     152     * @deprecated 6.3.0 Use WP_Metadata_Lazyloader::lazyload_meta_callback() instead.
    157153     *
    158154     * @param mixed $check The `$check` param passed from the {@see 'get_comment_metadata'} hook.
     
    160156     */
    161157    public function lazyload_comment_meta( $check ) {
    162         if ( ! empty( $this->pending_objects['comment'] ) ) {
    163             update_meta_cache( 'comment', array_keys( $this->pending_objects['comment'] ) );
     158        _deprecated_function( __METHOD__, '6.3.0', 'WP_Metadata_Lazyloader::lazyload_meta_callback' );
     159        return $this->lazyload_meta_callback( $check, 0, '', false, 'comment' );
     160    }
    164161
    165             // No need to run again for this set of comments.
    166             $this->reset_queue( 'comment' );
     162    /**
     163     * Lazy-loads meta for queued objects.
     164     *
     165     * This method is public so that it can be used as a filter callback. As a rule, there
     166     * is no need to invoke it directly.
     167     *
     168     * @since 6.3.0
     169     *
     170     * @param mixed  $check     The `$check` param passed from the 'get_*_metadata' hook.
     171     * @param int    $object_id ID of the object metadata is for.
     172     * @param string $meta_key  Unused.
     173     * @param bool   $single    Unused.
     174     * @param string $meta_type Type of object metadata is for. Accepts 'post', 'comment', 'term', 'user',
     175     *                          or any other object type with an associated meta table.
     176     * @return mixed In order not to short-circuit `get_metadata()`. Generally, this is `null`, but it could be
     177     *               another value if filtered by a plugin.
     178     */
     179    public function lazyload_meta_callback( $check, $object_id, $meta_key, $single, $meta_type ) {
     180        if ( empty( $this->pending_objects[ $meta_type ] ) ) {
     181            return $check;
    167182        }
     183
     184        $object_ids = array_keys( $this->pending_objects[ $meta_type ] );
     185        if ( $object_id && ! in_array( $object_id, $object_ids, true ) ) {
     186            $object_ids[] = $object_id;
     187        }
     188
     189        update_meta_cache( $meta_type, $object_ids );
     190
     191        // No need to run again for this set of objects.
     192        $this->reset_queue( $meta_type );
    168193
    169194        return $check;
  • trunk/tests/phpunit/tests/query/lazyLoadTermMeta.php

    r55252 r55608  
    109109    }
    110110
     111
     112    /**
     113     * @ticket 57901
     114     *
     115     * @covers ::wp_queue_posts_for_term_meta_lazyload
     116     */
     117    public function test_wp_queue_posts_for_term_meta_lazyload_insert_term() {
     118        $filter = new MockAction();
     119        add_filter( 'update_term_metadata_cache', array( $filter, 'filter' ), 10, 2 );
     120
     121        register_taxonomy( 'wptests_tax', 'post' );
     122
     123        $t1      = wp_insert_term( 'Foo', 'wptests_tax' );
     124        $term_id = $t1['term_id'];
     125
     126        new WP_Query(
     127            array(
     128                'post__in'            => self::$post_ids,
     129                'lazy_load_term_meta' => true,
     130            )
     131        );
     132
     133        get_term_meta( $term_id );
     134
     135        $args     = $filter->get_args();
     136        $first    = reset( $args );
     137        $term_ids = end( $first );
     138        $this->assertContains( $term_id, $term_ids );
     139    }
     140
    111141    /**
    112142     * @ticket 57150
     
    134164        $first    = reset( $args );
    135165        $term_ids = end( $first );
    136         $this->assertNotContains( $remove_term_id, $term_ids );
     166        $this->assertContains( $remove_term_id, $term_ids );
    137167    }
    138168}
Note: See TracChangeset for help on using the changeset viewer.