From e63146408d2be42fd8e0da46148c78877a3fc403 Mon Sep 17 00:00:00 2001 From: Neil Trini Lasrado Date: Wed, 6 May 2015 15:43:35 +0530 Subject: [PATCH 1/6] production order - fixes cost not considering qty issue --- .../doctype/production_order/production_order.js | 7 +++++++ .../doctype/production_order/production_order.py | 15 +++++++++++---- 2 files changed, 18 insertions(+), 4 deletions(-) diff --git a/erpnext/manufacturing/doctype/production_order/production_order.js b/erpnext/manufacturing/doctype/production_order/production_order.js index 60ecd03ee54..1946a6793dc 100644 --- a/erpnext/manufacturing/doctype/production_order/production_order.js +++ b/erpnext/manufacturing/doctype/production_order/production_order.js @@ -189,6 +189,13 @@ $.extend(cur_frm.cscript, { method: "set_production_order_operations" }); }, + + qty: function() { + return this.frm.call({ + doc: this.frm.doc, + method: "set_production_order_operations" + }); + }, show_time_logs: function(doc, cdt, cdn) { var child = locals[cdt][cdn] diff --git a/erpnext/manufacturing/doctype/production_order/production_order.py b/erpnext/manufacturing/doctype/production_order/production_order.py index 9d17cf64759..572b5275a93 100644 --- a/erpnext/manufacturing/doctype/production_order/production_order.py +++ b/erpnext/manufacturing/doctype/production_order/production_order.py @@ -35,7 +35,7 @@ class ProductionOrder(Document): self.validate_sales_order() self.validate_warehouse() - self.calculate_operating_cost() + self.calculate_time() self.validate_delivery_date() from erpnext.utilities.transaction_base import validate_uom_is_integer @@ -63,6 +63,7 @@ class ProductionOrder(Document): def calculate_operating_cost(self): self.planned_operating_cost, self.actual_operating_cost = 0.0, 0.0 for d in self.get("operations"): + d.planned_operating_cost = flt(d.hour_rate) * (flt(d.time_in_mins) / 60.0) d.actual_operating_cost = flt(d.hour_rate) * (flt(d.actual_operation_time) / 60.0) self.planned_operating_cost += flt(d.planned_operating_cost) @@ -175,14 +176,20 @@ class ProductionOrder(Document): self.set('operations', []) operations = frappe.db.sql("""select operation, description, workstation, idx, - hour_rate, time_in_mins, operating_cost as "planned_operating_cost", "Pending" as status + hour_rate, time_in_mins, 0 as "planned_operating_cost", "Pending" as status from `tabBOM Operation` where parent = %s order by idx""", self.bom_no, as_dict=1) self.set('operations', operations) - + self.calculate_time() + + def calculate_time(self): + bom_qty = frappe.db.get_value("BOM", self.bom_no, "quantity") + + for d in self.get("operations"): + d.time_in_mins = d.time_in_mins / bom_qty * flt(self.qty) + self.calculate_operating_cost() - def get_holidays(self, workstation): holiday_list = frappe.db.get_value("Workstation", workstation, "holiday_list") From 4f5cc9d67227e6601686f9972a8d3883e049a25c Mon Sep 17 00:00:00 2001 From: Neil Trini Lasrado Date: Wed, 6 May 2015 20:01:47 +0530 Subject: [PATCH 2/6] Test case added to Production Order to check planned-operating-cost against qty --- .../production_order/test_production_order.py | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/erpnext/manufacturing/doctype/production_order/test_production_order.py b/erpnext/manufacturing/doctype/production_order/test_production_order.py index db00754fc25..7b6425e9953 100644 --- a/erpnext/manufacturing/doctype/production_order/test_production_order.py +++ b/erpnext/manufacturing/doctype/production_order/test_production_order.py @@ -125,7 +125,17 @@ class TestProductionOrder(unittest.TestCase): "docstatus": 0 }) self.assertRaises(OverProductionLoggedError, time_log2.save) - + + def test_planned_operating_cost(self): + prod_order = make_prod_order_test_record(item="_Test FG Item 2", + planned_start_date="2014-11-25 00:00:00", qty=1, do_not_save=True) + prod_order.set_production_order_operations() + prod_order.save() + cost = prod_order.planned_operating_cost + prod_order.qty = 2 + prod_order.save() + self.assertEqual(prod_order.planned_operating_cost, cost*2) + def make_prod_order_test_record(**args): args = frappe._dict(args) From e64d453d09beb399a1e9fe9ab55139e23ff56320 Mon Sep 17 00:00:00 2001 From: Neil Trini Lasrado Date: Thu, 7 May 2015 11:12:14 +0530 Subject: [PATCH 3/6] patch added --- erpnext/patches.txt | 3 ++- ...te_planned_operating_cost_in_production_order.py | 13 +++++++++++++ 2 files changed, 15 insertions(+), 1 deletion(-) create mode 100644 erpnext/patches/v5_0/reclculate_planned_operating_cost_in_production_order.py diff --git a/erpnext/patches.txt b/erpnext/patches.txt index d857c59387d..593a2b4dbb8 100644 --- a/erpnext/patches.txt +++ b/erpnext/patches.txt @@ -150,4 +150,5 @@ erpnext.patches.v5_0.update_advance_paid erpnext.patches.v5_0.link_warehouse_with_account erpnext.patches.v5_0.rename_taxes_and_charges_master execute:frappe.delete_doc("Page", "stock-ledger") -execute:frappe.delete_doc("Page", "stock-level") \ No newline at end of file +execute:frappe.delete_doc("Page", "stock-level") +erpnext.patches.v5_0.reclculate_planned_operating_cost_in_production_order diff --git a/erpnext/patches/v5_0/reclculate_planned_operating_cost_in_production_order.py b/erpnext/patches/v5_0/reclculate_planned_operating_cost_in_production_order.py new file mode 100644 index 00000000000..a943c062bc4 --- /dev/null +++ b/erpnext/patches/v5_0/reclculate_planned_operating_cost_in_production_order.py @@ -0,0 +1,13 @@ +# Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors +# License: GNU General Public License v3. See license.txt + +from __future__ import unicode_literals +import frappe + +def execute(): + for po in frappe.db.sql("""select name from `tabProduction Order` where docstatus < 2""", as_dict=1): + prod_order = frappe.get_doc("Production Order", po.name) + if prod_order.operations: + prod_order.flags.ignore_validate_update_after_submit = True + prod_order.calculate_time() + prod_order.save() \ No newline at end of file From a10bdd4980d8620618d0985f994032ea8ea556c5 Mon Sep 17 00:00:00 2001 From: Neil Trini Lasrado Date: Thu, 7 May 2015 16:09:22 +0530 Subject: [PATCH 4/6] fixes --- .../manufacturing/doctype/production_order/production_order.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/erpnext/manufacturing/doctype/production_order/production_order.py b/erpnext/manufacturing/doctype/production_order/production_order.py index 572b5275a93..71f9c2446af 100644 --- a/erpnext/manufacturing/doctype/production_order/production_order.py +++ b/erpnext/manufacturing/doctype/production_order/production_order.py @@ -35,7 +35,7 @@ class ProductionOrder(Document): self.validate_sales_order() self.validate_warehouse() - self.calculate_time() + self.calculate_operating_cost() self.validate_delivery_date() from erpnext.utilities.transaction_base import validate_uom_is_integer From 20e1c781b69f0c8682043fa3ca69fe62a6ca772d Mon Sep 17 00:00:00 2001 From: Neil Trini Lasrado Date: Thu, 7 May 2015 16:16:23 +0530 Subject: [PATCH 5/6] js call changed to trigger --- .../doctype/production_order/production_order.js | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/erpnext/manufacturing/doctype/production_order/production_order.js b/erpnext/manufacturing/doctype/production_order/production_order.js index 1946a6793dc..3781450d363 100644 --- a/erpnext/manufacturing/doctype/production_order/production_order.js +++ b/erpnext/manufacturing/doctype/production_order/production_order.js @@ -191,10 +191,7 @@ $.extend(cur_frm.cscript, { }, qty: function() { - return this.frm.call({ - doc: this.frm.doc, - method: "set_production_order_operations" - }); + frappe.ui.form.trigger("Production Order", 'bom_no') }, show_time_logs: function(doc, cdt, cdn) { From 3c3cdc7029f4c73a8b95c4498a2df40732761278 Mon Sep 17 00:00:00 2001 From: Neil Trini Lasrado Date: Thu, 7 May 2015 18:52:12 +0530 Subject: [PATCH 6/6] fixes --- .../doctype/production_order/production_order.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/erpnext/manufacturing/doctype/production_order/production_order.py b/erpnext/manufacturing/doctype/production_order/production_order.py index 71f9c2446af..62eb400f05f 100644 --- a/erpnext/manufacturing/doctype/production_order/production_order.py +++ b/erpnext/manufacturing/doctype/production_order/production_order.py @@ -176,8 +176,8 @@ class ProductionOrder(Document): self.set('operations', []) operations = frappe.db.sql("""select operation, description, workstation, idx, - hour_rate, time_in_mins, 0 as "planned_operating_cost", "Pending" as status - from `tabBOM Operation` where parent = %s order by idx""", self.bom_no, as_dict=1) + hour_rate, time_in_mins, "Pending" as status from `tabBOM Operation` + where parent = %s order by idx""", self.bom_no, as_dict=1) self.set('operations', operations) self.calculate_time() @@ -186,7 +186,7 @@ class ProductionOrder(Document): bom_qty = frappe.db.get_value("BOM", self.bom_no, "quantity") for d in self.get("operations"): - d.time_in_mins = d.time_in_mins / bom_qty * flt(self.qty) + d.time_in_mins = flt(d.time_in_mins) / flt(bom_qty) * flt(self.qty) self.calculate_operating_cost()