mirror of
https://github.com/frappe/erpnext.git
synced 2026-10-29 22:57:42 +00:00
fix: recompute quotation status and guard state on Update Items
This commit is contained in:
@@ -4357,6 +4357,19 @@ def update_child_qty_rate(
|
||||
)
|
||||
)
|
||||
|
||||
# The Quotation form hides Update Items for these states; enforce it server-side too.
|
||||
if doc.doctype == "Quotation":
|
||||
if doc.status in ("Lost", "Ordered"):
|
||||
frappe.throw(
|
||||
_("Cannot update items of Quotation {0} because it is {1}.").format(
|
||||
doc.name, _(doc.status)
|
||||
)
|
||||
)
|
||||
if doc.valid_till and getdate(doc.valid_till) < getdate():
|
||||
frappe.throw(
|
||||
_("Cannot update items of Quotation {0} because it has expired.").format(doc.name)
|
||||
)
|
||||
|
||||
def validate_workflow_conditions(doc):
|
||||
workflow = get_workflow_name(doc.doctype)
|
||||
if not workflow:
|
||||
@@ -4774,6 +4787,9 @@ def update_child_qty_rate(
|
||||
elif parent_doctype == "Supplier Quotation":
|
||||
parent.update_rfq_supplier_status(parent.docstatus.is_submitted(), rfqs_before_update)
|
||||
|
||||
elif parent_doctype == "Quotation":
|
||||
parent.set_status(update=True)
|
||||
|
||||
parent.reload()
|
||||
validate_workflow_conditions(parent)
|
||||
|
||||
|
||||
@@ -1219,6 +1219,40 @@ class TestQuotation(FrappeTestCase):
|
||||
expired.submit()
|
||||
self.assertRaises(frappe.ValidationError, make_sales_invoice, expired.name)
|
||||
|
||||
def test_quotation_update_items_recomputes_status(self):
|
||||
from erpnext.stock.doctype.item.test_item import make_item
|
||||
|
||||
warehouse = "_Test Warehouse - _TC"
|
||||
item1 = make_item().item_code
|
||||
item2 = make_item().item_code
|
||||
quotation = make_quotation(
|
||||
item_list=[
|
||||
{"item_code": item1, "qty": 2, "rate": 100, "warehouse": warehouse},
|
||||
{"item_code": item2, "qty": 2, "rate": 100, "warehouse": warehouse},
|
||||
]
|
||||
)
|
||||
|
||||
so = make_sales_order(quotation.name, args={"filtered_children": [quotation.items[0].name]})
|
||||
so.delivery_date = nowdate()
|
||||
so.insert()
|
||||
so.submit()
|
||||
|
||||
quotation.reload()
|
||||
self.assertEqual(quotation.status, "Partially Ordered")
|
||||
|
||||
row = quotation.items[0]
|
||||
trans_items = json.dumps(
|
||||
[{"item_code": row.item_code, "qty": row.qty, "rate": row.rate, "docname": row.name}]
|
||||
)
|
||||
update_child_qty_rate("Quotation", trans_items, quotation.name)
|
||||
|
||||
quotation.reload()
|
||||
self.assertEqual(quotation.status, "Ordered")
|
||||
|
||||
row = quotation.items[0]
|
||||
raised = json.dumps([{"item_code": row.item_code, "qty": 5, "rate": row.rate, "docname": row.name}])
|
||||
self.assertRaises(frappe.ValidationError, update_child_qty_rate, "Quotation", raised, quotation.name)
|
||||
|
||||
|
||||
test_records = frappe.get_test_records("Quotation")
|
||||
|
||||
|
||||
Reference in New Issue
Block a user