fix: batch no not copied while making Material Consumption entry (#40290)

This commit is contained in:
rohitwaghchaure
2024-03-06 12:50:26 +05:30
committed by GitHub
parent 031465f5ec
commit 1eaa386657
2 changed files with 107 additions and 26 deletions

View File

@@ -1383,8 +1383,9 @@ class TestWorkOrder(FrappeTestCase):
# Inward raw materials in Stores warehouse
ste_doc.submit()
ste_doc.reload()
serial_nos_list = sorted(get_serial_nos(ste_doc.items[0].serial_no))
serial_nos_list = sorted(get_serial_nos_from_bundle(ste_doc.items[0].serial_and_batch_bundle))
wo_doc = make_wo_order_test_record(production_item=fg_item, qty=4)
transferred_ste_doc = frappe.get_doc(
@@ -1396,19 +1397,22 @@ class TestWorkOrder(FrappeTestCase):
# First Manufacture stock entry
manufacture_ste_doc1 = frappe.get_doc(make_stock_entry(wo_doc.name, "Manufacture", 1))
manufacture_ste_doc1.submit()
manufacture_ste_doc1.reload()
# Serial nos should be same as transferred Serial nos
self.assertEqual(get_serial_nos(manufacture_ste_doc1.items[0].serial_no), serial_nos_list[0:1])
self.assertEqual(
sorted(get_serial_nos_from_bundle(manufacture_ste_doc1.items[0].serial_and_batch_bundle)),
serial_nos_list[0:1],
)
self.assertEqual(manufacture_ste_doc1.items[0].qty, 1)
manufacture_ste_doc1.submit()
# Second Manufacture stock entry
manufacture_ste_doc2 = frappe.get_doc(make_stock_entry(wo_doc.name, "Manufacture", 2))
manufacture_ste_doc2 = frappe.get_doc(make_stock_entry(wo_doc.name, "Manufacture", 3))
# Serial nos should be same as transferred Serial nos
self.assertEqual(get_serial_nos(manufacture_ste_doc2.items[0].serial_no), serial_nos_list[1:3])
self.assertEqual(manufacture_ste_doc2.items[0].qty, 2)
self.assertEqual(get_serial_nos(manufacture_ste_doc2.items[0].serial_no), serial_nos_list[1:4])
self.assertEqual(manufacture_ste_doc2.items[0].qty, 3)
def test_backflushed_serial_no_batch_raw_materials_based_on_transferred(self):
frappe.db.set_single_value(
@@ -1542,19 +1546,9 @@ class TestWorkOrder(FrappeTestCase):
row.qty -= 2
row.transfer_qty -= 2
if not row.serial_and_batch_bundle:
continue
bundle_id = row.serial_and_batch_bundle
bundle_doc = frappe.get_doc("Serial and Batch Bundle", bundle_id)
if bundle_doc.has_serial_no:
bundle_doc.set("entries", bundle_doc.entries[0:5])
else:
for bundle_row in bundle_doc.entries:
bundle_row.qty += 2
bundle_doc.save()
bundle_doc.load_from_db()
if row.serial_no:
serial_nos = get_serial_nos(row.serial_no)
row.serial_no = "\n".join(serial_nos[:5])
ste_doc.save()
ste_doc.submit()
@@ -1897,6 +1891,71 @@ class TestWorkOrder(FrappeTestCase):
"Manufacturing Settings", {"disable_capacity_planning": 1, "mins_between_operations": 0}
)
def test_partial_material_consumption_with_batch(self):
from erpnext.stock.doctype.stock_entry.test_stock_entry import (
make_stock_entry as make_stock_entry_test_record,
)
frappe.db.set_single_value("Manufacturing Settings", "material_consumption", 1)
frappe.db.set_single_value(
"Manufacturing Settings",
"backflush_raw_materials_based_on",
"Material Transferred for Manufacture",
)
fg_item = make_item(
"Test FG Item For Partial Material Consumption",
{"is_stock_item": 1},
).name
rm_item = make_item(
"Test RM Item For Partial Material Consumption",
{
"is_stock_item": 1,
"has_batch_no": 1,
"create_new_batch": 1,
"batch_number_series": "TST-BATCH-PMCC-.####",
},
).name
make_bom(
item=fg_item,
source_warehouse="Stores - _TC",
raw_materials=[rm_item],
)
make_stock_entry_test_record(
purpose="Material Receipt",
item_code=rm_item,
target="Stores - _TC",
qty=10,
basic_rate=100,
)
wo_order = make_wo_order_test_record(item=fg_item, qty=10)
stock_entry = frappe.get_doc(
make_stock_entry(wo_order.name, "Material Transfer for Manufacture", 10)
)
stock_entry.submit()
stock_entry.reload()
batch_no = get_batch_from_bundle(stock_entry.items[0].serial_and_batch_bundle)
stock_entry = frappe.get_doc(
make_stock_entry(wo_order.name, "Material Consumption for Manufacture", 10)
)
self.assertEqual(stock_entry.items[0].batch_no, batch_no)
self.assertEqual(stock_entry.items[0].use_serial_batch_fields, 1)
frappe.db.set_single_value("Manufacturing Settings", "material_consumption", 0)
frappe.db.set_single_value(
"Manufacturing Settings",
"backflush_raw_materials_based_on",
"BOM",
)
def make_operation(**kwargs):
kwargs = frappe._dict(kwargs)

View File

@@ -2168,23 +2168,42 @@ class StockEntry(StockController):
if not qty:
return
use_serial_batch_fields = frappe.db.get_single_value("Stock Settings", "use_serial_batch_fields")
ste_item_details = {
"from_warehouse": item.warehouse,
"to_warehouse": "",
"qty": qty,
"item_name": item.item_name,
"serial_and_batch_bundle": create_serial_and_batch_bundle(self, row, item, "Outward"),
"serial_and_batch_bundle": create_serial_and_batch_bundle(self, row, item, "Outward")
if not use_serial_batch_fields
else "",
"description": item.description,
"stock_uom": item.stock_uom,
"expense_account": item.expense_account,
"cost_center": item.buying_cost_center,
"original_item": item.original_item,
"serial_no": "\n".join(row.serial_nos)
if row.serial_nos and not row.batches_to_be_consume
else "",
"use_serial_batch_fields": use_serial_batch_fields,
}
if self.is_return:
ste_item_details["to_warehouse"] = item.s_warehouse
self.add_to_stock_entry_detail({item.item_code: ste_item_details})
if use_serial_batch_fields and not row.serial_no and row.batches_to_be_consume:
for batch_no, batch_qty in row.batches_to_be_consume.items():
ste_item_details.update(
{
"batch_no": batch_no,
"qty": batch_qty,
}
)
self.add_to_stock_entry_detail({item.item_code: ste_item_details})
else:
self.add_to_stock_entry_detail({item.item_code: ste_item_details})
@staticmethod
def get_serial_nos_based_on_transferred_batch(batch_no, serial_nos) -> list:
@@ -2335,6 +2354,9 @@ class StockEntry(StockController):
"item_name",
"serial_and_batch_bundle",
"allow_zero_valuation_rate",
"use_serial_batch_fields",
"batch_no",
"serial_no",
]:
if item_row.get(field):
se_child.set(field, item_row.get(field))
@@ -2983,7 +3005,7 @@ def get_available_materials(work_order) -> dict:
if row.batch_no:
item_data.batch_details[row.batch_no] += row.qty
if row.batch_nos:
elif row.batch_nos:
for batch_no, qty in row.batch_nos.items():
item_data.batch_details[batch_no] += qty
@@ -2991,7 +3013,7 @@ def get_available_materials(work_order) -> dict:
item_data.serial_nos.extend(get_serial_nos(row.serial_no))
item_data.serial_nos.sort()
if row.serial_nos:
elif row.serial_nos:
item_data.serial_nos.extend(get_serial_nos(row.serial_nos))
item_data.serial_nos.sort()
else:
@@ -3001,7 +3023,7 @@ def get_available_materials(work_order) -> dict:
if row.batch_no:
item_data.batch_details[row.batch_no] -= row.qty
if row.batch_nos:
elif row.batch_nos:
for batch_no, qty in row.batch_nos.items():
item_data.batch_details[batch_no] += qty
@@ -3009,7 +3031,7 @@ def get_available_materials(work_order) -> dict:
for serial_no in get_serial_nos(row.serial_no):
item_data.serial_nos.remove(serial_no)
if row.serial_nos:
elif row.serial_nos:
for serial_no in get_serial_nos(row.serial_nos):
item_data.serial_nos.remove(serial_no)