[IMP] mrp_multi_level: Supply method computation for MRP Parameters

For each MRP Parameter, we will calculate its supply method based on the procurement rules path. We will go back in the rules until we find that the action is "buy" or "manufacture", or until the action is "Pull From" or "Pull & Push" and the supply method is "Take from Stock".

This means we will show what the latest rule is if we were to do a procurement. Although it would be possible that the final action does not end up being executed if stock already exists in one of the intermediate locations.
This commit is contained in:
BernatPForgeFlow
2023-02-08 16:37:41 +01:00
parent aa488e4b97
commit f5352325a2
4 changed files with 66 additions and 6 deletions

View File

@@ -36,6 +36,14 @@
eval="[(6, 0, [ref('mrp.route_warehouse0_manufacture')])]"
/>
</record>
<record id="product_product_fp_4" model="product.product">
<field name="name">FP-4</field>
<field name="categ_id" ref="product_category_mrp" />
<field name="type">product</field>
<field name="uom_id" ref="uom.product_uom_unit" />
<field name="uom_po_id" ref="uom.product_uom_unit" />
<field name="produce_delay">2</field>
</record>
<!-- Customizable Desk -->
<record id="product.product_product_4_product_template" model="product.template">

View File

@@ -184,14 +184,30 @@ class ProductMRPArea(models.Model):
"company_id": rec.mrp_area_id.company_id,
}
rule = group_obj._get_rule(rec.product_id, proc_loc, values)
if (
rule.action == "manufacture"
if not rule:
rec.supply_method = "none"
continue
# Keep getting the rule for the product and the source location until the
# action is "buy" or "manufacture". Or until the action is "Pull From" or
# "Pull & Push" and the supply method is "Take from Stock".
while rule.action not in ("buy", "manufacture") and rule.procure_method in (
"make_to_order",
"mts_else_mto",
):
new_rule = group_obj._get_rule(
rec.product_id, rule.location_src_id, values
)
if not new_rule:
break
rule = new_rule
# Determine the supply method based on the final rule.
rec.supply_method = (
"phantom"
if rule.action == "manufacture"
and rec.product_id.product_tmpl_id.bom_ids
and rec.product_id.product_tmpl_id.bom_ids[0].type == "phantom"
):
rec.supply_method = "phantom"
else:
rec.supply_method = rule.action if rule else "none"
else rule.action
)
@api.depends(
"mrp_area_id", "supply_method", "product_id.route_ids", "product_id.seller_ids"

View File

@@ -29,6 +29,7 @@ class TestMrpMultiLevelCommon(SavepointCase):
cls.fp_1 = cls.env.ref("mrp_multi_level.product_product_fp_1")
cls.fp_2 = cls.env.ref("mrp_multi_level.product_product_fp_2")
cls.fp_3 = cls.env.ref("mrp_multi_level.product_product_fp_3")
cls.fp_4 = cls.env.ref("mrp_multi_level.product_product_fp_4")
cls.sf_1 = cls.env.ref("mrp_multi_level.product_product_sf_1")
cls.sf_2 = cls.env.ref("mrp_multi_level.product_product_sf_2")
cls.sf_3 = cls.env.ref("mrp_multi_level.product_product_sf_3")
@@ -219,6 +220,22 @@ class TestMrpMultiLevelCommon(SavepointCase):
cls.product_mrp_area_obj.create(
{"product_id": cls.prod_uom_test.id, "mrp_area_id": cls.mrp_area.id}
)
# Product MRP Parameter to test supply method computation
cls.env.ref("stock.route_warehouse0_mto").active = True
cls.env["stock.rule"].create(
{
"name": "WH2: Main Area → Secondary Area (MTO)",
"action": "pull",
"picking_type_id": cls.env.ref("stock.picking_type_in").id,
"location_src_id": cls.env.ref("stock.stock_location_stock").id,
"location_id": cls.sec_loc.id,
"route_id": cls.env.ref("stock.route_warehouse0_mto").id,
"procure_method": "mts_else_mto",
}
)
cls.product_mrp_area_obj.create(
{"product_id": cls.fp_4.id, "mrp_area_id": cls.secondary_area.id}
)
# Create pickings for Scenario 1:
dt_base = cls.calendar.plan_days(3 + 1, datetime.today())

View File

@@ -428,3 +428,22 @@ class TestMrpMultiLevel(TestMrpMultiLevelCommon):
[("product_mrp_area_id.product_id", "=", self.pp_4.id)]
)
self.assertEqual(len(pp_4_planned_orders), 1)
def test_17_supply_method(self):
"""Test supply method computation."""
self.fp_4.route_ids = [(5, 0, 0)]
product_mrp_area = self.product_mrp_area_obj.search(
[("product_id", "=", self.fp_4.id)]
)
self.assertEqual(product_mrp_area.supply_method, "none")
self.fp_4.route_ids = [(4, self.env.ref("stock.route_warehouse0_mto").id)]
product_mrp_area._compute_supply_method()
self.assertEqual(product_mrp_area.supply_method, "pull")
self.fp_4.route_ids = [
(4, self.env.ref("purchase_stock.route_warehouse0_buy").id)
]
product_mrp_area._compute_supply_method()
self.assertEqual(product_mrp_area.supply_method, "buy")
self.fp_4.route_ids = [(4, self.env.ref("mrp.route_warehouse0_manufacture").id)]
product_mrp_area._compute_supply_method()
self.assertEqual(product_mrp_area.supply_method, "manufacture")