def check_if_latest(self, method="save"): from webnotes.model.meta import is_single conflict = False if not cint(self.doc.fields.get('__islocal')): if is_single(self.doc.doctype): modified = webnotes.conn.get_value(self.doc.doctype, self.doc.name, "modified") if isinstance(modified, list): modified = modified[0] if cstr(modified) and cstr(modified) != cstr(self.doc.modified): conflict = True else: tmp = webnotes.conn.sql("""select modified, docstatus from `tab%s` where name="%s" for update""" % (self.doc.doctype, self.doc.name), as_dict=True) if not tmp: webnotes.msgprint("""This record does not exist. Please refresh.""", raise_exception=1) modified = cstr(tmp[0].modified) if modified and modified != cstr(self.doc.modified): conflict = True self.check_docstatus_transition(tmp[0].docstatus, method) if conflict: webnotes.msgprint(_("Error: Document has been modified after you have opened it") \ + (" (%s, %s). " % (modified, self.doc.modified)) \ + _("Please refresh to get the latest document."), raise_exception=TimestampMismatchError)
def create_remarks(self): r = [] if self.doc.cheque_no : if self.doc.cheque_date: r.append('Via Reference #%s dated %s' % (self.doc.cheque_no, formatdate(self.doc.cheque_date))) else : msgprint("Please enter Reference date", raise_exception=1) for d in getlist(self.doclist, 'entries'): if d.against_invoice and d.credit: currency = webnotes.conn.get_value("Sales Invoice", d.against_invoice, "currency") r.append('%s %s against Invoice: %s' % (cstr(currency), fmt_money(flt(d.credit)), d.against_invoice)) if d.against_voucher and d.debit: bill_no = webnotes.conn.sql("""select bill_no, bill_date, currency from `tabPurchase Invoice` where name=%s""", d.against_voucher) if bill_no and bill_no[0][0] and bill_no[0][0].lower().strip() \ not in ['na', 'not applicable', 'none']: r.append('%s %s against Bill %s dated %s' % (cstr(bill_no[0][2]), fmt_money(flt(d.debit)), bill_no[0][0], bill_no[0][1] and formatdate(bill_no[0][1].strftime('%Y-%m-%d')) or '')) if self.doc.user_remark: r.append("User Remark : %s"%self.doc.user_remark) if r: self.doc.remark = ("\n").join(r) else: webnotes.msgprint("User Remarks is mandatory", raise_exception=1)
def validate_max_discount(self): for d in self.doclist.get({"parentfield": self.fname}): discount = flt(webnotes.conn.get_value("Item", d.item_code, "max_discount")) if discount and flt(d.adj_rate) > discount: webnotes.throw(_("You cannot give more than ") + cstr(discount) + "% " + _("discount on Item Code") + ": " + cstr(d.item_code))
def make_items_dict(self, items_list): """makes dict of unique items with it's qty""" for i in items_list: if self.item_dict.has_key(i[0]): self.item_dict[i[0]][0] = flt(self.item_dict[i[0]][0]) + flt(i[1]) else: self.item_dict[i[0]] = [flt(i[1]), cstr(i[2]), cstr(i[3])]
def make_new_invoice(ref_wrapper, posting_date): from webnotes.model.bean import clone from accounts.utils import get_fiscal_year new_invoice = clone(ref_wrapper) mcount = month_map[ref_wrapper.doc.recurring_type] invoice_period_from_date = get_next_date(ref_wrapper.doc.invoice_period_from_date, mcount) # get last day of the month to maintain period if the from date is first day of its own month # and to date is the last day of its own month if (cstr(get_first_day(ref_wrapper.doc.invoice_period_from_date)) == \ cstr(ref_wrapper.doc.invoice_period_from_date)) and \ (cstr(get_last_day(ref_wrapper.doc.invoice_period_to_date)) == \ cstr(ref_wrapper.doc.invoice_period_to_date)): invoice_period_to_date = get_last_day(get_next_date(ref_wrapper.doc.invoice_period_to_date, mcount)) else: invoice_period_to_date = get_next_date(ref_wrapper.doc.invoice_period_to_date, mcount) new_invoice.doc.fields.update({ "posting_date": posting_date, "aging_date": posting_date, "due_date": add_days(posting_date, cint(date_diff(ref_wrapper.doc.due_date, ref_wrapper.doc.posting_date))), "invoice_period_from_date": invoice_period_from_date, "invoice_period_to_date": invoice_period_to_date, "fiscal_year": get_fiscal_year(posting_date)[0], "owner": ref_wrapper.doc.owner, }) new_invoice.submit() return new_invoice
def update_against_doc(d, jv_obj): """ Updates against document, if partial amount splits into rows """ webnotes.conn.sql(""" update `tabJournal Voucher Detail` t1, `tabJournal Voucher` t2 set t1.%(dr_or_cr)s = '%(allocated_amt)s', t1.%(against_fld)s = '%(against_voucher)s', t2.modified = now() where t1.name = '%(voucher_detail_no)s' and t1.parent = t2.name""" % d) if d['allocated_amt'] < d['unadjusted_amt']: jvd = webnotes.conn.sql("""select cost_center, balance, against_account, is_advance from `tabJournal Voucher Detail` where name = %s""", d['voucher_detail_no']) # new entry with balance amount ch = addchild(jv_obj.doc, 'entries', 'Journal Voucher Detail') ch.account = d['account'] ch.cost_center = cstr(jvd[0][0]) ch.balance = cstr(jvd[0][1]) ch.fields[d['dr_or_cr']] = flt(d['unadjusted_amt']) - flt(d['allocated_amt']) ch.fields[d['dr_or_cr']== 'debit' and 'credit' or 'debit'] = 0 ch.against_account = cstr(jvd[0][2]) ch.is_advance = cstr(jvd[0][3]) ch.docstatus = 1 ch.save(1)
def unset_as_default_bom(self): # set Is Default as 1 set(self.doc,'is_default', flt(0)) # update current BOM as default bom in Item Master sql("update `tabItem` set default_bom = null where name = '%s'" % (self.doc.item)) msgprint(cstr(self.doc.name) + "has been unset as Default BOM for Item "+cstr(self.doc.item))
def update_stock(self): sl_entries = [] stock_items = self.get_stock_items() for d in getlist(self.doclist, 'purchase_receipt_details'): if d.item_code in stock_items and d.warehouse: pr_qty = flt(d.qty) * flt(d.conversion_factor) if pr_qty: sl_entries.append(self.get_sl_entries(d, { "actual_qty": flt(pr_qty), "serial_no": cstr(d.serial_no).strip(), "incoming_rate": d.valuation_rate })) if flt(d.rejected_qty) > 0: sl_entries.append(self.get_sl_entries(d, { "warehouse": d.rejected_warehouse, "actual_qty": flt(d.rejected_qty) * flt(d.conversion_factor), "serial_no": cstr(d.rejected_serial_no).strip(), "incoming_rate": d.valuation_rate })) self.bk_flush_supp_wh(sl_entries) self.make_sl_entries(sl_entries)
def get_tds(self): if cstr(self.doc.is_opening) != 'Yes': if not self.doc.credit_to: msgprint("Please Enter Credit To account first") raise Exception else: tds_applicable = sql("select tds_applicable from tabAccount where name = '%s'" % self.doc.credit_to) if tds_applicable and cstr(tds_applicable[0][0]) == 'Yes': if not self.doc.tds_applicable: msgprint("Please enter whether TDS Applicable or not") raise Exception if self.doc.tds_applicable == 'Yes': if not self.doc.tds_category: msgprint("Please select TDS Category") raise Exception else: get_obj('TDS Control').get_tds_amount(self) self.doc.total_tds_on_voucher = self.doc.ded_amount self.doc.total_amount_to_pay=flt(self.doc.grand_total) - flt(self.doc.ded_amount) - self.doc.write_off_amount self.doc.outstanding_amount = self.doc.total_amount_to_pay - flt(self.doc.total_advance) elif self.doc.tds_applicable == 'No': self.doc.tds_category = '' self.doc.tax_code = '' self.doc.rate = 0 self.doc.ded_amount = 0 self.doc.total_tds_on_voucher = 0
def create_remarks(self): r = [] if self.doc.cheque_no : if self.doc.cheque_date: r.append('Via Reference #%s dated %s' % (self.doc.cheque_no, formatdate(self.doc.cheque_date))) else : msgprint("Please enter Reference date") raise Exception for d in getlist(self.doclist, 'entries'): if d.against_invoice and d.credit: currency = sql("select currency from `tabSales Invoice` where name = '%s'" % d.against_invoice) currency = currency and currency[0][0] or '' r.append('%s %s against Invoice: %s' % (cstr(currency), fmt_money(flt(d.credit)), d.against_invoice)) if d.against_voucher and d.debit: bill_no = sql("select bill_no, bill_date, currency from `tabPurchase Invoice` where name=%s", d.against_voucher) if bill_no and bill_no[0][0] and bill_no[0][0].lower().strip() not in ['na', 'not applicable', 'none']: bill_no = bill_no and bill_no[0] r.append('%s %s against Bill %s dated %s' % (bill_no[2] and cstr(bill_no[2]) or '', fmt_money(flt(d.debit)), bill_no[0], bill_no[1] and formatdate(bill_no[1].strftime('%Y-%m-%d')) or '')) if self.doc.user_remark: r.append("User Remark : %s"%self.doc.user_remark) if r: self.doc.remark = ("\n").join(r)
def get_density_details(self,args): dic=eval(args) sub=cstr(flt(dic['syringe'])-flt(dic['weight'])) density=cstr(flt(sub)/flt(dic['volume'])) return{ "density":density }
def get_appr_user_role(self, det, doctype_name, total, based_on, condition, item, company): amt_list, appr_users, appr_roles = [], [], [] users, roles = '','' if det: for x in det: amt_list.append(flt(x[0])) max_amount = max(amt_list) app_dtl = sql("select approving_user, approving_role from `tabAuthorization Rule` where transaction = %s and (value = %s or value > %s) and docstatus != 2 and based_on = %s and company = %s %s" % ('%s', '%s', '%s', '%s', '%s', condition), (doctype_name, flt(max_amount), total, based_on, company)) if not app_dtl: app_dtl = sql("select approving_user, approving_role from `tabAuthorization Rule` where transaction = %s and (value = %s or value > %s) and docstatus != 2 and based_on = %s and ifnull(company,'') = '' %s" % ('%s', '%s', '%s', '%s', condition), (doctype_name, flt(max_amount), total, based_on)) for d in app_dtl: if(d[0]): appr_users.append(d[0]) if(d[1]): appr_roles.append(d[1]) if not has_common(appr_roles, webnotes.user.get_roles()) and not has_common(appr_users, [session['user']]): msg, add_msg = '','' if max_amount: dcc = get_company_currency(self.doc.company) if based_on == 'Grand Total': msg = "since Grand Total exceeds %s. %s" % (dcc, flt(max_amount)) elif based_on == 'Itemwise Discount': msg = "since Discount exceeds %s for Item Code : %s" % (cstr(max_amount)+'%', item) elif based_on == 'Average Discount' or based_on == 'Customerwise Discount': msg = "since Discount exceeds %s" % (cstr(max_amount)+'%') if appr_users: add_msg = "Users : "+cstr(appr_users) if appr_roles: add_msg = "Roles : "+cstr(appr_roles) if appr_users and appr_roles: add_msg = "Users : "+cstr(appr_users)+" or "+"Roles : "+cstr(appr_roles) msgprint("You are not authorize to submit this %s %s. Please send for approval to %s" % (doctype_name, msg, add_msg)) raise Exception
def post_comment(arg): arg = load_json(arg) from webnotes.model.doc import Document d = Document('Comment Widget Record') d.comment_doctype = 'My Company' d.comment_docname = arg['uid'] # to d.owner = webnotes.user.name d.comment = arg['comment'] d.save(1) if cint(arg['notify']): fn = webnotes.conn.sql('select first_name, last_name from tabProfile where name=%s', webnotes.user.name)[0] if fn[0] or f[1]: fn = cstr(fn[0]) + (fn[0] and ' ' or '') + cstr(fn[1]) else: fn = webnotes.user.name from webnotes.utils.email_lib import sendmail from setup.doctype.notification_control.notification_control import get_formatted_message message = '''A new comment has been posted on your page by %s: <b>Comment:</b> %s To answer, please login to your erpnext account! ''' % (fn, arg['comment']) sendmail([arg['uid']], webnotes.user.name, get_formatted_message('New Comment', message), fn + ' has posted a new comment')
def validate_existing_appraisal(self): chk = sql("select name from `tabAppraisal` where employee=%s and (status='Submitted' or status='Completed') and ((start_date>=%s and start_date<=%s) or (end_date>=%s and end_date<=%s))",(self.doc.employee,self.doc.start_date,self.doc.end_date,self.doc.start_date,self.doc.end_date)) if chk: msgprint("You have already created Appraisal "\ +cstr(chk[0][0])+" in the current date range for employee "\ +cstr(self.doc.employee_name)) raise Exception
def on_cancel(self): pc_obj = get_obj(dt = 'Purchase Common') # 1.Check if PO status is stopped pc_obj.check_for_stopped_status(cstr(self.doc.doctype), cstr(self.doc.name)) self.check_for_stopped_status(pc_obj) # 2.Check if Purchase Receipt has been submitted against current Purchase Order pc_obj.check_docstatus(check = 'Next', doctype = 'Purchase Receipt', docname = self.doc.name, detail_doctype = 'Purchase Receipt Detail') # 3.Check if Payable Voucher has been submitted against current Purchase Order #pc_obj.check_docstatus(check = 'Next', doctype = 'Payable Voucher', docname = self.doc.name, detail_doctype = 'PV Detail') submitted = sql("select t1.name from `tabPayable Voucher` t1,`tabPV Detail` t2 where t1.name = t2.parent and t2.purchase_order = '%s' and t1.docstatus = 1" % self.doc.name) if submitted: msgprint("Purchase Invoice : " + cstr(submitted[0][0]) + " has already been submitted !") raise Exception # 4.Set Status as Cancelled set(self.doc,'status','Cancelled') # 5.Update Indents Pending Qty and accordingly it's Status pc_obj.update_prevdoc_detail(self,is_submit = 0) # 6.Update Bin self.update_bin( is_submit = 0, is_stopped = 0) # Step 7 :=> Update last purchase rate pc_obj.update_last_purchase_rate(self, is_submit = 0)
def validate_receiver_nos(self,receiver_list): validated_receiver_list = [] for d in receiver_list: # remove invalid character invalid_char_list = [' ', '+', '-', '(', ')'] for x in invalid_char_list: d = d.replace(x, '') # mobile no validation for erpnext gateway if get_value('SMS Settings', None, 'sms_gateway_url'): mob_no = d else: if not d.startswith("0") and len(d) == 10: mob_no = "91" + d elif d.startswith("0") and len(d) == 11: mob_no = "91" + d[1:] elif len(d) == 12: mob_no = d else: msgprint("Invalid mobile no : " + cstr(d)) raise Exception if not mob_no.isdigit(): msgprint("Invalid mobile no : " + cstr(mob_no)) raise Exception validated_receiver_list.append(mob_no) if not validated_receiver_list: msgprint("Please enter valid mobile nos") raise Exception return validated_receiver_list
def on_cancel(self): pc_obj = get_obj(dt="Purchase Common") # 1.Check if PO status is stopped pc_obj.check_for_stopped_status(cstr(self.doc.doctype), cstr(self.doc.name)) self.check_for_stopped_status(pc_obj) # 2.Check if Purchase Receipt has been submitted against current Purchase Order pc_obj.check_docstatus( check="Next", doctype="Purchase Receipt", docname=self.doc.name, detail_doctype="Purchase Receipt Item" ) # 3.Check if Purchase Invoice has been submitted against current Purchase Order # pc_obj.check_docstatus(check = 'Next', doctype = 'Purchase Invoice', docname = self.doc.name, detail_doctype = 'Purchase Invoice Item') submitted = sql( "select t1.name from `tabPurchase Invoice` t1,`tabPurchase Invoice Item` t2 where t1.name = t2.parent and t2.purchase_order = '%s' and t1.docstatus = 1" % self.doc.name ) if submitted: msgprint("Purchase Invoice : " + cstr(submitted[0][0]) + " has already been submitted !") raise Exception # 4.Set Status as Cancelled webnotes.conn.set(self.doc, "status", "Cancelled") # 5.Update Material Requests Pending Qty and accordingly it's Status pc_obj.update_prevdoc_detail(self, is_submit=0) # 6.Update Bin self.update_bin(is_submit=0, is_stopped=0) # Step 7 :=> Update last purchase rate pc_obj.update_last_purchase_rate(self, is_submit=0)
def check_nextdoc_docstatus(self): # Checks Delivery Note submit_dn = sql("select t1.name from `tabDelivery Note` t1,`tabDelivery Note Item` t2 where t1.name = t2.parent and t2.prevdoc_docname = '%s' and t1.docstatus = 1" % (self.doc.name)) if submit_dn: msgprint("Delivery Note : " + cstr(submit_dn[0][0]) + " has been submitted against " + cstr(self.doc.doctype) + ". Please cancel Delivery Note : " + cstr(submit_dn[0][0]) + " first and then cancel "+ cstr(self.doc.doctype), raise_exception = 1) # Checks Sales Invoice submit_rv = sql("select t1.name from `tabSales Invoice` t1,`tabSales Invoice Item` t2 where t1.name = t2.parent and t2.sales_order = '%s' and t1.docstatus = 1" % (self.doc.name)) if submit_rv: msgprint("Sales Invoice : " + cstr(submit_rv[0][0]) + " has already been submitted against " +cstr(self.doc.doctype)+ ". Please cancel Sales Invoice : "+ cstr(submit_rv[0][0]) + " first and then cancel "+ cstr(self.doc.doctype), raise_exception = 1) #check maintenance schedule submit_ms = sql("select t1.name from `tabMaintenance Schedule` t1, `tabMaintenance Schedule Item` t2 where t2.parent=t1.name and t2.prevdoc_docname = %s and t1.docstatus = 1",self.doc.name) if submit_ms: msgprint("Maintenance Schedule : " + cstr(submit_ms[0][0]) + " has already been submitted against " +cstr(self.doc.doctype)+ ". Please cancel Maintenance Schedule : "+ cstr(submit_ms[0][0]) + " first and then cancel "+ cstr(self.doc.doctype), raise_exception = 1) # check maintenance visit submit_mv = sql("select t1.name from `tabMaintenance Visit` t1, `tabMaintenance Visit Purpose` t2 where t2.parent=t1.name and t2.prevdoc_docname = %s and t1.docstatus = 1",self.doc.name) if submit_mv: msgprint("Maintenance Visit : " + cstr(submit_mv[0][0]) + " has already been submitted against " +cstr(self.doc.doctype)+ ". Please cancel Maintenance Visit : " + cstr(submit_mv[0][0]) + " first and then cancel "+ cstr(self.doc.doctype), raise_exception = 1) # check production order pro_order = sql("""select name from `tabProduction Order` where sales_order = %s and docstatus = 1""", self.doc.name) if pro_order: msgprint("""Production Order: %s exists against this sales order. Please cancel production order first and then cancel this sales order""" % pro_order[0][0], raise_exception=1)
def update_packing_list_item(self,obj, packing_item_code, qty, warehouse, line): bin = self.get_bin_qty(packing_item_code, warehouse) item = self.get_packing_item_details(packing_item_code) # check if exists exists = 0 for d in getlist(obj.doclist, 'packing_details'): if d.parent_item == line.item_code and d.item_code == packing_item_code and d.parent_detail_docname == line.name: pi, exists = d, 1 break if not exists: pi = addchild(obj.doc, 'packing_details', 'Delivery Note Packing Item', 1, obj.doclist) pi.parent_item = line.item_code pi.item_code = packing_item_code pi.item_name = item['item_name'] pi.parent_detail_docname = line.name pi.description = item['description'] pi.uom = item['stock_uom'] pi.qty = flt(qty) pi.actual_qty = bin and flt(bin['actual_qty']) or 0 pi.projected_qty = bin and flt(bin['projected_qty']) or 0 pi.warehouse = warehouse pi.prevdoc_doctype = line.prevdoc_doctype if packing_item_code == line.item_code: pi.serial_no = cstr(line.serial_no) pi.batch_no = cstr(line.batch_no) pi.idx = self.packing_list_idx # has to be saved, since this function is called on_update of delivery note pi.save() self.packing_list_idx += 1
def get_permissions(self,doctype): import webnotes.model.doctype doclist = webnotes.model.doctype.get(doctype).get_parent_doclist() ptype = [{ 'role': perm.role, 'permlevel': cint(perm.permlevel), 'read': cint(perm.read), 'write': cint(perm.write), 'create': cint(perm.create), 'cancel': cint(perm.cancel), 'submit': cint(perm.submit), 'amend': cint(perm.amend), 'match': perm.match } for perm in sorted(doclist, key=lambda d: [d.fields.get('permlevel'), d.fields.get('role')]) if perm.doctype=='DocPerm'] fl = ['', 'owner'] + [d.fieldname for d in doclist \ if d.doctype=='DocField' and ((d.fieldtype=='Link' \ and cstr(d.options)!='') or (d.fieldtype=='Select' and 'link:' in cstr(d.options).lower()))] return { 'perms':ptype, 'fields':fl, 'is_submittable': doclist[0].fields.get('is_submittable') }
def get_outstanding(self, args): args = eval(args) o_s = sql("select outstanding_amount from `tab%s` where name = '%s'" % (args['doctype'],args['docname'])) if args['doctype'] == 'Payable Voucher': return cstr({'debit': o_s and flt(o_s[0][0]) or 0}) if args['doctype'] == 'Receivable Voucher': return cstr({'credit': o_s and flt(o_s[0][0]) or 0})
def print_packing_slip(self): prev_pack='0' sno=0 html='' tot_nett_wt,tot_gross_wt=0,0 for d in getlist(self.doclist, 'delivery_note_details'): sno=sno+1 if sno!=1 and prev_pack!=d.pack_no:#Footer goes here html+='</table><table style="page-break-after:always" width="100%"><tr><td>CASE NO</td><td>'+cstr(d.pack_no)+'</td><td>NETT WT</td><td>'+cstr(tot_nett_wt)+'</td><td>CHECKED BY</td><td></td></tr><tr><td>SIZE</td><td></td><td>GROSS WT</td><td>'+cstr(tot_gross_wt)+'</td><td>PACKED BY</td><td></td></tr></table></div>' if prev_pack!=d.pack_no: #Prepare Header Here #Header code goes here html+='<div align="center">[HEADER GOES HERE]</div><div><center><h2>Packing Slip</h2></center></div> <table width="100%"><tr><td width="15%">Order No.</td><td width="35%">'+cstr(self.doc.sales_order_no)+'</td><td width="15%">Shipping Marks</td><td>'+cstr(d.shipping_mark)+'</td></tr></table>' html+='<table class="cust_tbl" width="100%"><tr><td>S.NO.</td><td>QUANTITY</td><td>CS.NO.</td><td>DESCRIPTION</td><td>WEIGHT</td><tr>' sno=0 tot_nett_wt,to_gross_wt=flt(d.pack_nett_wt),flt(d.pack_gross_wt) #Body code goes here html+='<tr><td>'+cstr(sno+1)+'</td><td>'+cstr(d.qty)+'</td><td>'+d.item_code+'</td><td>'+d.description+'</td><td>'+cstr(d.pack_nett_wt)+'</td></tr>' prev_pack=d.pack_no tot_nett_wt+=flt(d.pack_nett_wt) tot_gross_wt+=flt(d.pack_gross_wt) if html!='': html+='</table><table style="page-break-after:always" width="100%"><tr><td>CASE NO</td><td>'+cstr(d.pack_no)+'</td><td>NETT WT</td><td>'+cstr(tot_nett_wt)+'</td><td>CHECKED BY</td><td>'+cstr(self.doc.packing_checked_by)+'</td></tr><tr><td>SIZE</td><td>'+cstr(self.doc.pack_size)+'</td><td>GROSS WT</td><td>'+cstr(tot_gross_wt)+'</td><td>PACKED BY</td><td>'+cstr(self.doc.packed_by)+'</td></tr></table></div>' html+='</html>' self.doc.print_packing_slip=html
def check_modified_date(self): mod_db = sql("select modified from `tabPurchase Request` where name = '%s'" % self.doc.name) date_diff = sql("select TIMEDIFF('%s', '%s')" % ( mod_db[0][0],cstr(self.doc.modified))) if date_diff and date_diff[0][0]: msgprint(cstr(self.doc.doctype) +" => "+ cstr(self.doc.name) +" has been modified. Please Refresh. ") raise Exception
def get_fy_details(fy_start_date, fy_end_date): start_year = getdate(fy_start_date).year if start_year == getdate(fy_end_date).year: fy = cstr(start_year) else: fy = cstr(start_year) + '-' + cstr(start_year + 1) return fy
def validate(self): fl = {'is_manufactured_item' :'Allow Bill of Materials', 'is_sub_contracted_item':'Is Sub Contracted Item', 'is_purchase_item' :'Is Purchase Item', 'is_pro_applicable' :'Allow Production Order'} for d in fl: if cstr(self.doc.fields.get(d)) != 'Yes': self.check_for_active_boms(fl[d]) self.check_ref_rate_detail() self.fill_customer_code() self.check_item_tax() self.validate_barcode() self.check_non_asset_warehouse() if cstr(self.doc.is_manufactured_item) == "No": self.doc.is_pro_applicable = "No" if self.doc.is_pro_applicable == 'Yes' and self.doc.is_stock_item == 'No': msgprint("As Production Order can be made for this Item, then Is Stock Item Should be 'Yes' as we maintain it's stock. Refer Manufacturing and Inventory section.", raise_exception=1) if self.doc.has_serial_no == 'Yes' and self.doc.is_stock_item == 'No': msgprint("'Has Serial No' can not be 'Yes' for non-stock item", raise_exception=1) if self.doc.name: self.old_page_name = webnotes.conn.get_value('Item', self.doc.name, 'page_name')
def validate_po_pr(self, d): # check po / pr for qty and rates and currency and conversion rate # currency, import_rate must be equal to currency, import_rate of purchase order if d.purchase_order and not d.purchase_order in self.po_list: # currency currency = cstr(sql("select currency from `tabPurchase Order` where name = '%s'" % d.purchase_order)[0][0]) if not cstr(currency) == cstr(self.doc.currency): msgprint("Purchase Order: " + cstr(d.purchase_order) + " currency : " + cstr(currency) + " does not match with currency of current document.") raise Exception # import_rate rate = flt(sql('select import_rate from `tabPurchase Order Item` where item_code=%s and parent=%s and name = %s', (d.item_code, d.purchase_order, d.po_detail))[0][0]) if abs(rate - flt(d.import_rate)) > 1 and cint(get_defaults('maintain_same_rate')): msgprint("Import Rate for %s in the Purchase Order is %s. Rate must be same as Purchase Order Rate" % (d.item_code,rate)) raise Exception if d.purchase_receipt and not d.purchase_receipt in self.pr_list: # currency , conversion_rate data = sql("select currency, conversion_rate from `tabPurchase Receipt` where name = '%s'" % d.purchase_receipt, as_dict = 1) if not cstr(data[0]['currency']) == cstr(self.doc.currency): msgprint("Purchase Receipt: " + cstr(d.purchase_receipt) + " currency : " + cstr(data[0]['currency']) + " does not match with currency of current document.") raise Exception if not flt(data[0]['conversion_rate']) == flt(self.doc.conversion_rate): msgprint("Purchase Receipt: " + cstr(d.purchase_receipt) + " conversion_rate : " + cstr(data[0]['conversion_rate']) + " does not match with conversion_rate of current document.") raise Exception
def maindoc_field(self): ret = '' for fi in self.field_list: if fi[1] !='Select' or fi[1] !='Link' or fi[1] !='Table': ret += "\n" + cstr(self.doc.select_form) + ':' + fi[0] elif fi[1] =='Select': op = fi[2].split(':') if op[0] != 'link': ret += "\n" + cstr(self.doc.select_form) + ':' +fi[0] #child table field list for fi in self.field_list: if fi[1] == 'Table': flist=sql("select label from tabDocField where parent='%s' and fieldtype in ('Data', 'Select', 'Int','Currency','Float','Link')"%fi[2]) for x in flist: ret += "\n" + fi[2] + ':' + x[0] # linked doctype field list for fi in self.field_list: if fi[1] == 'Link': flist=sql("select label from tabDocField where parent='%s' and fieldtype in ('Data', 'Int', 'Select','Currency','Float','Link')"%fi[2]) for f in flist: ret += "\n" + fi[0] + ':' +f[0] elif fi[1] == 'Select': op = fi[2].split(':') if op[0] == 'link': flist=sql("select label from tabDocField where parent='%s' and fieldtype in ('Data', 'Select', 'Int','Currency','Float','Link')"%op[1]) for f in flist: ret += "\n" + fi[0] + ':' +f[0] return cstr(ret)
def activate_inactivate_bom(self, action): if cstr(action) == 'Activate': self.validate() set(self.doc, 'is_active', 'Yes') elif cstr(action) == 'Inactivate': self.check_active_parent_boms() set(self.doc, 'is_active', 'No')
def sle_for_moving_avg(self, row, previous_sle, change_in_qty, change_in_rate): """Insert Stock Ledger Entries for Moving Average valuation""" def _get_incoming_rate(qty, valuation_rate, previous_qty, previous_valuation_rate): if previous_valuation_rate == 0: return flt(valuation_rate) else: if valuation_rate == "": valuation_rate = previous_valuation_rate return (qty * valuation_rate - previous_qty * previous_valuation_rate) \ / flt(qty - previous_qty) if change_in_qty: # if change in qty, irrespective of change in rate incoming_rate = _get_incoming_rate(flt(row.qty), flt(row.valuation_rate), flt(previous_sle.get("qty_after_transaction")), flt(previous_sle.get("valuation_rate"))) row["voucher_detail_no"] = "Row: " + cstr(row.row_num) + "/Actual Entry" self.insert_entries({"actual_qty": change_in_qty, "incoming_rate": incoming_rate}, row) elif change_in_rate and flt(previous_sle.get("qty_after_transaction")) > 0: # if no change in qty, but change in rate # and positive actual stock before this reconciliation incoming_rate = _get_incoming_rate( flt(previous_sle.get("qty_after_transaction"))+1, flt(row.valuation_rate), flt(previous_sle.get("qty_after_transaction")), flt(previous_sle.get("valuation_rate"))) # +1 entry row["voucher_detail_no"] = "Row: " + cstr(row.row_num) + "/Valuation Adjustment +1" self.insert_entries({"actual_qty": 1, "incoming_rate": incoming_rate}, row) # -1 entry row["voucher_detail_no"] = "Row: " + cstr(row.row_num) + "/Valuation Adjustment -1" self.insert_entries({"actual_qty": -1}, row)
def check_stock_uom_with_bin(self): if not self.doc.fields.get("__islocal"): matched=True ref_uom = webnotes.conn.get_value("Stock Ledger Entry", {"item_code": self.doc.name, "is_cancelled": "No"}, "stock_uom") if ref_uom: if cstr(ref_uom) != cstr(self.doc.stock_uom): matched = False else: bin_list = webnotes.conn.sql("select * from tabBin where item_code=%s", self.doc.item_code, as_dict=1) for bin in bin_list: if (bin.reserved_qty > 0 or bin.ordered_qty > 0 or bin.indented_qty > 0 \ or bin.planned_qty > 0) and cstr(bin.stock_uom) != cstr(self.doc.stock_uom): matched = False break if matched and bin_list: webnotes.conn.sql("""update tabBin set stock_uom=%s where item_code=%s""", (self.doc.stock_uom, self.doc.name)) if not matched: webnotes.throw(_("Default Unit of Measure can not be changed directly \ because you have already made some transaction(s) with another UOM.\n \ To change default UOM, use 'UOM Replace Utility' tool under Stock module."))
def get_doj(self): ret_doj = sql("select employee_name,date_of_joining from `tabEmployee` where name = '%s'"%self.doc.employee) if ret_doj: set(self.doc, 'employee_name', cstr(ret_doj[0][0])) set(self.doc,'date_of_joining', ret_doj[0][1].strftime('%Y-%m-%d'))
def get_stock_uom(self, item_code): return { 'current_stock_uom': cstr(get_value('Item', item_code, 'stock_uom')) }
def validate_budget(self, acct, cost_center, actual, budget, action): # action if actual exceeds budget if flt(actual) > flt(budget): msgprint("Your monthly expense "+ cstr((action == 'stop') and "will exceed" or "has exceeded") +" budget for <b>Account - "+cstr(acct)+" </b> under <b>Cost Center - "+ cstr(cost_center) + "</b>"+cstr((action == 'Stop') and ", you can not have this transaction." or ".")) if action == 'Stop': raise Exception
def scrub_options_list(self, ol): options = filter(lambda x: x, [cstr(n.upper()).strip() for n in ol]) return options
def check_nextdoc_docstatus(self): # Checks Delivery Note submit_dn = webnotes.conn.sql( "select t1.name from `tabDelivery Note` t1,`tabDelivery Note Item` t2 where t1.name = t2.parent and t2.against_sales_order = %s and t1.docstatus = 1", self.doc.name) if submit_dn: msgprint("Delivery Note : " + cstr(submit_dn[0][0]) + " has been submitted against " + cstr(self.doc.doctype) + ". Please cancel Delivery Note : " + cstr(submit_dn[0][0]) + " first and then cancel " + cstr(self.doc.doctype), raise_exception=1) # Checks Sales Invoice submit_rv = webnotes.conn.sql( "select t1.name from `tabSales Invoice` t1,`tabSales Invoice Item` t2 where t1.name = t2.parent and t2.sales_order = '%s' and t1.docstatus = 1" % (self.doc.name)) if submit_rv: msgprint("Sales Invoice : " + cstr(submit_rv[0][0]) + " has already been submitted against " + cstr(self.doc.doctype) + ". Please cancel Sales Invoice : " + cstr(submit_rv[0][0]) + " first and then cancel " + cstr(self.doc.doctype), raise_exception=1) #check maintenance schedule submit_ms = webnotes.conn.sql( "select t1.name from `tabMaintenance Schedule` t1, `tabMaintenance Schedule Item` t2 where t2.parent=t1.name and t2.prevdoc_docname = %s and t1.docstatus = 1", self.doc.name) if submit_ms: msgprint("Maintenance Schedule : " + cstr(submit_ms[0][0]) + " has already been submitted against " + cstr(self.doc.doctype) + ". Please cancel Maintenance Schedule : " + cstr(submit_ms[0][0]) + " first and then cancel " + cstr(self.doc.doctype), raise_exception=1) # check maintenance visit submit_mv = webnotes.conn.sql( "select t1.name from `tabMaintenance Visit` t1, `tabMaintenance Visit Purpose` t2 where t2.parent=t1.name and t2.prevdoc_docname = %s and t1.docstatus = 1", self.doc.name) if submit_mv: msgprint("Maintenance Visit : " + cstr(submit_mv[0][0]) + " has already been submitted against " + cstr(self.doc.doctype) + ". Please cancel Maintenance Visit : " + cstr(submit_mv[0][0]) + " first and then cancel " + cstr(self.doc.doctype), raise_exception=1) # check production order pro_order = webnotes.conn.sql( """select name from `tabProduction Order` where sales_order = %s and docstatus = 1""", self.doc.name) if pro_order: msgprint("""Production Order: %s exists against this sales order. Please cancel production order first and then cancel this sales order""" % pro_order[0][0], raise_exception=1)