Replace Woocommerce_Add_Order_Item_Meta Hook in Woocommerce 3.4

Replace woocommerce_add_order_item_meta hook in Woocommerce 3.4

Updated

Since Woocommerce version 3, woocommerce_checkout_create_order_line_item action hook now replace outdated woocommerce_add_order_item_meta hook in a much better way using the new introduced CRUD getters and setters methods:

// Save custom data to order item meta data
add_action( 'woocommerce_checkout_create_order_line_item', 'tshirt_order_meta_handler', 20, 4 );
function tshirt_order_meta_handler( $item, $cart_item_key, $values, $order ) {
$custom_designer = WC()->session->get( $cart_item_key.'_designer' );
if( ! empty($custom_designer) ) {
$item->update_meta_data( 'custom_designer', $custom_designer );
}
}

Code goes in function.php file of your active child theme (or active theme). It should works.

See this related thread:

Woocommerce: Which hook to replace deprecated "woocommerce_add_order_item_meta"

Replace woocommerce_add_order_item_meta hook in Woocommerce 3+

You need to change more than just the hook… The hooked function arguments are wrong in your code and the way to updated data has changed too. Try the following:

add_action( 'woocommerce_checkout_create_order_line_item', 'add_business_days', 10, 4 );
function add_business_days( $order_item, $cart_item_key, $cart_item, $order ){

$now = current_time( 'mysql' );
$add = $cart_item['data']->get_meta( 'dp_kargolanma_suresi' );
$d = new DateTime( $now );
$t = $d->getTimestamp();
$oneDay = 86400;
$nextDay = date('w', ($t + $oneDay));

// loop for X days
for( $i = 0; $i < $add; $i++ ) {
// if it's Saturday or Sunday get $i-1
if($nextDay == 0 || $nextDay == 6) {
$i--;
}
// modify timestamp, add 1 day
$t = $t + $oneDay;
}
$d->setTimestamp($t);

$teslim_tarihi = $d->format( 'd-m-Y' ). "\n";
$desiveyakg = ( $cart_item['quantity'] * $cart_item['data']->get_weight() );
$kargosinifi = $cart_item['data']->get_shipping_class();

$order_item->update_meta_data( 'En Gec Kargolanma Tarihi', $teslim_tarihi );
$order_item->update_meta_data( '_desi_kg', $desiveyakg );
$order_item->update_meta_data( '_alici_onay_durumu', 'Onay Bekliyor' );

if($cart_item['quantity'] >= 100) {
$order_item->update_meta_data( '_kargo_sinifi', 'ucretsiz-kargo' );
} else {
$order_item->update_meta_data( '_kargo_sinifi', $kargosinifi );
}
}

It should work…

Woocommerce: Which hook to replace deprecated woocommerce_add_order_item_meta

If you look at wc-deprecated-functions.php you will see

/**
* @deprecated
*/
function woocommerce_add_order_item_meta( $item_id, $meta_key, $meta_value, $unique = false ) {
return wc_add_order_item_meta( $item_id, $meta_key, $meta_value, $unique );
}

Basically, the function was renamed to wc_add_order_item_meta(), so if you need the function then use that. The action hook was not renamed and remains in class-wc-checkout.php as:

// Allow plugins to add order item meta
do_action( 'woocommerce_add_order_item_meta', $item_id, $values, $cart_item_key );

Problem with woocommerce_add_order_item_meta

Hook woocommerce_add_order_item_meta is replaced by woocommerce_checkout_create_order_line_item, so with your code (assuming that the cart object contains your custom cart item data):

add_action('woocommerce_checkout_create_order_line_item', 'save_custom_order_item_meta_data', 10, 4 );
function save_custom_order_item_meta_data( $item, $cart_item_key, $values, $order ) {
if( isset( $values['custom_data']['label'] ) && isset( $values['custom_data']['value'] ) ) {
$item->update_meta_data( $values['custom_data']['label'], $values['custom_data']['value'] );
}
}

Code goes in function.php file of your active child theme (or active theme). It should works.

Related:

  • Replace woocommerce_add_order_item_meta hook in Woocommerce 3.4
  • Woocommerce: Which hook to replace deprecated "woocommerce_add_order_item_meta"
  • Threads with: woocommerce_checkout_create_order_line_item action hook

How to add new meta item for each order item in WooCommerce?

Try this instead,

add_action( 'woocommerce_checkout_create_order_line_item', 'add_my_meta_to_line_item', 10, 4 );

function add_my_meta_to_line_item( $item, $cart_item_key, $values, $order) {
if ($_POST['design']) $item->add_meta_data( 'design', esc_attr($_POST['design'], true ));
}

Custom meta data added to Woocommerce not displayed in order item meta

The data that you are looking for is not order meta data, but order item meta data and is located in wp_woocommerce_order_itemmeta database table (see below how to access this data).

Since woocommerce 3, a much better hook replace old woocommerce_add_order_item_meta hook.

Displayed and readable order item meta data:

To make custom order item meta data displayed everywhere, the meta key should be a readable label name and without starting by an underscore, as this data will be displayed under each order item.

The code:

add_action( 'woocommerce_checkout_create_order_line_item', 'custom_order_item_meta', 20, 4 );
function custom_order_item_meta( $item, $cart_item_key, $values, $order ) {
if ( isset( $values['custom_option'] ) ) {
$item->update_meta_data( __('Custom option', 'woocommerce'), $values['custom_option'] );
}
}

In "Order received" (thankyou) page, you will get something like:

Sample Image

This will be displayed too in backend and email notifications.

To access this order item data you need to get items from the order object in a foreach loop:

foreach( $order->get_items() as $item_id => $item ){
    $custom_data = $item->get_meta( 'Custom option' );
}

To Get the first order item (avoiding a foreach loop), you will use:

$items       = $order->get_items(); // Order items
$item        = reset($items); // The first Order item
$custom_data = $item->get_meta( 'Custom option' ); // Your custom meta data

Related: Replace woocommerce_add_order_item_meta hook in Woocommerce 3.4

WooCommerce order again and custom item data for price calculation

You are not saving all the required cart item data as custom order item meta, so when using "Order again", some custom cart item data is missing ad your price calculations doesn't get applied.

Also woocommerce_add_order_item_meta hook is deprecated since WooCommerce 3.

Note: With your provided code, I am not able to change the percentage in cart page, so maybe something is missing.

You will need to remove/replace in your code the following functions:

// Add order item meta.
add_action('woocommerce_add_order_item_meta', 'add_order_item_meta', 10, 3);
function add_order_item_meta($item_id, $cart_item, $cart_item_key)
{
if (isset($cart_item['percentage'])) {
wc_add_order_item_meta($item_id, 'percentage', $cart_item['percentage']);
}
}

and this one too:

add_filter( 'woocommerce_order_again_cart_item_data', 'order_again_custom', 10, 3 );

function order_again_custom($cart_item_meta, $product, $order){
//Create an array of all the missing custom field keys that needs to be added in cart item.
$customfields = [
'Titulo1',
'percentage',
'custom_price',
'price',
'new_price',
];
global $woocommerce;
remove_all_filters( 'woocommerce_add_to_cart_validation' );
if ( ! array_key_exists( 'item_meta', $cart_item_meta ) || ! is_array( $cart_item_meta['item_meta'] ) )
foreach ( $customfields as $key ){
if(!empty($product[$key])){
$cart_item_meta[$key] = $product[$key];
}
}
return $cart_item_meta;
}

by the following ones:

// Save custom cart item data as custom order item meta data
add_action( 'woocommerce_checkout_create_order_line_item', 'add_order_item_meta', 10, 4 );
function add_order_item_meta( $item, $cart_item_key, $values, $order ) {

// Save and display the "Percentage" (optional - if needed)
if (isset($values['percentage'])) {
$item->update_meta_data( 'Percentage', $values['percentage'] );
}

// Save All custom cart item data as a hidden data array (important)
if (isset($values['percentage']) && isset($values['base_price']) && isset($values['new_price']) ) {
$custom_data = array(
'percentage' => $values['percentage'],
'base_price' => $values['base_price'],
'new_price' => $values['new_price'],
);
$item->update_meta_data( '_custom_data', $custom_data ); // save
}
}

// Add custom order item meta as custom cart item meta
add_filter( 'woocommerce_order_again_cart_item_data', 'custom_cart_item_data_for_order_again', 10, 3 );
function custom_cart_item_data_for_order_again( $cart_item_meta, $item, $order ) {
// Get the hidden order item data
$custom_data = (array) $item->get_meta( '_custom_data' );

if( ! empty($custom_data) ) {
$cart_item_meta = array_merge( $cart_item_meta, $custom_data );
}
return $cart_item_meta;
}

Code goes in function.php file of your active child theme (or active theme). Tested and works.



Related Topics



Leave a reply



Submit