[FIX] mrp: extra move line in sub-location

- Define a Component A tracked by lot.
- Define a Final Product B tracked by lot.
- Create a BOM, e.g. 5 units of A to produce B.
- Get some quantity of A in a sub-location, e.g. 'WH/Stock/Shelf 1'.
- Create a MO for 1 unit of B.
- When clicking on 'Produce', record 6 units consumed instead of 5.
- Post the inventory

5 units of A is removed from 'WH/Stock/Shelf 1' and 1 unit of A is
removed from 'WH/Stock'. The latter might create a negative quant if no
stock is available in 'WH/Stock'.

When the extra move line is created, it is created using the data of the
stock move (in `_generate_consumed_move_line`). When posting the
inventory, the quants selection is made strictly in the location set (in
`_update_available_quantity`), which might cause the mentioned negative
quant.

The solution is to select a sub-location where the product can be found.
This gives a higher chance to avoid negative quants afterwards. Note
that if we wanted to avoid negative quants, we could make a reservation
process on the move, and potentially create several stock move lines.
This is beyond the scope of the integration of MRP with sub-locations.

opw-803969
This commit is contained in:
Nicolas Martinelli
2018-01-09 08:59:44 +01:00
committed by Nicolas Martinelli
parent dc61861f90
commit a650f2359b
+15 -1
View File
@@ -212,10 +212,24 @@ class StockMove(models.Model):
ml.with_context(bypass_reservation_update=True).write({'product_uom_qty': new_qty_reserved, 'qty_done': 0})
if float_compare(qty_to_add, 0, precision_rounding=self.product_uom.rounding) > 0:
# Search for a sub-location where the product is available. This might not be perfectly
# correct if the quantity available is spread in several sub-locations, but at least
# we should be closer to the reality. Anyway, no reservation is made, so it is still
# possible to change it afterwards.
quants = self.env['stock.quant']._gather(self.product_id, self.location_id, lot_id=lot, strict=False)
available_quantity = self.product_id.uom_id._compute_quantity(
self.env['stock.quant']._get_available_quantity(
self.product_id, self.location_id, lot_id=lot, strict=False
), self.product_uom
)
location_id = False
if float_compare(qty_to_add, available_quantity, precision_rounding=self.product_uom.rounding) < 0:
location_id = quants.filtered(lambda r: r.quantity > 0)[-1:].location_id
vals = {
'move_id': self.id,
'product_id': self.product_id.id,
'location_id': self.location_id.id,
'location_id': location_id.id if location_id else self.location_id.id,
'location_dest_id': self.location_dest_id.id,
'product_uom_qty': 0,
'product_uom_id': self.product_uom.id,