Just a small request really, is it possible to get a
‘shipping by weight’ feature added to the starter kit and to Tea Commerce
itself? As shipping in United Kingdom is done by size and weight so our clients
get unhappy with having to work it out in another way, it would be great if you
could at least provide me with some information about this.
We have no plans on integrating this into the starter kit. We have done it for one of our customers though. What we did was to add some shipping rules to the Umbraco content:
All product will of cause have a weight in kg property. Then this “small” piece of code is used to update the shipping cost every time the order is changed. As you can see it’s a Tea Commerce .NET extension. It’s simpler than it looks.
Mat, I have recently changed my solution for shipping by weight to use different costs dependant on country, I've layed it out as 'Shipping Rules' -> 'Shipping Country' -> 'Shipping Rule'
Shipping by weight feature
Just a small request really, is it possible to get a ‘shipping by weight’ feature added to the starter kit and to Tea Commerce itself? As shipping in United Kingdom is done by size and weight so our clients get unhappy with having to work it out in another way, it would be great if you could at least provide me with some information about this.
Hi Luke,
We have no plans on integrating this into the starter kit. We have done it for one of our customers though. What we did was to add some shipping rules to the Umbraco content:
All product will of cause have a weight in kg property.
Then this “small” piece of code is used to update the shipping cost every time the order is changed. As you can see it’s a Tea Commerce .NET extension. It’s simpler than it looks.
public class TeaCommerceExtension : ITeaCommerceExtension {
#region ITeaCommerceExtension Members
public void Initialize() {
WebshopEvents.OrderLineChanged += WebshopEvents_OrderLineChanged;
WebshopEvents.ShippingMethodChanged += WebshopEvents_ShippingMethodChanged;
WebshopEvents.CurrencyChanged += WebshopEvents_CurrencyChanged;
WebshopEvents.OrderLineRemoved += WebshopEvents_OrderLineRemoved;
}
void WebshopEvents_OrderLineRemoved( Order order, OrderLine orderLine ) {
UpdateOrderShippingCost( order );
}
/// <summary>
/// On currency change
/// </summary>
/// <param name="order"></param>
/// <param name="currency"></param>
void WebshopEvents_CurrencyChanged( Order order, Currency currency ) {
UpdateOrderShippingCost( order );
}
/// <summary>
/// On shipping method change
/// </summary>
/// <param name="order"></param>
/// <param name="shippingMethod"></param>
void WebshopEvents_ShippingMethodChanged( Order order, ShippingMethod shippingMethod ) {
UpdateOrderShippingCost( order );
}
void WebshopEvents_OrderLineChanged( Order order, OrderLine orderLine ) {
UpdateOrderShippingCost( order );
}
#endregion
private void UpdateOrderShippingCost( Order order ) {
XPathNodeIterator allXml = umbraco.library.GetXmlAll();
XPathNavigator shippingRules = allXml.Current.SelectSingleNode( "//ShippingRules" );
decimal defaultWeightInKg = PriceHelper.ParsePrice( shippingRules.SelectSingleNode( "defaultWeight" ).Value );
decimal totalWeightInKg = 0;
foreach ( OrderLine ol in order.OrderLines ) {
OrderLineProperty weightProp = ol.Properties.FirstOrDefault( p => p.Alias == "productWeight" );
if ( weightProp != null && !string.IsNullOrEmpty( weightProp.Value ) )
totalWeightInKg += PriceHelper.ParsePrice( weightProp.Value.ToString() ) * ol.Quantity;
else
totalWeightInKg += defaultWeightInKg * ol.Quantity;
}
XPathExpression weightPathXPath = XPathExpression.Compile( "./WeightRange" );
weightPathXPath.AddSort( "upToWeight", XmlSortOrder.Ascending, XmlCaseOrder.None, string.Empty, XmlDataType.Number );
XPathNodeIterator weightRules = shippingRules.Select( weightPathXPath );
decimal shippingPricePerKgWithoutVAT = 0;
while ( weightRules.MoveNext() ) {
if ( PriceHelper.ParsePrice( weightRules.Current.SelectSingleNode( "upToWeight" ).Value ) >= totalWeightInKg ) {
shippingPricePerKgWithoutVAT = PriceHelper.ParsePrice( weightRules.Current.SelectSingleNode( "shippingPrice" + order.Currency.ISOCode ).Value );
break;
}
};
decimal totalShippingPriceWithoutVAT = shippingPricePerKgWithoutVAT * totalWeightInKg;
OrderProperty shippingPriceOP = order.Properties.FirstOrDefault( p => p.Alias == "shippingPriceWithoutVAT" + order.Currency.ISOCode );
OrderProperty totalWeightInKgProp = order.Properties.FirstOrDefault( p => p.Alias == "totalWeightInKg" );
if ( shippingPriceOP == null ) {
shippingPriceOP = new OrderProperty( "shippingPriceWithoutVAT" + order.Currency.ISOCode, totalShippingPriceWithoutVAT.ToString() );
order.AddProperty( shippingPriceOP );
totalWeightInKgProp = new OrderProperty( "totalWeightInKg", totalWeightInKg.ToString() );
order.AddProperty( totalWeightInKgProp );
} else {
if ( shippingPriceOP.Value.ParseToDecimal() != totalShippingPriceWithoutVAT )
shippingPriceOP.Value = totalShippingPriceWithoutVAT.ToString();
if ( totalWeightInKgProp.Value.ParseToDecimal() != totalWeightInKg )
totalWeightInKgProp.Value = totalWeightInKg.ToString();
}
if ( order.ShippingMethod.Id == 2 && order.ShippingFeeWithoutVAT != totalShippingPriceWithoutVAT )
order.ShippingFeeWithoutVAT = totalShippingPriceWithoutVAT;
order.Save();
}
}
/Rune
Thanks for the info, great to get the snippet too, really helpful!
Thanks for this info.
I have a requirement to calculate the shipping costs depending on the destination country and the value of the total order.
So shipping to the UK is $20 for orders up to $100, $15 for orders up to $150 and $10 for orders over $150.
I imagine I could use the same approach.
Hi Matt,
Yes you could do something like that in a similar fashion. All up to your imagination and ingenuity and the usecase.
/Rune
Can we see the Content structure and Doc Types that you have created to store the Shipping Rules?
Thanks
Mat, I have recently changed my solution for shipping by weight to use different costs dependant on country, I've layed it out as 'Shipping Rules' -> 'Shipping Country' -> 'Shipping Rule'
FYI, in TC v2 you have to use the above code in the new Shipping Calculator feature.
is working on a reply...