How to add a fee at WooCommerce checkout 2024

Recently, I was asked to add an optional fee at WooCommerce checkout to cover the costs of split shipping for orders that contain back-ordered products. The idea was to give the customer the opportunity to pay for a second shipping fee to send part of the order immediately and the remainder when the stock arrived. As the store used flat rate shipping, the best option was to add an optional fee to the checkout page.

Once enabled the checkout page will display an optional checkbox with a fee amount and label. When checked it will trigger an ajax call to update the cart totals and add the fee to the order. This fee then appears as a fee on the order edit page and is also available in the rest-API.

This snippet can be used for a range of different scenarios. While I was asked to implement it for backorder partial fulfillment, it can also be used to add a surcharge for visitors, a discount for logged in users, expedited handling and much more.

Begin by adding a checkbox to the shipping area. Use our WooCommerce checkout page visual hooks guide for other locations.


/*
 * Snippet: How to add a fee at WooCommerce checkout 2024
* Author: John Cook
* URL: https://wcsuccessacademy.com/?795
* Tested with WooCommerce 8.8.2
* "Add a checkbox to the shipping area"
*/ add_action( 'woocommerce_review_order_before_order_total', 'wcsuccess_fee_checkbox_field', 20 ); function wcsuccess_fee_checkbox_field(){ echo '<tr class="packing-select"><th>'; woocommerce_form_field( 'additional_fee', array( 'type' => 'checkbox', 'class' => array('additional-fee form-row-wide'), 'label' => __('Additional fee'), ), WC()->session->get('additional_fee') ? '1' : '' ); echo '</th><td>'; }

Add some JS that triggers an update to the checkout when the checkbox detects a change.

/*
 * Snippet: How to add a fee at WooCommerce checkout 2024
* Author: John Cook
* URL: https://wcsuccessacademy.com/?795
* Tested with WooCommerce 8.8.2
* "Add JS to trigger update to checkout"
*/ add_action( 'wp_footer', 'wcsuccess_add_fee_update_totals' ); function wcsuccess_add_fee_update_totals() { if( is_checkout() && ! is_wc_endpoint_url() ) : if( WC()->session->__isset('additional_fee') ) WC()->session->__unset('additional_fee'); ?> <script type="text/javascript"> jQuery( function($){ if (typeof wc_checkout_params === 'undefined') return false; $('form.checkout').on('change', 'input[name=additional_fee]', function(){ let fee = $(this).prop('checked') === true ? '1' : ''; $.ajax({ type: 'POST', url: wc_checkout_params.ajax_url, data: { 'action': 'additional_fee', 'installment_fee': fee, }, success: function (result) { $('body').trigger('update_checkout'); }, }); }); }); </script> <?php endif; }

Next we need to get the Ajax request response and save the checkbox value to the session.

/*
 * Snippet: How to add a fee at WooCommerce checkout 2024
* Author: John Cook
* URL: https://wcsuccessacademy.com/?795
* Tested with WooCommerce 8.8.2
* "Get Ajax request and saving to WC session"
*/ add_action( 'wp_ajax_installment_fee', 'wcsuccess_get_additional_fee' ); add_action( 'wp_ajax_nopriv_installment_fee', 'wcsuccess_get_additional_fee' ); function get_installment_fee() { if ( isset($_POST['additional_fee']) ) { WC()->session->set('additional_fee', ($_POST['additional_fee'] ? true : false) ); } die(); }

Next, we add the additional fee. In this example we are adding a 10% fee of the subtotal of the cart. If you want you can change it to a round number or any other calculation.

/*
 * Snippet: How to add a fee at WooCommerce checkout 2024
* Author: John Cook
* URL: https://wcsuccessacademy.com/?795
* Tested with WooCommerce 8.8.2
* "Add a custom calculated fee conditionally"
*/ add_action( 'woocommerce_cart_calculate_fees', 'wcsuccess_set_installment_fee' ); function wcsuccess_set_installment_fee( $cart ){ global $woocommerce; if ( is_admin() && ! defined('DOING_AJAX') || ! is_checkout() ) return; if ( did_action('woocommerce_cart_calculate_fees') >= 2 ) return; if ( 1 == WC()->session->get('additional_fee') ) { $fee_label = sprintf( __( "Ship instock items immediately" )); $fee_amount = $woocommerce->cart->get_subtotal() * 0.1; // adds 10% fee on subtotal value. This can be chaned to any value or calculation WC()->cart->add_fee( $fee_label, $fee_amount ); } }

If you want to remove the optional (optional) text next to the label you can add the following code. Instead of displaying:

It will display:

/*
 * Snippet: How to add a fee at WooCommerce checkout 2024
* Author: John Cook
* URL: https://wcsuccessacademy.com/?795
* Tested with WooCommerce 8.8.2
* "Remove optional text"
*/add_filter( 'woocommerce_form_field' , 'wcsuccess_remove_optional_txt_from_checkbox', 10, 4 ); function wcsuccess_remove_optional_txt_from_checkbox( $field, $key, $args, $value ) { // Only on checkout page for Order notes field if( 'additional_fee' === $key && is_checkout() ) { $optional = ' <span class="optional">(' . esc_html__( 'optional', 'woocommerce' ) . ')</span>'; $field = str_replace( $optional, '', $field ); } return $field; }

Add the above snippets to your child themes functions.php file or code snippet plugin. Modify the label and amounts to suit your own needs and customise its display as necessary.

0 0 votes
Article Rating

Stay In Touch

Was this post helpful? Why not show your support and buy me a coffee?

Subscribe
Notify of
guest
0 Comments
Inline Feedbacks
View all comments
0
Would love your thoughts, please comment.x
()
x
Scroll to Top
×