[fix] #8427
This commit is contained in:
parent
834541a7e8
commit
f5279a0d67
@ -13,7 +13,7 @@ from erpnext.stock.stock_balance import update_bin_qty, get_ordered_qty
|
||||
from frappe.desk.notifications import clear_doctype_notifications
|
||||
from erpnext.buying.utils import (validate_for_items, check_for_closed_status,
|
||||
update_last_purchase_rate)
|
||||
|
||||
from erpnext.stock.utils import get_bin
|
||||
|
||||
form_grid_templates = {
|
||||
"items": "templates/form_grid/item_grid.html"
|
||||
@ -187,6 +187,8 @@ class PurchaseOrder(BuyingController):
|
||||
self.update_prevdoc_status()
|
||||
self.update_requested_qty()
|
||||
self.update_ordered_qty()
|
||||
if self.is_subcontracted == "Yes":
|
||||
self.update_reserved_qty_for_subcontract()
|
||||
|
||||
frappe.get_doc('Authorization Control').validate_approving_authority(self.doctype,
|
||||
self.company, self.base_grand_total)
|
||||
@ -249,6 +251,17 @@ class PurchaseOrder(BuyingController):
|
||||
if item.delivered_by_supplier == 1:
|
||||
item.received_qty = item.qty
|
||||
|
||||
def update_reserved_qty_for_subcontract(self):
|
||||
items = list(set([d.rm_item_code for d in self.get("supplied_items")]))
|
||||
item_wh = frappe._dict(frappe.db.sql("""select item_code, default_warehouse
|
||||
from `tabItem` where name in ({0})""".format(", ".join(["%s"] * len(items))), items))
|
||||
|
||||
for d in self.supplied_items:
|
||||
if d.rm_item_code:
|
||||
warehouse = item_wh.get(d.rm_item_code)
|
||||
stock_bin = get_bin(d.rm_item_code, warehouse)
|
||||
stock_bin.update_reserved_qty_for_sub_contracting(self.name, transferred_qty=0, transaction_type = "Reserve")
|
||||
|
||||
@frappe.whitelist()
|
||||
def close_or_unclose_purchase_orders(names, status):
|
||||
if not frappe.has_permission("Purchase Order", "write"):
|
||||
|
@ -89,7 +89,7 @@ erpnext.stock.ItemDashboard = Class.extend({
|
||||
data.forEach(function(d) {
|
||||
d.actual_or_pending = d.projected_qty + d.reserved_qty + d.reserved_qty_for_production;
|
||||
d.pending_qty = 0;
|
||||
d.total_reserved = d.reserved_qty + d.reserved_qty_for_production;
|
||||
d.total_reserved = d.reserved_qty + d.reserved_qty_for_production + d.reserved_qty_for_sub_contract;
|
||||
if(d.actual_or_pending > d.actual_qty) {
|
||||
d.pending_qty = d.actual_or_pending - d.actual_qty;
|
||||
}
|
||||
|
@ -26,13 +26,14 @@ def get_data(item_code=None, warehouse=None, item_group=None,
|
||||
return frappe.db.sql('''
|
||||
select
|
||||
b.item_code, b.warehouse, b.projected_qty, b.reserved_qty,
|
||||
b.reserved_qty_for_production, b.actual_qty, b.valuation_rate, i.item_name
|
||||
b.reserved_qty_for_production, b.reserved_qty_for_sub_contract, b.actual_qty, b.valuation_rate, i.item_name
|
||||
from
|
||||
tabBin b, tabItem i
|
||||
where
|
||||
b.item_code = i.name
|
||||
and
|
||||
(b.projected_qty != 0 or b.reserved_qty != 0 or b.reserved_qty_for_production != 0 or b.actual_qty != 0)
|
||||
(b.projected_qty != 0 or b.reserved_qty != 0 or b.reserved_qty_for_production != 0
|
||||
or b.reserved_qty_for_sub_contract != 0 or b.actual_qty != 0)
|
||||
{conditions}
|
||||
order by
|
||||
{sort_by} {sort_order}
|
||||
|
@ -296,6 +296,36 @@
|
||||
"set_only_once": 0,
|
||||
"unique": 0
|
||||
},
|
||||
{
|
||||
"allow_bulk_edit": 0,
|
||||
"allow_on_submit": 0,
|
||||
"bold": 0,
|
||||
"collapsible": 0,
|
||||
"columns": 0,
|
||||
"fieldname": "reserved_qty_for_sub_contract",
|
||||
"fieldtype": "Float",
|
||||
"hidden": 0,
|
||||
"ignore_user_permissions": 0,
|
||||
"ignore_xss_filter": 0,
|
||||
"in_filter": 0,
|
||||
"in_global_search": 0,
|
||||
"in_list_view": 0,
|
||||
"in_standard_filter": 0,
|
||||
"label": "Reserved Qty for sub contract",
|
||||
"length": 0,
|
||||
"no_copy": 0,
|
||||
"permlevel": 0,
|
||||
"precision": "",
|
||||
"print_hide": 0,
|
||||
"print_hide_if_no_value": 0,
|
||||
"read_only": 0,
|
||||
"remember_last_selected_value": 0,
|
||||
"report_hide": 0,
|
||||
"reqd": 0,
|
||||
"search_index": 0,
|
||||
"set_only_once": 0,
|
||||
"unique": 0
|
||||
},
|
||||
{
|
||||
"allow_bulk_edit": 0,
|
||||
"allow_on_submit": 0,
|
||||
@ -463,7 +493,7 @@
|
||||
"issingle": 0,
|
||||
"istable": 0,
|
||||
"max_attachments": 0,
|
||||
"modified": "2017-06-13 13:06:32.601505",
|
||||
"modified": "2017-11-22 08:14:30.615638",
|
||||
"modified_by": "Administrator",
|
||||
"module": "Stock",
|
||||
"name": "Bin",
|
||||
|
@ -94,6 +94,28 @@ class Bin(Document):
|
||||
self.db_set('reserved_qty_for_production', self.reserved_qty_for_production)
|
||||
self.db_set('projected_qty', self.projected_qty)
|
||||
|
||||
def update_reserved_qty_for_sub_contracting(self, po_name, transferred_qty, transaction_type):
|
||||
#Update Reserved Quantity for Sub Contracting in Bin
|
||||
if transaction_type == "Reserve":
|
||||
required_qty = frappe.db.sql('''select sum(itemsup.required_qty)
|
||||
from `tabItem` item, `tabPurchase Order` po, `tabPurchase Order Item Supplied` itemsup
|
||||
where
|
||||
item.name = itemsup.rm_item_code
|
||||
and po.name = %s
|
||||
and itemsup.rm_item_code = %s
|
||||
and itemsup.parent = po.name
|
||||
and po.docstatus = 1
|
||||
and po.is_subcontracted = 'Yes'
|
||||
and item.default_warehouse = %s''', (po_name, self.item_code, self.warehouse))[0][0]
|
||||
elif transaction_type == "Transfer":
|
||||
required_qty = 0
|
||||
|
||||
reserved_qty_bin = self.reserved_qty_for_sub_contract
|
||||
reserved_qty_for_sub_contract = reserved_qty_bin + required_qty - transferred_qty
|
||||
|
||||
self.set_projected_qty()
|
||||
self.db_set('reserved_qty_for_sub_contract', reserved_qty_for_sub_contract)
|
||||
self.db_set('projected_qty', self.projected_qty)
|
||||
|
||||
def update_item_projected_qty(item_code):
|
||||
'''Set total_projected_qty in Item as sum of projected qty in all warehouses'''
|
||||
|
@ -11,6 +11,7 @@ from erpnext.stock.stock_ledger import get_previous_sle, NegativeStockError
|
||||
from erpnext.stock.get_item_details import get_bin_details, get_default_cost_center, get_conversion_factor
|
||||
from erpnext.stock.doctype.batch.batch import get_batch_no, set_batch_nos
|
||||
from erpnext.manufacturing.doctype.bom.bom import validate_bom_no
|
||||
from erpnext.stock.utils import get_bin
|
||||
import json
|
||||
|
||||
class IncorrectValuationRateError(frappe.ValidationError): pass
|
||||
@ -64,6 +65,8 @@ class StockEntry(StockController):
|
||||
update_serial_nos_after_submit(self, "items")
|
||||
self.update_production_order()
|
||||
self.validate_purchase_order()
|
||||
if self.purchase_order and self.purpose == "Subcontract":
|
||||
self.update_purchase_order_supplied_items()
|
||||
self.make_gl_entries()
|
||||
|
||||
def on_cancel(self):
|
||||
@ -803,6 +806,30 @@ class StockEntry(StockController):
|
||||
if getdate(self.posting_date) > getdate(expiry_date):
|
||||
frappe.throw(_("Batch {0} of Item {1} has expired.").format(item.batch_no, item.item_code))
|
||||
|
||||
def update_purchase_order_supplied_items(self):
|
||||
materials_transferred = frappe._dict(frappe.db.sql("""
|
||||
select
|
||||
concat(item_code, sed.s_warehouse), sum(qty)
|
||||
from
|
||||
`tabStock Entry` se, `tabStock Entry Detail` sed
|
||||
where
|
||||
se.name = sed.parent and se.docstatus=1 and se.purpose='Subcontract'
|
||||
and se.purchase_order= %s and ifnull(sed.s_warehouse, '') != ''
|
||||
group by sed.item_code, sed.s_warehouse
|
||||
""", self.purchase_order))
|
||||
#Get PO Supplied Items Details
|
||||
po_doc = frappe.get_doc("Purchase Order",self.purchase_order)
|
||||
po_supplied_items = po_doc.get("supplied_items")
|
||||
items = list(set([d.rm_item_code for d in po_supplied_items]))
|
||||
item_wh = frappe._dict(frappe.db.sql("""select item_code as "item_code", default_warehouse as "warehouse"
|
||||
from tabItem where name in ({0})""".format(", ".join(["%s"] * len(items))), items))
|
||||
#Update reserved sub contracted quantity in bin based on Supplied Item Details
|
||||
for d in po_supplied_items:
|
||||
warehouse = item_wh.get(d.rm_item_code)
|
||||
transferred_qty = materials_transferred.get(d.rm_item_code + warehouse)
|
||||
stock_bin = get_bin(d.rm_item_code, warehouse)
|
||||
stock_bin.update_reserved_qty_for_sub_contracting(self.purchase_order, transferred_qty, transaction_type = "Transfer")
|
||||
|
||||
@frappe.whitelist()
|
||||
def get_production_order_details(production_order):
|
||||
production_order = frappe.get_doc("Production Order", production_order)
|
||||
|
@ -48,6 +48,7 @@ frappe.pages['stock-balance'].on_page_load = function(wrapper) {
|
||||
{fieldname: 'projected_qty', label: __('Projected qty')},
|
||||
{fieldname: 'reserved_qty', label: __('Reserved for sale')},
|
||||
{fieldname: 'reserved_qty_for_production', label: __('Reserved for manufacturing')},
|
||||
{fieldname: 'reserved_qty_for_sub_contract', label: __('Reserved for sub contracting')},
|
||||
{fieldname: 'actual_qty', label: __('Actual qty in stock')},
|
||||
]
|
||||
},
|
||||
|
@ -150,7 +150,7 @@ def update_bin_qty(item_code, warehouse, qty_dict=None):
|
||||
if mismatch:
|
||||
bin.projected_qty = (flt(bin.actual_qty) + flt(bin.ordered_qty) +
|
||||
flt(bin.indented_qty) + flt(bin.planned_qty) - flt(bin.reserved_qty)
|
||||
- flt(bin.reserved_qty_for_production))
|
||||
- flt(bin.reserved_qty_for_production)) - flt(bin.reserved_qty_for_sub_contract)
|
||||
|
||||
bin.save()
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user