In WooCommerce version 2.1 a new feature was introduced that allowed one order to have multiple shipping packages. Having multiple shipping packages can come in handy in various situations. One that comes to mind at first is when you actually have multiple packages, for example when you can’t ship items together, or when someone has an order that should ship via two different vendors.
Or the other obvious scenario, having to ship one order to multiple different destinations.

Another very useful use-case that a other WooCommerce user pointed me too not long ago was the ability to allow free shipping on just a specific set of products. When using a shipping carrier plugin like UPS it can be hard to set this up, but when splitting your order into multiple packages, and then setup free shipping (with WooCommerce Advanced Free Shipping for example) you can target only the package with the free shipping items, while the UPS plugin still gets the shipping cost for the other products.

Splitting Shipping Package

Just to give a clear example of what ‘splitting a shipping package’ means, this is how it would look like for the user when shipping multiple packages;

woocommerce-split-shipping-packages-example

Before actually splitting a order in multiple packages, you should first understand what a shipping package is exactly. Obviously a shipping package contains a part of the products to ship, but besides that, it also contains information like the cost, applied coupons and the destination address. A shipping package looks a bit like the following:

  • Contents
    • {{ All package contents }}
  • Contents cost
  • Applied Coupons
    • 10_OFF
  • User
    • User ID
  • Destination
    • Country
    • State
    • Postcode
    • City
    • Address
    • Address_2
Update I’ve build a plugin that allows you to split the cart into multiple packages. If you’re not comfortable with the code snippets below you may want to checkout the WooCommerce Advanced Shipping Packages plugin.

Splitting Shipping Package on Shipping Class

The follow code snippet will split the shipping package based on the shipping class. Each product that has a shipping class A will be split into a separate package from the other products.

Splitting Shipping Package on Product ID

If you want to split the shipping package based on product IDs you can replace the top part of the code with the following (partial code);

This will setup a separte shipping package for the products with the ID 188, 189 and 190.

Splitting Shipping Package on Category

The following code is similar to the (partial) code above. Use it by copying into the full code as seen as the first code snippet in this post.

Changing the shipping package name

When you’ve implemented the code above, the shippng should look something like this;

woocommerce-split-shipping-packages-example

 

As you can see, there are two shipping packages, each where the user can select a shipping method. One thing that you will see is that the shipping packages are called Shipping #x. If you want to change this, you’re in bad luck, currently it is not possible to change that package name.

I made a Pul Request to WooCommerce in order to allow the re-naming of the shipping package name, so you can call it what you want from within the shipping package array (as you saw in the first code snippet). When this Pull Request is accepted and it is in WooCommerce Core, I will update this post to include the new feature.

Setting Up Shipping Based on Shipping Package

Not all shipping plugins support shipping packages, so make sure you test everything extensively so your customers will pay the right amount on shipping cost.

My own WooCommerce Advanced Shipping plugin supports shipping packages.

  • Jeroen Sormani

    I'm a professional WordPress plugin developer on a mission to create the best plugins for my clients. I'm specialised in developing general WordPress, WooCommerce and Easy Digital Downloads plugins.

    Interested in talking about a WordPress project? Get in touch!

    Follow me on Twitter
  • 46 thoughts on “Splitting Shipping Packages in WooCommerce

    Matteo Raggi March 27, 2016 at 10:10 am

    Nice! And what about a sampel code about the vendors? For example I would like to see a sampel code for the WC MARKETPLACE multivendors plugin: https://wordpress.org/support/plugin/dc-woocommerce-multi-vendor

    jeroen March 27, 2016 at 6:38 pm

    HI Matteo,

    Unfortunately I don’t have a code snippet available for that..

    If you end up creating one, feel free to include it here 🙂

    Jeroen

    A Hayes March 31, 2016 at 2:34 pm

    Where should this code be inserted? Does it go in the woocommerce-advanced-shipping/woocommerce-advanced-shipping.php? And if so, where should it be added?

    jeroen April 3, 2016 at 12:35 am

    Hi Angela,

    I wrote this blog post about code snippets that I can recommend 😉
    https://shopplugins.com/how-to-add-a-code-snippet-to-your-site/

    Cheers,
    Jeroen

    Megan Duckett April 2, 2016 at 12:14 am

    My site developer has been working with Jeroen to improve the shipping scenarios on our modestly sized apparel sales site. The challenges we had related to splitting shipping classes and assigning different rates and rules to products that are drop shipping internationally versus locally “all within a single order”. Jeroen has been so incredibly responsive and helpful! Already we have implemented the site improvements and could not be more pleased. Both my programmer and I highly recommend Jeroen and want to share our positive experience with him. Thank You. Megan Duckett. Rock’n Roll Outfitters.

    Mohamed June 21, 2016 at 3:39 pm

    Hi, Thank you for your Help

    How can i add a speciffic Price for a specific Shipping package

    Fanie July 27, 2016 at 3:53 am

    Very cool! Thank you so much for your advice! I am now going to subscribe 🙂

    James September 2, 2016 at 7:05 am

    Hi Jeroen,

    This is awesome and I’ve used it to save money we were losing on shipping so thank you. However, there’s something I’m trying to debug. When AJAX is enabled on the checkout page. This function stalls the AJAX loading and it never completes. Any idea why that is? It seems that the data isn’t being passed over from cart to checkout. This has proven nearly impossible to debug. Please help! Thanks!

    Jeroen September 2, 2016 at 9:26 am

    Hi James,

    Just tested the code for splitting on shipping class, and everything seems to work for me. It could be you have a plugin running that causes an error behind the scenes, preventing from data being send back and the loading to be stopped / table to be refreshed.

    Should be able to find a error in the error log in such case.

    Cheers,
    Jeroen

    ms September 25, 2016 at 1:51 pm

    Hi,

    Do you have news from woocommerce regarding to your pul request for shipping package name?

    Is there a way to follow your request? link?

    Thanks!

    Jeroen September 25, 2016 at 9:24 pm

    Hi Marius,

    I don’t have a direct link right now, but you can search by author on GitHub.
    The package name can be filtered right now.

    Cheers,
    Jeroen

    Ian September 30, 2016 at 4:07 pm

    Hi Jeroen,
    Can you please help me to modify your code to handle 3 or more packages based on splitting out more than one shipping class?

    Tom October 19, 2016 at 8:51 am

    Hi,

    I used the shipping on class for my online shop and it works awesome. The shipping costs of all products which belong to this one class are seperated from the rest of the order. 🙂

    Now I need the shop to deal with another class the same way. The shipping costs of those class shouldn´t be added to the costs of the first class I already splitted. So, there has to be a third field of splitted shipping costs.
    I tried a few things but the shop always adds the shipping costs to the costs of the first class.
    Is there a way to realise this additonal seperation somehow?

    Jeroen October 19, 2016 at 2:37 pm

    Hi Tom,

    You can copy a part of the code and create a third shipping package.

    If you’re not that familiar with code, a new extension has actually been released yesterday that would also be able to help you with that 😉 https://woocommerce.com/products/woocommerce-advanced-shipping-packages/

    Feel free to reach out through the contact form if you need some further advise.

    Cheers,
    Jeroen

    shawn November 28, 2016 at 10:53 pm

    Hi,
    This is exactly what I’m looking for I believe. Does your advanced plugin do the same without code? Does it support the woocommerce ups and usps shipping cost plugin? Thank you for your time.

    Jeroen November 28, 2016 at 11:02 pm

    Hi Shawn,

    Yes the Advanced Shipping Packages plugin does the same without code.
    I haven’t tested it with any shipping carrier plugin, but I do think it should work out of the box.

    Cheers,
    Jeroen

    shawn November 29, 2016 at 6:39 pm

    Can I display certain shipping options based on class. example, I only want to show flat rate shipping options for certain classes and and then for other classes i want to be able to show ups and usps. also what if i run a free shipping promotion? can i have a coupon apply to certain or all classes.

    I’m currently using the packages grouping plugin and It is exactly what I need except the shipping isn’t transfering correctly to paypal so I hope I can do the same with your plugin.

    Thank you for actually responding to support request. I think your the only one out there.

    Jeroen November 29, 2016 at 7:21 pm

    Hi Shawn,

    Yes you can setup the shipping packages / options based on the shipping class.
    A free shipping coupon should also be possible, though I also haven’t tested that scenario.

    I’m not familiar with the packages grouping plugin, but WooCommerce sends over the data to PP so that is not interfered by the plugin itself.

    PS. note that I’m not responsible for the support of the Advanced Shipping Packages plugin, this is done by WooCommerce.com, so if you want to be sure / guarantees about this you’d need to contact them as I can’t speak on their behalf 😉

    Cheers,
    Jeroen

    shawn November 29, 2016 at 7:34 pm

    Thank you,
    Do you have a development company that offers custom work incase I need anything in the future?

    shawn November 29, 2016 at 9:10 pm

    How does this integrate with shipping zones? Do you still use zones or does this override all that? Thank you, I just want to make sure this does what I hope.

    Jeroen November 30, 2016 at 8:57 am

    Yes, you can contact me here: http://jeroensormani.com/hire-me

    The plugin doesn’t create any shipping rates so it is not related to shipping zones in any way like that. Please contact me through the contact form if you have any further questions.

    Cheers,
    Jeroen

    Jared Wilcox December 17, 2016 at 12:25 am

    Jeroen,

    I am trying to use your code to apply free shipping to a product with a specific shipping class. The only problem is that it is adding the free shipping method to all packages in the cart. Even the package that does not have the free shipping class.

    The goal is to have one package with free shipping available, and the other package with only the paid options available and no free shipping option.

    Is this possible?

    Thank you,
    Jared

    Jeroen December 17, 2016 at 10:09 pm

    Hi Jared,

    It might be that the free shipping option you’re using isn’t compatible with shipping packages.
    My Advanced Shipping plugin definitely is compatible with shipping packages and would allow you to set that up.

    Cheers,
    Jeroen

    Angelo December 23, 2016 at 6:45 am

    Hi Jeroen,
    it is incredible how you can manage WP problemas and help people to clean up their problems with it! Thank you!

    I have a question about a problem that, even looking for a lot of time in google i cannot find a valid solution:

    i have a woocommerce shop where i have products with shipping cost included for national shipping (A) and products where the product weight adds to calculate the total shipping weight (B).

    Problems comes when, in the same order, i have both type of products….. i dont want woocommerce to calculate the shipping including the A product weight…

    You would say: so put the A product weigth to 0… The answer would be: I cannot, because, for international shipping i need to know the product weight…

    So, which solution you would take? I thought to find a way to exclude product A weight from the shipping calculation for national shipping and leave as it is in the others shipping… but i don’t know how!

    Well, i hope i describe in a comprehensive way the problem…thank you very much!

    Jeroen December 23, 2016 at 9:45 am

    Hi Angelo,

    One (important) Q came from your message: how do you want to calculate the cost?

    If you want to use a shipping carrier / live quotes it is a different story then when using your own shipping rates.

    If you setup your own rates, you can use my Advanced Shipping plugin to setup cost based on the weight of a product or shipping class (or category). http://codecanyon.net/item/woocommerce-advanced-shipping/8634573

    In case its live quotes, what you could try is setting up two packages as per this post, and using my Advanced Shipping plugin again to setup a free shipping rate (and hide others) for the A package.

    Hope that helps 😉

    Cheers,
    Jeroen

    Sam January 17, 2017 at 7:02 pm

    Hi Jeroen,

    It works only for cart and checkout, can we call it on thank you page or order detail page?
    Thank you page or order detail page still display total shipping cost.
    After splitting the package, is it possible to create separate order for each package?

    Thanks

    VK January 24, 2017 at 10:37 pm

    Hi Jeroen,

    This snippet seems like exactly what I am looking for in my store. I have a quick question though, I am currently using Advanced Flat Rate Shipping plugin for my store – primarily because it lets me create customized flat rate shipping options with descriptions during checkout. The shipping methods I create in this plugin override the flat rate shipping classes that are associated with the product. My question is will your snippet work with this plugin?

    Thanks,

    Vik

    Jeroen January 25, 2017 at 9:58 am

    Hi Vik,

    The code will work regardless of that plugin, the question is whether that plugin supports shipping packages, which I cannot answer for you since I’m not familiar with that plugin.

    I can say that my own shipping plugin handles Shipping packages: Advanced Shipping for WooCommerce

    Cheers,
    Jeroen

    Sam February 2, 2017 at 9:22 pm

    Hi Jeroen,

    I am trying the display shipping package cost for each item on thank you page and order details page, this snippet is splitting the package on cart but what about thank you page or order details page? Any idea?

    Thanks,
    Sam

    Jeroen February 2, 2017 at 10:29 pm

    Hi Sam,

    If the package is split properly, then WC core should also show the separate rates for each package in the emails, detail pages and everywhere else the order totals table is displayed.

    If its not it could be the order wasn’t split,, or maybe outdated theme files?

    Cheers,
    Jeroen

    Sam February 3, 2017 at 2:52 pm

    Jeroen, i am working with latest version of [Storefront theme, WooCommerce & WordPress].
    I am testing with Flat Rate 10*[qty].
    As you said that package may not be splitting properly so i tried to simplify the code, now i putting following code in function.php but still it is splitting property only on Cart & Checkout page and getting total shipping cost on thank-you page and everywhere else:

    add_filter( 'woocommerce_cart_shipping_packages', 'bulky_woocommerce_cart_shipping_packages' );
    function bulky_woocommerce_cart_shipping_packages( $packages ) {
        // Reset the packages
        $packages = array();
        foreach ( WC()->cart->get_cart() as $item ) {
            if ( $item['data']->needs_shipping() ) {
            $packages[] = array(
                'contents' => array($item),
                'contents_cost' => array_sum( wp_list_pluck( array($item), 'line_total' ) ),
                'applied_coupons' => WC()->cart->applied_coupons,
                'destination' => array(
                    'country' => WC()->customer->get_shipping_country(),
                    'state' => WC()->customer->get_shipping_state(),
                    'postcode' => WC()->customer->get_shipping_postcode(),
                    'city' => WC()->customer->get_shipping_city(),
                    'address' => WC()->customer->get_shipping_address(),
                    'address_2' => WC()->customer->get_shipping_address_2()
                )
            );
            }
        }
        return $packages;
    }
    Jeroen February 4, 2017 at 2:41 pm

    Hi Sam,

    Your code is fine;
    https://cl.ly/2d3x1r3y130L
    https://cl.ly/0p1t2r283l1Z

    On the checkout page it does show the accumulated shipping cost, but it still shows which rates were selected there. Not sure if you meant that specifically. If you want to change that you’d need to modify your theme files to show that.

    Cheers,
    Jeroen

    Sam February 5, 2017 at 2:28 am

    Thanks Jeroen, i was not sure, why properly separated packages still show total in thank you page or order detail page.
    Rather than modifying the theme file i am trying to get separated values of shipping with this “add_filter ‘woocommerce_get_order_item_totals'”
    but no luck yet.

    andry tan February 4, 2017 at 5:47 am

    Hi… Jeroen….

    thank you for the code.
    Is there any way to split shopping cart base on the package?

    if we have 3 different package then we can have 3 different shopping cart…

    thank you for your answer….

    Cheers,

    Andry

    Jeroen February 4, 2017 at 2:43 pm

    Hi Andry,

    What do you mean with you have 3 different packages? It doesn’t sound like you mean that these are the split packages I’m talking about.
    Please clarify your comment as it doesn’t really make sense to have ‘3 different shopping cart’.

    Cheers,
    Jeroen

    Greg February 6, 2017 at 3:51 am

    Hi Jeroen,

    I just purchased the Advanced Shipping plugin and am having issues with how I’m trying to set things up. I have 3 different shipping package types setup so if the cart includes a product from each shipping type: the first package receives free shipping if the product has the specific shipping class assigned to it; the second package displays a message to the customer saying that they must call for special shipping (for large bulky shipments); and the last package receives UPS shipping rates. Can your plugin help get this setup?

    Thanks,

    Greg

    Jeroen February 6, 2017 at 9:18 am

    Hi Greg,

    The Advanced Shipping plugin would be useful for the first package and possibly the second.
    For the UPS rates you’d want to use a UPS plugin.

    To split the cart you can either use a code snippet as shown above, or use my other plugin Advanced Shipping Packages to split the cart, and exclude the UPS rate from the 1st/2nd package for example.
    https://woocommerce.com/products/woocommerce-advanced-shipping-packages/

    PS. if you have any further support questions, please reach out through the appropriate form 😉

    Thanks,
    Jeroen

    Rajat February 7, 2017 at 5:09 am

    Hi Jeroen,

    I want to split the package on specific condition like if Product A exceeds 64” – split up the delivery into two equal sized shipments.

    Does your plugin allow this shipment?

    Thanks

    Jeroen February 7, 2017 at 9:26 am

    Hi Rajat,

    The Shipping Packages plugin doesn’t have a condition for a specific product quantity/subtotal, but if wanted this can be added through a custom code snippet though.

    Splitting it up automatically in two equal sized shipments is not possible though (by default anyways). Could you maybe elaborate on how you’d like them to be split up (based on weight, $$, size)? This would help me with determining possible future features.

    Thank you,
    Jeroen

    Erick February 9, 2017 at 4:09 am

    Hello Jeroen,

    Could you tell me if there is already a way to change the shipping package name for each different vendor?

    Jeroen February 9, 2017 at 9:13 am

    Hi Erick,

    There is a way to modify the shipping package name, there’s a hook available for that since, I believe, WC 2.5 (IIRC).

    I proposed that change to WC core for my Advanced Shipping Package plugin which has the feature build in.

    Cheers,
    Jeroen

    Oliver February 22, 2017 at 1:02 pm

    Hi Jeroen,

    I’m looking to implement your code on my website. We currently store small items on-site and any larger items we drop-ship direct from the supplier’s warehouse. We’d like to offer express & standard shipping methods for on-site products/classes and a ship by courier method only for the large dropship products/classes.

    Is there a way to ‘group’ shipping classes together into packages, such as ‘small-2kg & medium-1kg’ (on-site) and ‘extra-large-15kg & large-10kg’ (drop-ship), to allow customers to pay/checkout for each package seperately?

    Thanks

    Jeroen February 23, 2017 at 8:43 am

    Hi Oliver,

    Let me first note that split shipping packages cause shipping to be calculated separately per package, but it doesn’t allow customers to ‘pay/checkout for each package’.

    Its relatively easy to do a conditional check for one of two shipping classes and pack them into one package.

    If you’re not comfortable with coding that I’d recommend to take a look my plugin that would also fit your needs: https://woocommerce.com/products/woocommerce-advanced-shipping-packages/

    Cheers,
    Jeroen

    Oliver February 23, 2017 at 10:14 am

    Thanks for the prompt reply. That’s great, separate calculation is what I actually meant/wanted and I appreciate you clarifying that. I’ll have to have a look at your plugin as my coding is very hit and miss!

    Thanks again,
    Oliver

    Francine February 23, 2017 at 4:29 pm

    Could you tell me whether your plugin would be appropriate for me?

    I am currently using Dokan plugin based on WooCommerc and I would like to see the shipping cost split between each vendor that the customer purchases from.

    I would like the capability that if the customer reaches a particular dollar value on their order they may be entitled to free shipping and this is mentioned to them through the cart experience.

    So it could end up being that they order from 3 vendors – vendor a $20 ordered, pay $10 shipping, vendor b – $70 orders pay $0 shipping, vendor c – orders $50, but if they spend up to $60 they get free shipping so in total the shipping only reaches $10.

    Can you please tell me if your plugin will do this?

    Jeroen February 24, 2017 at 8:49 am

    Hi Francine,

    The Advanced Shipping Packages would only be able to split the cart into separate packages. If you can distinguish the vendors by something like shipping class or category you’d be able to split those based on those identifiers.

    Then for shipping,, do you mean that they get free shipping per vendor if the subtotal per that vendor is above $60? You might be able to setup something like that using my Advanced Shipping plugin, but that also depends on how your shipping cost is setup.

    Re it being mentioned in the cart, neither of the plugins above adds any type of notification (outside the scope of the plugin(s)). I do have another that has such type of functionality, but that doesn’t work out of the box with different amounts that are in the cart per vendor. https://shopplugins.com/plugins/woocommerce-advanced-messages/
    It would require some additional work to get that working the way I imagine you want it to.

    Does that help?

    Cheers,
    Jeroen

    Leave a Reply