WooCommerce offers a powerful coupon system, but one major limitation is that it doesn’t natively support discounts on shipping costs. By default, you can apply coupons to product prices, but if you want to offer a discount on shipping fees, you need to use custom code.
In this post, we’ll show you how to apply a 50% discount on shipping costs when a specific coupon is used, while also ensuring the checkout displays this information cleanly.
Why WooCommerce Doesn’t Support Shipping Discounts Natively
WooCommerce’s built-in coupon system allows discounts on products, carts, and even free shipping, but it doesn’t provide a way to apply percentage-based discounts to shipping fees. If you want to reduce shipping costs dynamically when a coupon is applied, you’ll need to use a custom function.
How to Add a Shipping Discount for a Coupon in WooCommerce
Firstly, you need to create a coupon in WooCommerce with the coupon code that you want to use.
In our example, we’re going to use the coupon code “COURAGE“.
- In WordPress head to “Marketing > Coupons
- Create you coupon and set the expiry date, if desired.
- Now add this custom code snippet.
You can add this to your functions.php file (if you’re using a child theme). Or, my preferred method is to use the free Code Snippets plugin to easily add code snippets, without needing to edit functions.php
The following code automatically applies a 50% discount on shipping when the “COURAGE” coupon is used at checkout. It also ensures that:
- The discount appears properly in the order totals.
- The coupon discount row is hidden if the discount is $0.00 (to avoid confusion).
- The shipping discount label clearly mentions the coupon used.
The Custom Code Solution
// Define the coupon code as a constant define( 'COUPON_CODE', 'COURAGE' ); function apply_shipping_discount_for_coupon( $cart ) { // Use the constant instead of hardcoding the coupon code $coupon_code = COUPON_CODE; // Only apply the coupon code if it exists in the cart if ( isset( WC()->cart ) && WC()->cart->has_discount( $coupon_code ) ) { $coupon = new WC_Coupon( $coupon_code ); $expiry_date = $coupon->get_date_expires(); // Get expiry date from WooCommerce coupon settings // If the coupon has an expiry date and it's expired, do nothing if ( $expiry_date && time() > $expiry_date->getTimestamp() ) { return; } // Get the total shipping cost $shipping_total = $cart->get_shipping_total(); $shipping_discount = $shipping_total * 0.50; // Apply the shipping discount $cart->add_fee( __( 'Coupon: ' . strtoupper( $coupon_code ) . ' - Shipping Discount (50%)', 'woocommerce' ), -$shipping_discount, true ); } } add_action( 'woocommerce_cart_calculate_fees', 'apply_shipping_discount_for_coupon', 20 ); // Hide the "Coupon" row when discount is $0.00 add_filter( 'woocommerce_cart_totals_coupon_label', 'hide_zero_value_coupon', 10, 2 ); add_filter( 'woocommerce_cart_totals_coupon_html', 'hide_zero_value_coupon_amount', 10, 2 ); function hide_zero_value_coupon( $coupon_label, $coupon ) { // Use the constant instead of hardcoding the coupon code $coupon_code = COUPON_CODE; if ( strtoupper( $coupon->get_code() ) === $coupon_code && WC()->cart->get_coupon_discount_amount( $coupon->get_code() ) == 0 ) { return ''; // Hide coupon label } return $coupon_label; } function hide_zero_value_coupon_amount( $discount_html, $coupon ) { // Use the constant instead of hardcoding the coupon code $coupon_code = COUPON_CODE; if ( strtoupper( $coupon->get_code() ) === $coupon_code && WC()->cart->get_coupon_discount_amount( $coupon->get_code() ) == 0 ) { return ''; // Hide coupon amount } return $discount_html; }
The end result
Here’s what the end result looks like:
The coupon code is displayed alongside “Shipping Discount (50%)” and then the amount discounted.
You can adjust the Shipping percentage on the $shipping_discount line. And you’ll also need to change the % shown in the discount label.
And adjust the coupon code on the second line where it declares the constant, so that it matches the coupon code you added in WooCommerce.
Happy discounting!