Make WordPress Core

Changeset 34999


Ignore:
Timestamp:
10/10/2015 03:38:41 AM (11 years ago)
Author:
boonebgorges
Message:

Return WP_Post objects from wp_get_object_terms().

A side effect of this change is that terms stored in the cache no longer have
an object_id associated with them. Previously, object_id had always been
cached when the term cache was populated via wp_get_object_terms(), a
strategy that was mostly harmless but still incorrect.

See #14162.

Location:
trunk
Files:
2 edited

Legend:

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

    r34998 r34999  
    21952195 * @since 4.2.0 Added support for 'taxonomy', 'parent', and 'term_taxonomy_id' values of `$orderby`.
    21962196 *              Introduced `$parent` argument.
    2197  * @since 4.4.0 Introduced `$meta_query` and `$update_term_meta_cache` arguments.
     2197 * @since 4.4.0 Introduced `$meta_query` and `$update_term_meta_cache` arguments. When `$fields` is 'all' or
     2198 *              'all_with_object_id', an array of `WP_Term` objects will be returned.
    21982199 *
    21992200 * @global wpdb $wpdb WordPress database abstraction object.
     
    23372338        if ( 'all' == $fields || 'all_with_object_id' == $fields ) {
    23382339                $_terms = $wpdb->get_results( $query );
     2340                $object_id_index = array();
    23392341                foreach ( $_terms as $key => $term ) {
    2340                         $_terms[$key] = sanitize_term( $term, $taxonomy, 'raw' );
    2341                 }
     2342                        $term = sanitize_term( $term, $taxonomy, 'raw' );
     2343                        $_terms[ $key ] = $term;
     2344
     2345                        if ( isset( $term->object_id ) ) {
     2346                                $object_id_index[ $key ] = $term->object_id;
     2347                        }
     2348                }
     2349
     2350                update_term_cache( $_terms );
     2351                $_terms = array_map( 'get_term', $_terms );
     2352
     2353                // Re-add the object_id data, which is lost when fetching terms from cache.
     2354                if ( 'all_with_object_id' === $fields ) {
     2355                        foreach ( $_terms as $key => $_term ) {
     2356                                if ( isset( $object_id_index[ $key ] ) ) {
     2357                                        $_term->object_id = $object_id_index[ $key ];
     2358                                }
     2359                        }
     2360                }
     2361
    23422362                $terms = array_merge( $terms, $_terms );
    2343                 update_term_cache( $terms );
    23442363                $objects = true;
     2364
    23452365        } elseif ( 'ids' == $fields || 'names' == $fields || 'slugs' == $fields ) {
    23462366                $_terms = $wpdb->get_col( $query );
     
    35563576function update_term_cache( $terms, $taxonomy = '' ) {
    35573577        foreach ( (array) $terms as $term ) {
    3558                 $term_taxonomy = $taxonomy;
    3559                 if ( empty($term_taxonomy) )
    3560                         $term_taxonomy = $term->taxonomy;
    3561 
    3562                 wp_cache_add( $term->term_id, $term, 'terms' );
     3578                // Create a copy in case the array was passed by reference.
     3579                $_term = $term;
     3580
     3581                // Object ID should not be cached.
     3582                unset( $_term->object_id );
     3583
     3584                wp_cache_add( $term->term_id, $_term, 'terms' );
    35633585        }
    35643586}
  • trunk/tests/phpunit/tests/term/wpGetObjectTerms.php

    r34529 r34999  
    499499        }
    500500
     501        /**
     502         * @ticket 14162
     503         */
     504        public function test_should_return_wp_term_objects_for_fields_all() {
     505                register_taxonomy( 'wptests_tax', 'post' );
     506                $p = $this->factory->post->create();
     507                $t = $this->factory->term->create( array( 'taxonomy' => 'wptests_tax' ) );
     508                wp_set_object_terms( $p, $t, 'wptests_tax' );
     509
     510                $found = wp_get_object_terms( $p, 'wptests_tax', array(
     511                        'fields' => 'all',
     512                ) );
     513
     514                $this->assertNotEmpty( $found );
     515                foreach ( $found as $f ) {
     516                        $this->assertInstanceOf( 'WP_Term', $f );
     517                }
     518        }
     519
     520        /**
     521         * @ticket 14162
     522         */
     523        public function test_should_return_wp_term_objects_for_fields_all_with_object_id() {
     524                register_taxonomy( 'wptests_tax', 'post' );
     525                $p = $this->factory->post->create();
     526                $t = $this->factory->term->create( array( 'taxonomy' => 'wptests_tax' ) );
     527                wp_set_object_terms( $p, $t, 'wptests_tax' );
     528
     529                $found = wp_get_object_terms( $p, 'wptests_tax', array(
     530                        'fields' => 'all_with_object_id',
     531                ) );
     532
     533                $this->assertNotEmpty( $found );
     534                foreach ( $found as $f ) {
     535                        $this->assertInstanceOf( 'WP_Term', $f );
     536                }
     537        }
     538
     539        /**
     540         * @ticket 14162
     541         */
     542        public function test_should_prime_cache_for_found_terms() {
     543                global $wpdb;
     544
     545                register_taxonomy( 'wptests_tax', 'post' );
     546                $p = $this->factory->post->create();
     547                $t = $this->factory->term->create( array( 'taxonomy' => 'wptests_tax' ) );
     548                wp_set_object_terms( $p, $t, 'wptests_tax' );
     549
     550                $found = wp_get_object_terms( $p, 'wptests_tax', array(
     551                        'fields' => 'all_with_object_id',
     552                ) );
     553
     554                $num_queries = $wpdb->num_queries;
     555                $term = get_term( $t );
     556                $this->assertSame( $num_queries, $wpdb->num_queries );
     557        }
     558
     559        /**
     560         * @ticket 14162
     561         */
     562        public function test_object_id_should_not_be_cached_with_term_object() {
     563                register_taxonomy( 'wptests_tax', 'post' );
     564                $p = $this->factory->post->create();
     565                $t = $this->factory->term->create( array( 'taxonomy' => 'wptests_tax' ) );
     566                wp_set_object_terms( $p, $t, 'wptests_tax' );
     567
     568                $found = wp_get_object_terms( $p, 'wptests_tax', array(
     569                        'fields' => 'all_with_object_id',
     570                ) );
     571
     572                foreach ( $found as $f ) {
     573                        $this->assertSame( $p, $f->object_id );
     574                }
     575
     576                $term = get_term( $t );
     577                $this->assertFalse( isset( $term->object_id ) );
     578        }
     579
     580        /**
     581         * @ticket 14162
     582         */
     583        public function test_term_cache_should_be_primed_for_all_taxonomies() {
     584                global $wpdb;
     585
     586                register_taxonomy( 'wptests_tax1', 'post' );
     587                register_taxonomy( 'wptests_tax2', 'post' );
     588                $p = $this->factory->post->create();
     589                $t1 = $this->factory->term->create( array( 'taxonomy' => 'wptests_tax1' ) );
     590                $t2 = $this->factory->term->create( array( 'taxonomy' => 'wptests_tax2' ) );
     591                wp_set_object_terms( $p, $t1, 'wptests_tax1' );
     592                wp_set_object_terms( $p, $t2, 'wptests_tax2' );
     593
     594                $found = wp_get_object_terms( $p, array(
     595                        'wptests_tax1',
     596                        'wptests_tax2',
     597                ), array(
     598                        'fields' => 'all_with_object_id',
     599                ) );
     600
     601                $this->assertEqualSets( array( $t1, $t2 ), wp_list_pluck( $found, 'term_id' ) );
     602
     603                $num_queries = $wpdb->num_queries;
     604                $term1 = get_term( $t1 );
     605                $term2 = get_term( $t2 );
     606                $this->assertSame( $num_queries, $wpdb->num_queries );
     607        }
     608
     609        /**
     610         * @ticket 14162
     611         */
     612        public function test_object_id_should_be_set_on_objects_that_share_terms() {
     613                register_taxonomy( 'wptests_tax', 'post' );
     614                $posts = $this->factory->post->create_many( 2 );
     615                $t = $this->factory->term->create( array( 'taxonomy' => 'wptests_tax' ) );
     616                wp_set_object_terms( $posts[0], $t, 'wptests_tax' );
     617                wp_set_object_terms( $posts[1], $t, 'wptests_tax' );
     618
     619                $found = wp_get_object_terms( $posts, 'wptests_tax', array(
     620                        'fields' => 'all_with_object_id',
     621                ) );
     622
     623                $this->assertEqualSets( $posts, wp_list_pluck( $found, 'object_id' ) );
     624        }
     625
    501626        public function filter_get_object_terms( $terms ) {
    502627                $term_ids = wp_list_pluck( $terms, 'term_id' );
Note: See TracChangeset for help on using the changeset viewer.