Make WordPress Core


Ignore:
Timestamp:
11/04/2015 09:23:28 PM (9 years ago)
Author:
boonebgorges
Message:

Don't allow term meta to be added to shared taxonomy terms.

add_term_meta() and update_term_meta() identify terms by $term_id. In
cases where a term is shared between taxonomies, $term_id is insufficient to
distinguish where the metadata belongs.

When attempting to add/update termmeta on a shared term, a WP_Error object
is returned. This gives developers enough information to decide whether they'd
like to force the term to be split and retry the save, or show an error in the
UI, or whatever.

Props boonebgorges, mboynes, DH-Shredder, jorbin, aaroncampbell.
Fixes #34544.

File:
1 edited

Legend:

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

    r35504 r35515  
    15791579 * @param bool   $unique     Optional. Whether to bail if an entry with the same key is found for the term.
    15801580 *                           Default false.
    1581  * @return int|bool Meta ID on success, false on failure.
     1581 * @return int|WP_Error|bool Meta ID on success. WP_Error when term_id is ambiguous between taxonomies.
     1582 *                           False on failure.
    15821583 */
    15831584function add_term_meta( $term_id, $meta_key, $meta_value, $unique = false ) {
     
    15851586    if ( get_option( 'db_version' ) < 34370 ) {
    15861587        return false;
     1588    }
     1589
     1590    if ( wp_term_is_shared( $term_id ) ) {
     1591        return new WP_Error( 'ambiguous_term_id', __( 'Term meta cannot be added to terms that are shared between taxonomies.'), $term_id );
    15871592    }
    15881593
     
    16561661 * @param mixed  $meta_value Metadata value.
    16571662 * @param mixed  $prev_value Optional. Previous value to check before removing.
    1658  * @return int|bool Meta ID if the key didn't previously exist. True on successful update. False on failure.
     1663 * @return int|WP_Error|bool Meta ID if the key didn't previously exist. True on successful update.
     1664 *                           WP_Error when term_id is ambiguous between taxonomies. False on failure.
    16591665 */
    16601666function update_term_meta( $term_id, $meta_key, $meta_value, $prev_value = '' ) {
     
    16621668    if ( get_option( 'db_version' ) < 34370 ) {
    16631669        return false;
     1670    }
     1671
     1672    if ( wp_term_is_shared( $term_id ) ) {
     1673        return new WP_Error( 'ambiguous_term_id', __( 'Term meta cannot be added to terms that are shared between taxonomies.'), $term_id );
    16641674    }
    16651675
     
    40084018    }
    40094019
     4020    // If we've just split the final shared term, set the "finished" flag.
     4021    $shared_terms_exist = $wpdb->get_results(
     4022        "SELECT tt.term_id, t.*, count(*) as term_tt_count FROM {$wpdb->term_taxonomy} tt
     4023         LEFT JOIN {$wpdb->terms} t ON t.term_id = tt.term_id
     4024         GROUP BY t.term_id
     4025         HAVING term_tt_count > 1
     4026         LIMIT 1"
     4027    );
     4028    if ( ! $shared_terms_exist ) {
     4029        update_option( 'finished_splitting_shared_terms', true );
     4030    }
     4031
    40104032    /**
    40114033     * Fires after a previously shared taxonomy term is split into two separate terms.
     
    42534275
    42544276    return $term_id;
     4277}
     4278
     4279/**
     4280 * Determine whether a term is shared between multiple taxonomies.
     4281 *
     4282 * Shared taxonomy terms began to be split in 4.3, but failed cron tasks or other delays in upgrade routines may cause
     4283 * shared terms to remain.
     4284 *
     4285 * @since 4.4.0
     4286 *
     4287 * @param int $term_id
     4288 * @return bool
     4289 */
     4290function wp_term_is_shared( $term_id ) {
     4291    global $wpdb;
     4292
     4293    if ( get_option( 'finished_splitting_shared_terms' ) ) {
     4294        return false;
     4295    }
     4296
     4297    $tt_count = $wpdb->get_var( $wpdb->prepare( "SELECT COUNT(*) FROM $wpdb->term_taxonomy WHERE term_id = %d", $term_id ) );
     4298
     4299    return $tt_count > 1;
    42554300}
    42564301
Note: See TracChangeset for help on using the changeset viewer.