wp_delete_term() │ WP 2.3.0
Deletes a term (category, tag) from the Database.
If the current term is a parent to others, then after its deletion, the child terms will move up one level.
Along with the term, all associated metadata will be deleted. See: delete_metadata_by_mid() .
Returns
true|false|Int|WP_Error .
true - if everything went successfully.
false - if the term could not be deleted.
0 - if this term cannot be deleted.
wp_error - if the taxonomy does not exist.
Usage
wp_delete_term( $term_id, $taxonomy, $args );
$term_id(integer) (required)
ID of the term to be deleted. For example, the id of the category.
$taxonomy(string) (required)
The taxonomy to which the term belongs. For example, category for categories.
$args(array)
Parameters for deleting the term. In particular, here you can specify where to place the objects of the deleted term (posts of the deleted category) if they remain "orphaned" (without any term).
In other words, here we can specify a base term (category) where all orphaned posts will be collected. You can specify two parameters:
default (integer) - after deletion, orphaned posts will be attached to the specified term.
force_default (boolean) - if true, then posts from the deleted term will go to the term specified in default, regardless of whether they remain orphaned or not (whether they have other tags or not).
For the taxonomy category , default is taken from the setting: "default category".
Default: []
Examples
#1 Delete WooCommerce Product Category on Form submit with post request.
$nonce = $_POST['pro_cat_nonce'] ?? '';
$product_cat_id = (int) ( $_POST['id'] ?? '' );
// delete product_cat taxonomy term
if ( $product_cat_id && $nonce && wp_verify_nonce( $nonce, 'pro_cat_nonce_delete' ) ) {
wp_delete_term( $product_cat_id, 'product_cat' );
}
#2 Remove the taxonomy element (term)
Delete term 25, which is in taxonomy category. In other words, delete the category with ID 25.
wp_delete_term( 25, 'category' );
#3 Example of using arguments
Let's remove term 25, of the "books" taxonomy. In doing so, put all the posts of this term into term 15 (parameter default) and it does not matter if these posts remain orphaned (parameter force_default):
wp_delete_term( 25, 'books', [ 'default'=>15, 'force_default'=>true ] );
Add Your Own Example
Notes
Global. wpdb. $wpdb WordPress database abstraction object.
Changelog
wp_delete_term() wp delete term code
WP 7.0
function wp_delete_term( $term, $taxonomy, $args = array() ) {
global $wpdb;
$term = (int) $term;
$ids = term_exists( $term, $taxonomy );
if ( ! $ids ) {
return false;
}
if ( is_wp_error( $ids ) ) {
return $ids;
}
$tt_id = $ids['term_taxonomy_id'];
$defaults = array();
if ( 'category' === $taxonomy ) {
$defaults['default'] = (int) get_option( 'default_category' );
if ( $defaults['default'] === $term ) {
return 0; // Don't delete the default category.
}
}
// Don't delete the default custom taxonomy term.
$taxonomy_object = get_taxonomy( $taxonomy );
if ( ! empty( $taxonomy_object->default_term ) ) {
$defaults['default'] = (int) get_option( 'default_term_' . $taxonomy );
if ( $defaults['default'] === $term ) {
return 0;
}
}
$args = wp_parse_args( $args, $defaults );
if ( isset( $args['default'] ) ) {
$default = (int) $args['default'];
if ( ! term_exists( $default, $taxonomy ) ) {
unset( $default );
}
}
if ( isset( $args['force_default'] ) ) {
$force_default = $args['force_default'];
}
/**
* Fires when deleting a term, before any modifications are made to posts or terms.
*
* @since 4.1.0
*
* @param int $term Term ID.
* @param string $taxonomy Taxonomy name.
*/
do_action( 'pre_delete_term', $term, $taxonomy );
// Update children to point to new parent.
if ( is_taxonomy_hierarchical( $taxonomy ) ) {
$term_obj = get_term( $term, $taxonomy );
if ( is_wp_error( $term_obj ) ) {
return $term_obj;
}
$parent = $term_obj->parent;
$edit_ids = $wpdb->get_results( "SELECT term_id, term_taxonomy_id FROM $wpdb->term_taxonomy WHERE `parent` = " . (int) $term_obj->term_id );
$edit_tt_ids = wp_list_pluck( $edit_ids, 'term_taxonomy_id' );
/**
* Fires immediately before a term to delete's children are reassigned a parent.
*
* @since 2.9.0
*
* @param array $edit_tt_ids An array of term taxonomy IDs for the given term.
*/
do_action( 'edit_term_taxonomies', $edit_tt_ids );
$wpdb->update( $wpdb->term_taxonomy, compact( 'parent' ), array( 'parent' => $term_obj->term_id ) + compact( 'taxonomy' ) );
// Clean the cache for all child terms.
$edit_term_ids = wp_list_pluck( $edit_ids, 'term_id' );
clean_term_cache( $edit_term_ids, $taxonomy );
/**
* Fires immediately after a term to delete's children are reassigned a parent.
*
* @since 2.9.0
*
* @param array $edit_tt_ids An array of term taxonomy IDs for the given term.
*/
do_action( 'edited_term_taxonomies', $edit_tt_ids );
}
// Get the term before deleting it or its term relationships so we can pass to actions below.
$deleted_term = get_term( $term, $taxonomy );
$object_ids = (array) $wpdb->get_col( $wpdb->prepare( "SELECT object_id FROM $wpdb->term_relationships WHERE term_taxonomy_id = %d", $tt_id ) );
foreach ( $object_ids as $object_id ) {
if ( ! isset( $default ) ) {
wp_remove_object_terms( $object_id, $term, $taxonomy );
continue;
}
$terms = wp_get_object_terms(
$object_id,
$taxonomy,
array(
'fields' => 'ids',
'orderby' => 'none',
)
);
if ( 1 === count( $terms ) ) {
$terms = array( $default );
} else {
$terms = array_diff( $terms, array( $term ) );
if ( isset( $force_default ) && $force_default ) {
$terms = array_merge( $terms, array( $default ) );
}
}
$terms = array_map( 'intval', $terms );
wp_set_object_terms( $object_id, $terms, $taxonomy );
}
// Clean the relationship caches for all object types using this term.
$tax_object = get_taxonomy( $taxonomy );
foreach ( $tax_object->object_type as $object_type ) {
clean_object_term_cache( $object_ids, $object_type );
}
$term_meta_ids = $wpdb->get_col( $wpdb->prepare( "SELECT meta_id FROM $wpdb->termmeta WHERE term_id = %d ", $term ) );
foreach ( $term_meta_ids as $mid ) {
delete_metadata_by_mid( 'term', $mid );
}
/**
* Fires immediately before a term taxonomy ID is deleted.
*
* @since 2.9.0
*
* @param int $tt_id Term taxonomy ID.
*/
do_action( 'delete_term_taxonomy', $tt_id );
$wpdb->delete( $wpdb->term_taxonomy, array( 'term_taxonomy_id' => $tt_id ) );
/**
* Fires immediately after a term taxonomy ID is deleted.
*
* @since 2.9.0
*
* @param int $tt_id Term taxonomy ID.
*/
do_action( 'deleted_term_taxonomy', $tt_id );
// Delete the term if no taxonomies use it.
if ( ! $wpdb->get_var( $wpdb->prepare( "SELECT COUNT(*) FROM $wpdb->term_taxonomy WHERE term_id = %d", $term ) ) ) {
$wpdb->delete( $wpdb->terms, array( 'term_id' => $term ) );
}
clean_term_cache( $term, $taxonomy );
/**
* Fires after a term is deleted from the database and the cache is cleaned.
*
* The {@see 'delete_$taxonomy'} hook is also available for targeting a specific
* taxonomy.
*
* @since 2.5.0
* @since 4.5.0 Introduced the `$object_ids` argument.
*
* @param int $term Term ID.
* @param int $tt_id Term taxonomy ID.
* @param string $taxonomy Taxonomy slug.
* @param WP_Term $deleted_term Copy of the already-deleted term.
* @param array $object_ids List of term object IDs.
*/
do_action( 'delete_term', $term, $tt_id, $taxonomy, $deleted_term, $object_ids );
/**
* Fires after a term in a specific taxonomy is deleted.
*
* The dynamic portion of the hook name, `$taxonomy`, refers to the specific
* taxonomy the term belonged to.
*
* Possible hook names include:
*
* - `delete_category`
* - `delete_post_tag`
*
* @since 2.3.0
* @since 4.5.0 Introduced the `$object_ids` argument.
*
* @param int $term Term ID.
* @param int $tt_id Term taxonomy ID.
* @param WP_Term $deleted_term Copy of the already-deleted term.
* @param array $object_ids List of term object IDs.
*/
do_action( "delete_{$taxonomy}", $term, $tt_id, $deleted_term, $object_ids );
return true;
}
Related Functions