0

I am trying to add a new attribute with multiple values to an existing WooCommerce product.

This is the code I am using. I simplified it a bit to make it more clear.

$productId = 87356;

$attr = get_post_meta( $productId, '_product_attributes', true );

$gears = [ '3', '7' ];

$attr['pa_aantal-versnellingen'] = [
    'name' => 'pa_aantal-versnellingen',
    'value' => implode(' | ', $gears),
    'is_visible' => '1',
    'is_variation' => '1',
    'is_taxonomy' => '1'
];

update_post_meta( $productId, '_product_attributes', $attr );

foreach ( $gears as $gear ) {
    wp_set_object_terms( $productId, $gear, 'pa_aantal-versnellingen', true );
}

The attribute appears in the list of attributes on the product. However the terms are not added.

enter image description here

The terms also do exist in the DB:

enter image description here

What do I do wrong? I did a lot of research, read some other questions but they didn't help me.

Create new product attribute programmatically in Woocommerce

jrswgtr
  • 2,287
  • 8
  • 23
  • 49

1 Answers1

0

After studying the WordPress ERD I came up with a workaround.

enter image description here

Instead of wp_set_object_terms(); I use plain MySQL queries.

  1. Get the term_taxonomy_id values from the wp_term_taxonomy table

    $placeholders = array_fill( 0, count( $gears ), '%s' );
    $format = implode( ', ', $placeholders );
    
    $sql = 
        "SELECT tt.term_taxonomy_id" .
        "FROM {$wpdb->prefix}term_taxonomy tt" .
        "JOIN {$wpdb->prefix}terms t ON tt.term_id = t.term_id" . 
        "WHERE tt.taxonomy = 'pa_aantal-versnellingen' AND t.name IN($format)"
    ;
    
    $termTaxIds = $wpdb->get_results( $wpdb->prepare( $sql, $gears ), ARRAY_N );
    
  2. For each term_taxonomy_id value, insert a new entry into the wp_term_relationships table

    foreach ( $termTaxIds as $termTaxId ) {
        $insertSql = 
            "INSERT INTO {$wpdb->prefix}term_relationships" .
            "(object_id, term_taxonomy_id, term_order)" .
            "VALUES (%d, %d, 0)"
        ;
    
        $wpdb->query( $wpdb->prepare( $$insertSql, $productId, $termTaxId[0] ) );
    }
    
jrswgtr
  • 2,287
  • 8
  • 23
  • 49