0
votes

I am using a custom PHP Script to create variations of a WooCommerce product. The user chooses "Size" and "Color" of the product through a select field, and the variations is created based on that.

Works fine, product is created with the correct price, attribute and variations. Except that you cant select the actual variations when trying to shop (they are "disabled").

When I go back-end in WooCommerce and open the product there, and hit the blue "Update"-button on the product, it works as intended and the variations can be selected and bought front-end.

Is there any function to "force update" the product in PHP after variations have been created?

After creating the product/variations programatically

--

After hitting Update-button back-end it works as intended

Below the code which adds color and size as attributes to the product. Also creates a single variation with "Any color" and "Any size" as the rules.

function save_wc_custom_attributes($post_id, $custom_attributes) {
$i = 0;
$product = wc_get_product( $post_id );
$product_id = $post_id;
$terms = wp_get_post_terms( $post_id, 'pa_farge') ;
// Remove existing colors from the product
foreach ( $terms as $term ) {
  wp_remove_object_terms( $post_id, $term->term_id, 'pa_farge' );
}
$terms = wp_get_post_terms( $post_id, 'pa_str') ;
// Remove existing sizes from the product
foreach ( $terms as $term ) {
  wp_remove_object_terms( $post_id, $term->term_id, 'pa_str' );
}

foreach ($custom_attributes as $name => $value) {
    // Relate post to a custom attribute, add term if it does not exist
    wp_set_object_terms($post_id, $value, $name, true);
    // Create product attributes array
    $product_attributes[$i] = array(
        'name' => $name, // set attribute name
        'value' => $value, // set attribute value
        'is_visible' => 1,
        'is_variation' => 1,
        'is_taxonomy' => 1
    );
    $i++;
}
// Now update the post with its new attributes
update_post_meta($post_id, '_product_attributes', $product_attributes);
// Details for the variation
$variation_post = array(
    'post_title'  => $product->get_name(),
    'post_name'   => 'product-'.$product_id.'-variation',
    'post_status' => 'publish',
    'post_parent' => $product_id,
    'post_type'   => 'product_variation',
    'guid'        => $product->get_permalink()
);

if( !$product->has_child() ) { 
  // Creating a single variation if none exists
  $variation_id = wp_insert_post( $variation_post );
  $variation = new WC_Product_Variation( $variation_id );
  $variation->set_regular_price( $product->get_price() );
  $variation->save(); // Save the data
  $product_variable = new WC_Product_Variable($post_id);
  $product_variable->sync($post_id);
  wc_delete_product_transients($post_id);
}
else {
  // Update the variation if it already exists
  $product_variable = new WC_Product_Variable($post_id);
  $product_variable->sync($post_id);
  wc_delete_product_transients($post_id);
}
$product->save();
}
1

1 Answers

1
votes

Your actual code is jus setting product attributes to the main variable product, but it doesn't set any attribute to a product variation… So the question is may be related to this variable product instead…

So try simply to add at the end of your code:

$product = wc_get_product( $post_id );
$product->save();