I'm trying to create an order programmatically. Using wc_create_order()
this is pretty straightforward:
$myProduct = new WC_Product(100);
$order = wc_create_order();
$order->add_product($myProduct, 1);
$order->calculate_totals();
This works as expected, and an order is created for a simple product with ID 100 for the correct amount.
However, if I try to do this with a variation, it doesn't seem to behave correctly. After much trial and error, I got it to sort-of work this way:
$membershipProduct = new WC_Product_Variable(100);
$theMemberships = $membershipProduct->get_available_variations();
$trueProduct = new WC_Product(100);
$variationsArray = array();
foreach ($theMemberships as $membership) {
if ($membership['sku'] == $chosenVariation) {
$variationID = $membership['variation_id'];
$variationsArray = $membership['attributes'];
}
}
if ($variationID) {
$trueProduct->variation_id = $variationID;
}
$order = wc_create_order();
$order->add_product($trueProduct, 1, $variationsArray);
$order->calculate_totals();
However, although it does create the order with the correct product and the correct variation ID, the total for the order is always 0 (which, coincidentally, is the price of the first variation).
Originally I was trying $order->add_product()
with the object created from new WC_Product_Variable()
, but that resulted in no products being added to the order at all, which leads me to believe it's an issue with creating orders programmatically with variable products. However, following the WooCommerce source code for these calls, I can't see what I'm doing wrong.
Is there something I'm missing, or a better way to create an order with a variable product?
We can use the WC function to create the order programmatically, also we can set the order number. You can add the following codes to the functions. php file. You can also change the get_product( 1061 ) ID to add the product number of orders.
Solved it.
Even though I could have sworn I'd tried (and failed) doing it this way, the answer was to not add the parent product ($trueProduct
in the example), but to add the variation product by its ID.
This may have failed previously because, as @helgatheviking noted, my $variationsArray
was formatted incorrectly according to the source; I needed an array with a ['variation']
key to send the correct variation array of attributes.
In total, my working code now looks like this:
$membershipProduct = new WC_Product_Variable(100);
$theMemberships = $membershipProduct->get_available_variations();
$variationsArray = array();
foreach ($theMemberships as $membership) {
if ($membership['sku'] == $chosenVariation) {
$variationID = $membership['variation_id'];
$variationsArray['variation'] = $membership['attributes'];
}
}
if ($variationID) {
$varProduct = new WC_Product_Variation($variationID);
$order = wc_create_order();
$order->add_product($varProduct, 1, $variationsArray);
$order->calculate_totals();
}
if you already have the variation_id you can just do this
$product_variation = new WC_Product_Variation($variation_id);
$order = wc_create_order();
$args=array();
foreach($product_variation->get_variation_attributes() as $attribute=>$attribute_value){
$args['variation'][$attribute]=$attribute_value;
}
$order->add_product($product_variation, $product['quantity'], $args);
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With