aii: stock entry

This commit is contained in:
Nabin Hait 2013-03-19 12:01:24 +05:30
parent 35e037651c
commit c3afb256b4
8 changed files with 174 additions and 81 deletions

View File

@ -19,9 +19,9 @@ import webnotes
from webnotes.utils import cint
from setup.utils import get_company_currency
from controllers.accounts_controller import AccountsController
from controllers.stock_controller import StockController
class SellingController(AccountsController):
class SellingController(StockController):
def validate(self):
self.set_total_in_words()
@ -37,27 +37,4 @@ class SellingController(AccountsController):
self.doc.grand_total or self.doc.rounded_total, company_currency)
if self.meta.get_field("in_words_export"):
self.doc.in_words_export = money_in_words(disable_rounded_total and
self.doc.grand_total_export or self.doc.rounded_total_export, self.doc.currency)
def get_stock_ledger_entries(self):
item_list, warehouse_list = self.get_distinct_item_warehouse()
if item_list and warehouse_list:
return webnotes.conn.sql("""select item_code, voucher_type, voucher_no,
voucher_detail_no, posting_date, posting_time, stock_value,
warehouse, actual_qty as qty from `tabStock Ledger Entry`
where ifnull(`is_cancelled`, "No") = "No" and company = %s
and item_code in (%s) and warehouse in (%s)
order by item_code desc, warehouse desc, posting_date desc,
posting_time desc, name desc""" %
('%s', ', '.join(['%s']*len(item_list)), ', '.join(['%s']*len(warehouse_list))),
tuple([self.doc.company] + item_list + warehouse_list), as_dict=1)
def get_distinct_item_warehouse(self):
item_list = []
warehouse_list = []
for item in self.doclist.get({"parentfield": self.fname}) \
+ self.doclist.get({"parentfield": "packing_details"}):
item_list.append(item.item_code)
warehouse_list.append(item.warehouse)
return list(set(item_list)), list(set(warehouse_list))
self.doc.grand_total_export or self.doc.rounded_total_export, self.doc.currency)

View File

@ -0,0 +1,71 @@
# ERPNext - web based ERP (http://erpnext.com)
# Copyright (C) 2012 Web Notes Technologies Pvt Ltd
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
from __future__ import unicode_literals
import webnotes
from controllers.accounts_controller import AccountsController
class StockController(AccountsController):
def make_gl_entries(self, against_stock_account, amount, cost_center=None):
stock_in_hand_account = self.get_stock_in_hand_account()
if amount:
gl_entries = [
# stock in hand account
self.get_gl_dict({
"account": stock_in_hand_account,
"against": against_stock_account,
"debit": amount,
"remarks": self.doc.remarks or "Accounting Entry for Stock",
}, self.doc.docstatus == 2),
# account against stock in hand
self.get_gl_dict({
"account": against_stock_account,
"against": stock_in_hand_account,
"credit": amount,
"cost_center": cost_center or None,
"remarks": self.doc.remarks or "Accounting Entry for Stock",
}, self.doc.docstatus == 2),
]
from accounts.general_ledger import make_gl_entries
make_gl_entries(gl_entries, cancel=self.doc.docstatus == 2)
def get_stock_ledger_entries(self, item_list=None, warehouse_list=None):
if not (item_list and warehouse_list):
item_list, warehouse_list = self.get_distinct_item_warehouse()
if item_list and warehouse_list:
return webnotes.conn.sql("""select item_code, voucher_type, voucher_no,
voucher_detail_no, posting_date, posting_time, stock_value,
warehouse, actual_qty as qty from `tabStock Ledger Entry`
where ifnull(`is_cancelled`, "No") = "No" and company = %s
and item_code in (%s) and warehouse in (%s)
order by item_code desc, warehouse desc, posting_date desc,
posting_time desc, name desc""" %
('%s', ', '.join(['%s']*len(item_list)), ', '.join(['%s']*len(warehouse_list))),
tuple([self.doc.company] + item_list + warehouse_list), as_dict=1)
def get_distinct_item_warehouse(self):
item_list = []
warehouse_list = []
for item in self.doclist.get({"parentfield": self.fname}) \
+ self.doclist.get({"parentfield": "packing_details"}):
item_list.append(item.item_code)
warehouse_list.append(item.warehouse)
return list(set(item_list)), list(set(warehouse_list))

View File

@ -234,4 +234,11 @@ cur_frm.cscript.validate_items = function(doc) {
cur_frm.fields_dict.customer.get_query = erpnext.utils.customer_query;
cur_frm.fields_dict.supplier.get_query = erpnext.utils.supplier_query;
cur_frm.fields_dict.supplier.get_query = erpnext.utils.supplier_query;
cur_frm.fields_dict["expense_adjustment_account"].get_query = function(doc) {
return {
"query": "accounts.utils.get_account_list",
"filters": { "company": doc.company }
}
}

View File

@ -26,12 +26,11 @@ from stock.utils import get_incoming_rate
from stock.stock_ledger import get_previous_sle
import json
sql = webnotes.conn.sql
from controllers.accounts_controller import AccountsController
from controllers.stock_controller import StockController
class DocType(AccountsController):
class DocType(StockController):
def __init__(self, doc, doclist=[]):
self.doc = doc
self.doclist = doclist
@ -168,41 +167,24 @@ class DocType(AccountsController):
if not cint(webnotes.defaults.get_global_default("auto_inventory_accounting")):
return
abbr = webnotes.conn.get_value("Company", self.doc.company, "abbr")
stock_in_hand_account = self.get_stock_in_hand_account()
total_valuation_amount = self.get_total_valuation_amount()
if total_valuation_amount:
gl_entries = [
# debit stock in hand account
self.get_gl_dict({
"account": stock_in_hand_account,
"against": "Stock Adjustment - %s" % abbr,
"debit": total_valuation_amount,
"remarks": self.doc.remarks or "Accounting Entry for Stock",
}, self.doc.docstatus == 2),
# debit stock received but not billed account
self.get_gl_dict({
"account": "Stock Adjustment - %s" % abbr,
"against": stock_in_hand_account,
"credit": total_valuation_amount,
"cost_center": "Auto Inventory Accounting - %s" % abbr,
"remarks": self.doc.remarks or "Accounting Entry for Stock",
}, self.doc.docstatus == 2),
]
from accounts.general_ledger import make_gl_entries
make_gl_entries(gl_entries, cancel=self.doc.docstatus == 2)
if not self.doc.expense_adjustment_account:
webnotes.msgprint(_("Please enter Expense/Adjustment Account"), raise_exception=1)
cost_center = "Auto Inventory Accounting - %s" % (self.company_abbr,)
total_valuation_amount = self.get_total_valuation_amount()
super(DocType, self).make_gl_entries(self.doc.expense_adjustment_account,
total_valuation_amount, cost_center)
def get_total_valuation_amount(self):
total_valuation_amount = 0
for item in self.doclist.get({"parentfield": "mtn_details"}):
if item.t_warehouse and not item.s_warehouse:
total_valuation_amount += flt(item.incoming_rate) * flt(item.transfer_qty)
if item.s_warehouse and not item.t_warehouse:
total_valuation_amount -= flt(item.incoming_rate) * flt(item.transfer_qty)
return total_valuation_amount
def get_stock_and_rate(self):

View File

@ -1,8 +1,8 @@
[
{
"creation": "2013-01-23 19:57:20",
"creation": "2013-03-07 18:50:32",
"docstatus": 0,
"modified": "2013-01-28 17:59:20",
"modified": "2013-03-14 12:25:00",
"modified_by": "Administrator",
"owner": "Administrator"
},
@ -60,6 +60,7 @@
"fieldtype": "Column Break",
"oldfieldtype": "Column Break",
"print_width": "50%",
"read_only": 0,
"width": "50%"
},
{
@ -76,6 +77,7 @@
"oldfieldtype": "Select",
"options": "\nSTE",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0
@ -95,6 +97,7 @@
"oldfieldtype": "Select",
"options": "Material Issue\nMaterial Receipt\nMaterial Transfer\nManufacture/Repack\nSubcontract\nSales Return\nPurchase Return",
"print_hide": 0,
"read_only": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0
@ -105,6 +108,7 @@
"fieldtype": "Column Break",
"oldfieldtype": "Column Break",
"print_width": "50%",
"read_only": 0,
"width": "50%"
},
{
@ -122,6 +126,7 @@
"oldfieldname": "posting_date",
"oldfieldtype": "Date",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 1
@ -138,16 +143,26 @@
"oldfieldname": "posting_time",
"oldfieldtype": "Time",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0
},
{
"depends_on": "eval:sys_defaults.auto_inventory_accounting",
"doctype": "DocField",
"fieldname": "expense_adjustment_account",
"fieldtype": "Link",
"label": "Expense/Adjustment Account",
"options": "Account"
},
{
"doctype": "DocField",
"fieldname": "items_section",
"fieldtype": "Section Break",
"label": "Items",
"oldfieldtype": "Section Break"
"oldfieldtype": "Section Break",
"read_only": 0
},
{
"allow_on_submit": 0,
@ -163,6 +178,7 @@
"oldfieldtype": "Link",
"options": "Warehouse",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0
@ -170,7 +186,8 @@
{
"doctype": "DocField",
"fieldname": "cb0",
"fieldtype": "Column Break"
"fieldtype": "Column Break",
"read_only": 0
},
{
"allow_on_submit": 0,
@ -186,6 +203,7 @@
"oldfieldtype": "Link",
"options": "Warehouse",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0
@ -194,7 +212,8 @@
"doctype": "DocField",
"fieldname": "sb0",
"fieldtype": "Section Break",
"options": "Simple"
"options": "Simple",
"read_only": 0
},
{
"allow_on_submit": 0,
@ -209,6 +228,7 @@
"oldfieldtype": "Table",
"options": "Stock Entry Detail",
"print_hide": 0,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0
@ -221,13 +241,15 @@
"label": "Get Stock and Rate",
"oldfieldtype": "Button",
"options": "get_stock_and_rate",
"print_hide": 1
"print_hide": 1,
"read_only": 0
},
{
"doctype": "DocField",
"fieldname": "sb1",
"fieldtype": "Section Break",
"label": "Reference"
"label": "Reference",
"read_only": 0
},
{
"allow_on_submit": 0,
@ -243,6 +265,7 @@
"oldfieldtype": "Link",
"options": "Production Order",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 1
@ -253,7 +276,8 @@
"fieldname": "bom_no",
"fieldtype": "Link",
"label": "BOM No",
"options": "BOM"
"options": "BOM",
"read_only": 0
},
{
"allow_on_submit": 0,
@ -269,6 +293,7 @@
"oldfieldname": "fg_completed_qty",
"oldfieldtype": "Currency",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0
@ -287,6 +312,7 @@
"oldfieldtype": "Link",
"options": "Delivery Note",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 1
@ -305,6 +331,7 @@
"oldfieldtype": "Link",
"options": "Purchase Receipt",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 1
@ -312,7 +339,8 @@
{
"doctype": "DocField",
"fieldname": "cb1",
"fieldtype": "Column Break"
"fieldtype": "Column Break",
"read_only": 0
},
{
"default": "1",
@ -321,7 +349,8 @@
"doctype": "DocField",
"fieldname": "use_multi_level_bom",
"fieldtype": "Check",
"label": "Use Multi-Level BOM"
"label": "Use Multi-Level BOM",
"read_only": 0
},
{
"allow_on_submit": 0,
@ -335,6 +364,7 @@
"no_copy": 0,
"oldfieldtype": "Button",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0
@ -348,14 +378,16 @@
"label": "Sales Invoice No",
"no_copy": 1,
"options": "Sales Invoice",
"print_hide": 1
"print_hide": 1,
"read_only": 0
},
{
"depends_on": "eval:(doc.purpose==\"Sales Return\" || doc.purpose==\"Purchase Return\")",
"doctype": "DocField",
"fieldname": "contact_section",
"fieldtype": "Section Break",
"label": "Contact Info"
"label": "Contact Info",
"read_only": 0
},
{
"allow_on_submit": 0,
@ -371,6 +403,7 @@
"oldfieldtype": "Link",
"options": "Supplier",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0
@ -406,6 +439,7 @@
"oldfieldname": "supplier_address",
"oldfieldtype": "Small Text",
"print_hide": 0,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0
@ -424,6 +458,7 @@
"oldfieldtype": "Link",
"options": "Customer",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0
@ -459,6 +494,7 @@
"oldfieldname": "customer_address",
"oldfieldtype": "Small Text",
"print_hide": 0,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0
@ -468,13 +504,15 @@
"fieldname": "more_info",
"fieldtype": "Section Break",
"label": "More Info",
"oldfieldtype": "Section Break"
"oldfieldtype": "Section Break",
"read_only": 0
},
{
"doctype": "DocField",
"fieldname": "col4",
"fieldtype": "Column Break",
"print_width": "50%",
"read_only": 0,
"width": "50%"
},
{
@ -485,7 +523,8 @@
"label": "Project Name",
"oldfieldname": "project_name",
"oldfieldtype": "Link",
"options": "Project"
"options": "Project",
"read_only": 0
},
{
"allow_on_submit": 0,
@ -500,6 +539,7 @@
"oldfieldtype": "Link",
"options": "Print Heading",
"print_hide": 0,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0
@ -517,6 +557,7 @@
"oldfieldtype": "Link",
"options": "Company",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 1,
"search_index": 0
@ -526,6 +567,7 @@
"fieldname": "col5",
"fieldtype": "Column Break",
"print_width": "50%",
"read_only": 0,
"width": "50%"
},
{
@ -558,6 +600,7 @@
"oldfieldname": "remarks",
"oldfieldtype": "Text",
"print_hide": 1,
"read_only": 0,
"report_hide": 0,
"reqd": 0,
"search_index": 0
@ -569,5 +612,13 @@
{
"doctype": "DocPerm",
"role": "Manufacturing User"
},
{
"doctype": "DocPerm",
"role": "Manufacturing Manager"
},
{
"doctype": "DocPerm",
"role": "Material Manager"
}
]

View File

@ -168,6 +168,7 @@ test_records = [
"posting_time": "17:14:24",
"purpose": "Material Receipt",
"fiscal_year": "_Test Fiscal Year 2013",
"expense_adjustment_account": "Stock Adjustment - _TC"
},
{
"conversion_factor": 1.0,
@ -190,6 +191,7 @@ test_records = [
"posting_time": "17:15",
"purpose": "Material Issue",
"fiscal_year": "_Test Fiscal Year 2013",
"expense_adjustment_account": "Stock Adjustment - _TC"
},
{
"conversion_factor": 1.0,
@ -212,6 +214,7 @@ test_records = [
"posting_time": "17:14:24",
"purpose": "Material Transfer",
"fiscal_year": "_Test Fiscal Year 2013",
"expense_adjustment_account": "Stock Adjustment - _TC"
},
{
"conversion_factor": 1.0,

View File

@ -71,7 +71,7 @@ def update_entries_after(args, verbose=1):
(qty_after_transaction * valuation_rate) or 0
else:
stock_value = sum((flt(batch[0]) * flt(batch[1]) for batch in stock_queue))
# print sle.posting_date, sle.actual_qty, sle.incoming_rate, stock_queue, stock_value
# update current sle
webnotes.conn.sql("""update `tabStock Ledger Entry`
set qty_after_transaction=%s, valuation_rate=%s, stock_queue=%s,

View File

@ -165,8 +165,8 @@ def get_warehouse_list(doctype, txt, searchfield, start, page_len, filters):
return wlist
def get_buying_amount(item_code, warehouse, qty, voucher_type, voucher_no, voucher_detail_no,
stock_ledger_entries, item_sales_bom):
if item_sales_bom.get(item_code):
stock_ledger_entries, item_sales_bom=None):
if item_sales_bom and item_sales_bom.get(item_code):
# sales bom item
buying_amount = 0.0
for bom_item in item_sales_bom[item_code]:
@ -182,13 +182,15 @@ def _get_buying_amount(voucher_type, voucher_no, item_row, item_code, warehouse,
stock_ledger_entries):
for i, sle in enumerate(stock_ledger_entries):
if sle.voucher_type == voucher_type and sle.voucher_no == voucher_no and \
len(stock_ledger_entries) > i+1:
if (sle.voucher_detail_no == item_row) or \
(sle.item_code == item_code and sle.warehouse == warehouse and \
abs(flt(sle.qty)) == qty):
buying_amount = flt(stock_ledger_entries[i+1].stock_value) - \
flt(sle.stock_value)
return buying_amount
(sle.voucher_detail_no == item_row or (sle.voucher_type != "Stock Reconciliation"
and sle.item_code == item_code and sle.warehouse == warehouse and flt(sle.qty) == qty)):
# print "previous_sle", stock_ledger_entries[i+1]
# print "current sle", sle
previous_stock_value = len(stock_ledger_entries) > i+1 and \
flt(stock_ledger_entries[i+1].stock_value) or 0.0
buying_amount = previous_stock_value - flt(sle.stock_value)
return buying_amount
return 0.0
def get_sales_bom():