Hello, We have some questions what the correct/easiet way of handling inventory is in the new system.. Should we do the InventoryRequest manually and also updating the inventory manually or should this be done some other way...
let say we have one item with 1 in stock and 10 in backorder we buy 2 of these items.. one should be shipped now and the other later when in stock.. so what would the easiest happy flow be for making this happend :)?
when we do this now we can buy these 2 items and create the purchase order..
The inventory will be instock 1 and backorder 10 for this items (not changed)The order will be "In Progress" stateAnd shipping status "awaiting inventory" If we manually in "commerce manager" change the status to "On Hold" and then back things happens:-The inventory will be instock 0 and backorder 9 for this items-shipping status "Inventory Assigned" (one is still in backorder)
We want this to be set already when purchase order is created but i guess is some extra steps to do that.
When we add up inventory manually to be instock 2 and backorder 9, nothing happends.. and maybe it should not. .so should all this be handled manually from code? (order status, shipping status, invetory quantitys.. ) im a bit confused abut the right way doing this and dont want to start doing things wrong way. .
Thanks in advance for any directions.. :)
I might not fully understand the whole picture (busy day), but I think that would require some custom changes in your "workflow" - processing code. You would have to automatically split shipments if one or more items shared across InStock and BackOrder (things that can be shipped right away into a shipment, and other ones into another shipment). One place to do that is before calling UpdateInventoryOrRemoveLineItems
thanks for response..Ok, and how about the Inventory handling? In your book you are describing the manual process of how its done.. So if we want items to be substracted from inventory after placing a order we have to handle it manuall from code (InventoryService.Request.... ) ? But feels lite its lot of code to write to handle a quite simple process, is there a faster way to do it? Because its not handled right now even if we put order status to completed
Also other question, when doing a AdjustInventoryOrRemoveLineItems just before creating order everything will be adjusted in the inventory..
but how can i find items that are "BackoOrdered" in my orders?Do i need to do something or is there a easy way to find them?
Out of my head, at that point couldn't you query the inventory and decide if you should split?
ok, so what you saying is that we can´t see on order is some items are backordered..
I would like the customer to be able to fulfill the order even with item that are backorderes but i want them ontl shipped when all items are in stock..
So i guess when refilling stock we should look at the inventory to see if we have anything on "BackorderRequestedQuantity"
and then add to our orders that are "On Hold" and fill them up before we fill the inventory.
then step 2 in our case would be to split into severals shipments..
would this be a good way to go?
ok, still not clear how this should be handled..
i see 2 ways..
one way manually make "RequestInventory"
the other call "AdjustInventoryOrRemoveLineItems"
im really confused how to use it correct the new "way" without workflows.
the first way requires us to store "OperationKeys" on shipment i guess?
Is there any documentaiton on how it should be done somewhere?
i have only found the 2 links above
i would use AdjustInventoryOrRemoveLineItems this will handle all cases depending the status of the order. The reason the framework does not work as you would like is becasue not all customers would want to create a new shipment for the backorder as they might want to wait to ship all together. When calling AdjustInventoryOrRemoveLineItems you only get back AdjustedQuantityByBackorderQuantity when there is not enough to fullfill the order. If you want to check if an item was placed on back order but did not receive a valiadation issue you can use the method below.
public Dictionary<ILineItem, Dictionary<InventoryRequestType, InventoryChange>> GetInventoryStatus(IOrderGroup order)
var status = new Dictionary<ILineItem, Dictionary<InventoryRequestType, InventoryChange>>();
var serializer = ServiceLocator.Current.GetInstance<OperationKeySerializer>();
foreach (var shipment in order.GetFirstForm().Shipments)
if (!(shipment is IShipmentInventory shipmentInventory))
foreach (var lineItem in shipment.LineItems)
var keys = shipmentInventory.GetOperationKeys(lineItem).ToList();
foreach (var key in keys)
if (!serializer.TryDeserialize(key, out var inventoryRequestType, out var inventoryChange))
status.Add(lineItem, new Dictionary<InventoryRequestType, InventoryChange>());
Ok, so lets take a happy flow fo rexample.. Without backorder to make things really easy.. Item A -> 10 in stockcustomer adds 1 to cart and complete the checkout.. just before we convert the cart to purchase order we do a "AdjustInventoryOrRemoveLineItems" with cart now we have inventoryrecord that looks like this:
PurchaseAvailableQuantity: 9 PurchaseRequestedQuantity: 1
We mark the order as completed and also mark the onyl shipment as shipped and save order.
now we call "AdjustInventoryOrRemoveLineItems" again but on order this time (cart is gone now)
nothing happens.. we still have
PurchaseAvailableQuantity: 9PurchaseRequestedQuantity: 1
Shouldnt this look like:PurchaseAvailableQuantity: 9PurchaseRequestedQuantity: 0
so to complete this i only found that we should make a "RequestInventory"https://world.episerver.com/documentation/developer-guides/commerce/warehouses-and-inventories/Warehouses-and-inventories-examples/
and mark it as Completed.. ? mixing these 2 makes it a but confusing
so "i would use AdjustInventoryOrRemoveLineItems this will handle all cases" does not handle that much or i use it wrong way in the wrong time?
I think this will work as expected if you want to use the api instead of commerce manager to prcoess shipments.
public void CompleteOrder(IOrderGroup cart)
var inventoryProcessor = ServiceLocator.Current.GetInstance<IInventoryProcessor>();
var paymentProcessor = ServiceLocator.Current.GetInstance<IPaymentProcessor>();
var orderGroupCalculator = ServiceLocator.Current.GetInstance<IOrderGroupCalculator>();
var orderRepository = ServiceLocator.Current.GetInstance<IOrderRepository>();
var validationIssues = new Dictionary<ILineItem, List<ValidationIssue>>();
cart.AdjustInventoryOrRemoveLineItems((item, issue) => AddValidationIssues(validationIssues, item, issue), inventoryProcessor);
var orderReference = orderRepository.SaveAsPurchaseOrder(cart);
var purchaseOrder = orderRepository.Load<IPurchaseOrder>(orderReference.OrderGroupId);
purchaseOrder.GetFirstForm().Shipments.First().OrderShipmentStatus = OrderShipmentStatus.Shipped;
purchaseOrder.OrderStatus = OrderStatus.Completed;
validationIssues = new Dictionary<ILineItem, List<ValidationIssue>>();
purchaseOrder.AdjustInventoryOrRemoveLineItems((item, issue) => AddValidationIssues(validationIssues, item, issue), inventoryProcessor);
public static void AddValidationIssues(Dictionary<ILineItem, List<ValidationIssue>> issues, ILineItem lineItem, ValidationIssue issue)
issues.Add(lineItem, new List<ValidationIssue>());