Setting Up Role-Based Shipping Methods in WooCommerce
In this guide, I will show you how you can enable or disable specific shipping methods depending on a user role in your WordPress site (I mean, WooCommerce store).
But don’t all the customers in WooCommerce have a dedicated role β “Customer”? Well, while it is true, it is not a requirement; customers still can have other WordPress roles, even multiple roles, along with the “Customer” role.
A simple example: let’s say you have a custom role in your store, “Premium customer” or something like that, and your goal is to grant free shipping to all your premium customers.
We will take a look at two approaches β using a plugin and a programmatic approach.
Sounds good? Now, let’s dive into it.
Configuring Role-Based Shipping Using a Plugin
We will use Simple Conditional Shipping and Payments in this part of the tutorial.
I’d recommend considering the plugin approach:
- It is super-simple and feels like the default WooCommerce functionality,
- You can do much more than role-based shipping; for example, you can do it for payment methods as well, or configure product-based shipping, and much more.
- At the moment, when you have a lot of code snippets in your WordPress website, it could become messy and cause issues, but the plugin is tested and supported.
Now, straight to the configuration.
In WooCommerce settings, open the “Conditions” tab, then the “Shipping conditions” section. Then, you can add as many conditions as you want with the “Add shipping condition” button.
For example, to achieve what I mentioned before (free shipping for the “Premium customers” role), we need the following configuration:

As simple as that π
What is also important to remember here is that WooCommerce allows you to set up free shipping methods individually for each shipping zone. The plugin has it covered as well.

Setting Up Role-Based Shipping Programmatically
The programmatic approach is also possible, if you know what you’re doing, of course. Let me guide you through it step by step.
Creating a “Premium customer” user role
Probably, the whole role-management process is already configured in your WooCommerce store, and you do not need these clarifications; however, you can create a custom role in WordPress/WooCommerce easily with the piece of code below:
add_role(
'premium_customer',
'Premium customer',
array(
'read',
)
);The only thing you need to keep in mind is that you do not need to put this code into the functions.php file by all means; you just need to run it once.
Assigning our custom user role to a customer
This part actually gives us a lot of room for different scenarios.
For example:
- You can use some kind of a membership plugin to set a role for your WooCommerce customers depending on certain conditions.
- Or maybe you have a custom-coded solution, for example, when you assign a role to a customer after purchasing a specific product in your store.
In other words, this part of the process is fully up to you π
Enable shipping methods based on a role
Technically, we need to do the opposite. I mean, let’s say the free shipping methods are enabled by default for everyone, and what we need to do in the code is leave it that way only if a customer is logged in and has a specific role.
The hook we will be using isΒ woocommerce_package_rates (it will work great for both the block and classic WooCommerce checkout).
add_filter( 'woocommerce_package_rates', 'rudr_role_based_shipping', 25, 2 );
function rudr_role_based_shipping( $rates, $package ) {
// we do nothing if user role is "Premium customer"
// free shipping methods remain active
if( wc_current_user_has_role( 'premium_customer' ) ) {
return $rates;
}
foreach( $rates as $rate_id => $rate ) {
if( str_starts_with( $rate_id, 'free_shipping' ) ) {
unset( $rates[ $rate_id ] );
}
}
return $rates;
}If you don’t know where to use this code snippet, you can feel free to check this guide.
The condition str_starts_with( $rate_id, 'free_shipping' ) covers all free shipping methods from all shipping zones at the same time.
However, it is also possible to check some specific shipping methods by their IDs, for example, this way:
if( 'free_shipping:5' === $rate_id ) {If you have any more questions, feel free to ask in the comments below.
Misha Rudrastyh
Hey guys and welcome to my website. For more than 15 years I've been doing my best to share with you some superb WordPress guides and tips for free.
Need some developer help? Contact me