set stock balance as per serial no count
Cherry Picked and Modified by @anandpdoshi Conflicts: stock/doctype/stock_ledger/stock_ledger.py utilities/repost_stock.py
This commit is contained in:
parent
88a869f34d
commit
6298536e46
@ -0,0 +1,13 @@
|
|||||||
|
# Copyright (c) 2013, Web Notes Technologies Pvt. Ltd. and Contributors
|
||||||
|
# License: GNU General Public License v3. See license.txt
|
||||||
|
|
||||||
|
from __future__ import unicode_literals
|
||||||
|
import frappe
|
||||||
|
|
||||||
|
def execute():
|
||||||
|
from erpnext.utilities.repost_stock import set_stock_balance_as_per_serial_no
|
||||||
|
frappe.db.auto_commit_on_many_writes = 1
|
||||||
|
|
||||||
|
set_stock_balance_as_per_serial_no()
|
||||||
|
|
||||||
|
frappe.db.auto_commit_on_many_writes = 0
|
@ -3,47 +3,7 @@
|
|||||||
|
|
||||||
from __future__ import unicode_literals
|
from __future__ import unicode_literals
|
||||||
import frappe
|
import frappe
|
||||||
|
|
||||||
from frappe.utils import flt, now
|
|
||||||
from frappe.model.document import Document
|
from frappe.model.document import Document
|
||||||
|
|
||||||
class StockLedger(Document):
|
class StockLedger(Document):
|
||||||
|
pass
|
||||||
def update_stock(self, values, is_amended = 'No'):
|
|
||||||
for v in values:
|
|
||||||
sle_id = ''
|
|
||||||
|
|
||||||
# reverse quantities for cancel
|
|
||||||
if v.get('is_cancelled') == 'Yes':
|
|
||||||
v['actual_qty'] = -flt(v['actual_qty'])
|
|
||||||
# cancel matching entry
|
|
||||||
frappe.db.sql("""update `tabStock Ledger Entry` set is_cancelled='Yes',
|
|
||||||
modified=%s, modified_by=%s
|
|
||||||
where voucher_no=%s and voucher_type=%s""",
|
|
||||||
(now(), frappe.session.user, v['voucher_no'], v['voucher_type']))
|
|
||||||
|
|
||||||
if v.get("actual_qty"):
|
|
||||||
sle_id = self.make_entry(v)
|
|
||||||
|
|
||||||
args = v.copy()
|
|
||||||
args.update({
|
|
||||||
"sle_id": sle_id,
|
|
||||||
"is_amended": is_amended
|
|
||||||
})
|
|
||||||
|
|
||||||
frappe.get_doc('Warehouse', v["warehouse"]).update_bin(args)
|
|
||||||
|
|
||||||
|
|
||||||
def make_entry(self, args):
|
|
||||||
args.update({"doctype": "Stock Ledger Entry"})
|
|
||||||
sle = frappe.get_doc(args)
|
|
||||||
sle.ignore_permissions = 1
|
|
||||||
sle.insert()
|
|
||||||
return sle.name
|
|
||||||
|
|
||||||
def repost(self):
|
|
||||||
"""
|
|
||||||
Repost everything!
|
|
||||||
"""
|
|
||||||
for wh in frappe.db.sql("select name from tabWarehouse"):
|
|
||||||
frappe.get_doc('Warehouse', wh[0]).repost_stock()
|
|
||||||
|
@ -4,8 +4,10 @@
|
|||||||
from __future__ import unicode_literals
|
from __future__ import unicode_literals
|
||||||
import frappe
|
import frappe
|
||||||
|
|
||||||
from frappe.utils import flt
|
from frappe.utils import flt, cstr, nowdate, nowtime
|
||||||
|
from erpnext.stock.utils import update_bin
|
||||||
|
from erpnext.stock.stock_ledger import update_entries_after
|
||||||
|
from erpnext.accounts.utils import get_fiscal_year
|
||||||
|
|
||||||
def repost(allow_negative_stock=False):
|
def repost(allow_negative_stock=False):
|
||||||
"""
|
"""
|
||||||
@ -39,7 +41,6 @@ def repost_stock(item_code, warehouse):
|
|||||||
})
|
})
|
||||||
|
|
||||||
def repost_actual_qty(item_code, warehouse):
|
def repost_actual_qty(item_code, warehouse):
|
||||||
from erpnext.stock.stock_ledger import update_entries_after
|
|
||||||
try:
|
try:
|
||||||
update_entries_after({ "item_code": item_code, "warehouse": warehouse })
|
update_entries_after({ "item_code": item_code, "warehouse": warehouse })
|
||||||
except:
|
except:
|
||||||
@ -76,7 +77,7 @@ def get_reserved_qty(item_code, warehouse):
|
|||||||
(select qty as dnpi_qty, qty as so_item_qty,
|
(select qty as dnpi_qty, qty as so_item_qty,
|
||||||
ifnull(delivered_qty, 0) as so_item_delivered_qty, parent, name
|
ifnull(delivered_qty, 0) as so_item_delivered_qty, parent, name
|
||||||
from `tabSales Order Item` so_item
|
from `tabSales Order Item` so_item
|
||||||
where item_code = %s and warehouse = %s
|
where item_code = %s and reserved_warehouse = %s
|
||||||
and exists(select * from `tabSales Order` so
|
and exists(select * from `tabSales Order` so
|
||||||
where so.name = so_item.parent and so.docstatus = 1
|
where so.name = so_item.parent and so.docstatus = 1
|
||||||
and so.status != 'Stopped'))
|
and so.status != 'Stopped'))
|
||||||
@ -129,3 +130,63 @@ def update_bin(item_code, warehouse, qty_dict=None):
|
|||||||
flt(bin.indented_qty) + flt(bin.planned_qty) - flt(bin.reserved_qty)
|
flt(bin.indented_qty) + flt(bin.planned_qty) - flt(bin.reserved_qty)
|
||||||
|
|
||||||
bin.save()
|
bin.save()
|
||||||
|
|
||||||
|
def set_stock_balance_as_per_serial_no(item_code=None, posting_date=None, posting_time=None,
|
||||||
|
fiscal_year=None):
|
||||||
|
if not posting_date: posting_date = nowdate()
|
||||||
|
if not posting_time: posting_time = nowtime()
|
||||||
|
if not fiscal_year: fiscal_year = get_fiscal_year(posting_date)[0]
|
||||||
|
|
||||||
|
condition = " and item.name='%s'" % item_code.replace("'", "\'") if item_code else ""
|
||||||
|
|
||||||
|
bin = frappe.db.sql("""select bin.item_code, bin.warehouse, bin.actual_qty, item.stock_uom
|
||||||
|
from `tabBin` bin, tabItem item
|
||||||
|
where bin.item_code = item.name and item.has_serial_no = 'Yes' %s""" % condition)
|
||||||
|
|
||||||
|
for d in bin:
|
||||||
|
serial_nos = frappe.db.sql("""select count(name) from `tabSerial No`
|
||||||
|
where item_code=%s and warehouse=%s and status = 'Available' and docstatus < 2""", (d[0], d[1]))
|
||||||
|
|
||||||
|
if serial_nos and flt(serial_nos[0][0]) != flt(d[2]):
|
||||||
|
print d[0], d[1], d[2], serial_nos[0][0]
|
||||||
|
|
||||||
|
sle = frappe.db.sql("""select valuation_rate, company from `tabStock Ledger Entry`
|
||||||
|
where item_code = %s and warehouse = %s and ifnull(is_cancelled, 'No') = 'No'
|
||||||
|
order by posting_date desc limit 1""", (d[0], d[1]))
|
||||||
|
|
||||||
|
sle_dict = {
|
||||||
|
'doctype' : 'Stock Ledger Entry',
|
||||||
|
'item_code' : d[0],
|
||||||
|
'warehouse' : d[1],
|
||||||
|
'transaction_date' : nowdate(),
|
||||||
|
'posting_date' : posting_date,
|
||||||
|
'posting_time' : posting_time,
|
||||||
|
'voucher_type' : 'Stock Reconciliation (Manual)',
|
||||||
|
'voucher_no' : '',
|
||||||
|
'voucher_detail_no' : '',
|
||||||
|
'actual_qty' : flt(serial_nos[0][0]) - flt(d[2]),
|
||||||
|
'stock_uom' : d[3],
|
||||||
|
'incoming_rate' : sle and flt(serial_nos[0][0]) > flt(d[2]) and flt(sle[0][0]) or 0,
|
||||||
|
'company' : sle and cstr(sle[0][1]) or 0,
|
||||||
|
'fiscal_year' : fiscal_year,
|
||||||
|
'is_cancelled' : 'No',
|
||||||
|
'batch_no' : '',
|
||||||
|
'serial_no' : ''
|
||||||
|
}
|
||||||
|
|
||||||
|
sle_doc = frappe.get_doc(sle_dict)
|
||||||
|
sle_doc.insert()
|
||||||
|
|
||||||
|
args = sle_dict.copy()
|
||||||
|
args.update({
|
||||||
|
"sle_id": sle_doc.name,
|
||||||
|
"is_amended": 'No'
|
||||||
|
})
|
||||||
|
|
||||||
|
update_bin(args)
|
||||||
|
update_entries_after({
|
||||||
|
"item_code": d[0],
|
||||||
|
"warehouse": d[1],
|
||||||
|
"posting_date": posting_date,
|
||||||
|
"posting_time": posting_time
|
||||||
|
})
|
||||||
|
Loading…
x
Reference in New Issue
Block a user