Compare commits
92 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
722b22a834 | ||
|
|
08e2105b09 | ||
|
|
11d565b07c | ||
|
|
a2c9d13f68 | ||
|
|
508542d4d9 | ||
|
|
50ff8471e0 | ||
|
|
78b8cdc3c1 | ||
|
|
2275cd15e6 | ||
|
|
b9376641af | ||
|
|
ee018b5ae1 | ||
|
|
acf85dffc5 | ||
|
|
660f3ed0d6 | ||
|
|
d5c83122f2 | ||
|
|
2777f23ace | ||
|
|
ae65172dca | ||
|
|
d261d40c7e | ||
|
|
4b231c2692 | ||
|
|
7e27e32e92 | ||
|
|
ed1b8cfe3f | ||
|
|
99d4ff4a29 | ||
|
|
595dbd6dea | ||
|
|
f979b18ddb | ||
|
|
3ef6e7847e | ||
|
|
2dba3b5e25 | ||
|
|
2cb8c6a867 | ||
|
|
be3aee973c | ||
|
|
c30c342bdf | ||
|
|
f02a0d4d24 | ||
|
|
cd6c00d505 | ||
|
|
e6cd228288 | ||
|
|
ec14c81ebd | ||
|
|
8793b823af | ||
|
|
537301a210 | ||
|
|
f1d8fc3d51 | ||
|
|
20b4666e89 | ||
|
|
84969bdb2d | ||
|
|
705384d8fe | ||
|
|
2123e02eda | ||
|
|
b77a1057ce | ||
|
|
93b1f2ad72 | ||
|
|
9a433ffca1 | ||
|
|
c1162796c5 | ||
|
|
82446bf83e | ||
|
|
c72f8976aa | ||
|
|
c49a3425ef | ||
|
|
50b2278eda | ||
|
|
e1d85f2467 | ||
|
|
3962cded76 | ||
|
|
66360f694e | ||
|
|
5dba950afa | ||
|
|
6a3f51bee2 | ||
|
|
efe1ab742f | ||
|
|
4d32d5301a | ||
|
|
58bc00f954 | ||
|
|
155074479b | ||
|
|
fa1775b6a6 | ||
|
|
764e6ef210 | ||
|
|
f2d89987f5 | ||
|
|
06c92a782a | ||
|
|
f43e49f378 | ||
|
|
ea5ad84c5e | ||
|
|
46f328cbda | ||
|
|
1b9a01b6c3 | ||
|
|
e8ab7b8898 | ||
|
|
ae921ce2c8 | ||
|
|
b77ad7c31d | ||
|
|
cc13a9f2f6 | ||
|
|
97c74f9f8f | ||
|
|
e1e6468b33 | ||
|
|
6620e2a494 | ||
|
|
08aadb853c | ||
|
|
3bb1a421f0 | ||
|
|
afc0bbc8ff | ||
|
|
8869430a81 | ||
|
|
7f031d1bfd | ||
|
|
5b1ebc5c54 | ||
|
|
5bb2f56b47 | ||
|
|
1e3e6865ce | ||
|
|
94542e104c | ||
|
|
90bf69aa52 | ||
|
|
3b8109780f | ||
|
|
f863055b91 | ||
|
|
3aac12d56b | ||
|
|
ed75667f64 | ||
|
|
16a0fef759 | ||
|
|
08aec855c4 | ||
|
|
e96b3ce725 | ||
|
|
60e9f84c8a | ||
|
|
1ffa76ba5c | ||
|
|
798f3897a3 | ||
|
|
e810ea3a2f | ||
|
|
29a8a93aa1 |
15
.travis.yml
@@ -1,4 +1,5 @@
|
|||||||
language: python
|
language: python
|
||||||
|
dist: trusty
|
||||||
|
|
||||||
python:
|
python:
|
||||||
- "2.7"
|
- "2.7"
|
||||||
@@ -11,10 +12,14 @@ before_install:
|
|||||||
- "sh -e /etc/init.d/xvfb start"
|
- "sh -e /etc/init.d/xvfb start"
|
||||||
|
|
||||||
install:
|
install:
|
||||||
- sudo apt-get purge -y mysql-common
|
- sudo apt-get purge -y mysql-common mysql-server mysql-client
|
||||||
- wget https://raw.githubusercontent.com/frappe/bench/master/install_scripts/setup_frappe.sh
|
# - wget https://raw.githubusercontent.com/frappe/bench/master/install_scripts/setup_frappe.sh
|
||||||
- sudo bash setup_frappe.sh --skip-setup-bench --mysql-root-password travis --bench-branch develop
|
# - sudo bash setup_frappe.sh --skip-setup-bench --mysql-root-password travis --bench-branch develop
|
||||||
- sudo pip install --upgrade pip
|
- wget https://raw.githubusercontent.com/frappe/bench/master/playbooks/install.py
|
||||||
|
- sudo python install.py --develop --user travis --without-bench-setup
|
||||||
|
- sudo pip install -e ~/bench
|
||||||
|
|
||||||
|
# - sudo pip install --upgrade pip
|
||||||
- rm $TRAVIS_BUILD_DIR/.git/shallow
|
- rm $TRAVIS_BUILD_DIR/.git/shallow
|
||||||
- bash $TRAVIS_BUILD_DIR/travis/bench_init.sh
|
- bash $TRAVIS_BUILD_DIR/travis/bench_init.sh
|
||||||
- cp -r $TRAVIS_BUILD_DIR/test_sites/test_site ~/frappe-bench/sites/
|
- cp -r $TRAVIS_BUILD_DIR/test_sites/test_site ~/frappe-bench/sites/
|
||||||
@@ -30,7 +35,7 @@ script:
|
|||||||
- bench --verbose run-tests --driver Firefox
|
- bench --verbose run-tests --driver Firefox
|
||||||
|
|
||||||
before_script:
|
before_script:
|
||||||
- mysql -e 'create database test_frappe'
|
- mysql -u root -ptravis -e 'create database test_frappe'
|
||||||
- echo "USE mysql;\nCREATE USER 'test_frappe'@'localhost' IDENTIFIED BY 'test_frappe';\nFLUSH PRIVILEGES;\n" | mysql -u root -ptravis
|
- echo "USE mysql;\nCREATE USER 'test_frappe'@'localhost' IDENTIFIED BY 'test_frappe';\nFLUSH PRIVILEGES;\n" | mysql -u root -ptravis
|
||||||
- echo "USE mysql;\nGRANT ALL PRIVILEGES ON \`test_frappe\`.* TO 'test_frappe'@'localhost';\n" | mysql -u root -ptravis
|
- echo "USE mysql;\nGRANT ALL PRIVILEGES ON \`test_frappe\`.* TO 'test_frappe'@'localhost';\n" | mysql -u root -ptravis
|
||||||
|
|
||||||
|
|||||||
@@ -2,7 +2,7 @@
|
|||||||
from __future__ import unicode_literals
|
from __future__ import unicode_literals
|
||||||
import frappe
|
import frappe
|
||||||
|
|
||||||
__version__ = '7.0.13'
|
__version__ = '7.0.23'
|
||||||
|
|
||||||
def get_default_company(user=None):
|
def get_default_company(user=None):
|
||||||
'''Get default company for user'''
|
'''Get default company for user'''
|
||||||
|
|||||||
@@ -772,6 +772,9 @@ def get_account_balance_and_party_type(account, date, company, debit=None, credi
|
|||||||
company_currency = get_company_currency(company)
|
company_currency = get_company_currency(company)
|
||||||
account_details = frappe.db.get_value("Account", account, ["account_type", "account_currency"], as_dict=1)
|
account_details = frappe.db.get_value("Account", account, ["account_type", "account_currency"], as_dict=1)
|
||||||
|
|
||||||
|
if not account_details:
|
||||||
|
return
|
||||||
|
|
||||||
if account_details.account_type == "Receivable":
|
if account_details.account_type == "Receivable":
|
||||||
party_type = "Customer"
|
party_type = "Customer"
|
||||||
elif account_details.account_type == "Payable":
|
elif account_details.account_type == "Payable":
|
||||||
|
|||||||
@@ -100,8 +100,8 @@ frappe.ui.form.on('Payment Entry', {
|
|||||||
frm.toggle_display("base_received_amount", (frm.doc.paid_to_account_currency != company_currency &&
|
frm.toggle_display("base_received_amount", (frm.doc.paid_to_account_currency != company_currency &&
|
||||||
frm.doc.paid_from_account_currency != frm.doc.paid_to_account_currency));
|
frm.doc.paid_from_account_currency != frm.doc.paid_to_account_currency));
|
||||||
|
|
||||||
frm.toggle_display("received_amount",
|
frm.toggle_display("received_amount", (frm.doc.payment_type=="Internal Transfer" ||
|
||||||
frm.doc.paid_from_account_currency != frm.doc.paid_to_account_currency)
|
frm.doc.paid_from_account_currency != frm.doc.paid_to_account_currency))
|
||||||
|
|
||||||
frm.toggle_display(["base_total_allocated_amount"],
|
frm.toggle_display(["base_total_allocated_amount"],
|
||||||
(frm.doc.paid_amount && frm.doc.received_amount && frm.doc.base_total_allocated_amount &&
|
(frm.doc.paid_amount && frm.doc.received_amount && frm.doc.base_total_allocated_amount &&
|
||||||
@@ -414,10 +414,7 @@ frappe.ui.form.on('Payment Entry', {
|
|||||||
|
|
||||||
paid_amount: function(frm) {
|
paid_amount: function(frm) {
|
||||||
frm.set_value("base_paid_amount", flt(frm.doc.paid_amount) * flt(frm.doc.source_exchange_rate));
|
frm.set_value("base_paid_amount", flt(frm.doc.paid_amount) * flt(frm.doc.source_exchange_rate));
|
||||||
|
|
||||||
frm.trigger("reset_received_amount");
|
frm.trigger("reset_received_amount");
|
||||||
|
|
||||||
frm.set_paid_amount_based_on_received_amount = false;
|
|
||||||
},
|
},
|
||||||
|
|
||||||
received_amount: function(frm) {
|
received_amount: function(frm) {
|
||||||
@@ -436,22 +433,19 @@ frappe.ui.form.on('Payment Entry', {
|
|||||||
frm.events.allocate_party_amount_against_ref_docs(frm, frm.doc.received_amount);
|
frm.events.allocate_party_amount_against_ref_docs(frm, frm.doc.received_amount);
|
||||||
else
|
else
|
||||||
frm.events.set_difference_amount(frm);
|
frm.events.set_difference_amount(frm);
|
||||||
|
|
||||||
|
frm.set_paid_amount_based_on_received_amount = false;
|
||||||
},
|
},
|
||||||
|
|
||||||
reset_received_amount: function(frm) {
|
reset_received_amount: function(frm) {
|
||||||
if(!frm.set_paid_amount_based_on_received_amount &&
|
if(!frm.set_paid_amount_based_on_received_amount &&
|
||||||
(frm.doc.paid_from_account_currency == frm.doc.paid_to_account_currency)) {
|
(frm.doc.paid_from_account_currency == frm.doc.paid_to_account_currency)) {
|
||||||
|
|
||||||
// var total_deductions = frappe.utils.sum($.map(frm.doc.deductions || [],
|
|
||||||
// function(d) { return d.amount}));
|
|
||||||
//
|
|
||||||
// var received_amount = frm.doc.paid_amount +
|
|
||||||
// flt(total_deductions) / flt(frm.doc.source_exchange_rate);
|
|
||||||
//
|
|
||||||
frm.set_value("received_amount", frm.doc.paid_amount);
|
frm.set_value("received_amount", frm.doc.paid_amount);
|
||||||
frm.set_value("target_exchange_rate", frm.doc.source_exchange_rate);
|
frm.set_value("target_exchange_rate", frm.doc.source_exchange_rate);
|
||||||
frm.set_value("base_received_amount", frm.doc.base_paid_amount);
|
frm.set_value("base_received_amount", frm.doc.base_paid_amount);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(frm.doc.payment_type == "Receive")
|
if(frm.doc.payment_type == "Receive")
|
||||||
frm.events.allocate_party_amount_against_ref_docs(frm, frm.doc.paid_amount);
|
frm.events.allocate_party_amount_against_ref_docs(frm, frm.doc.paid_amount);
|
||||||
else
|
else
|
||||||
@@ -608,10 +602,17 @@ frappe.ui.form.on('Payment Entry', {
|
|||||||
var party_amount = frm.doc.payment_type=="Receive" ?
|
var party_amount = frm.doc.payment_type=="Receive" ?
|
||||||
frm.doc.paid_amount : frm.doc.received_amount;
|
frm.doc.paid_amount : frm.doc.received_amount;
|
||||||
|
|
||||||
if(frm.doc.total_allocated_amount < party_amount)
|
var total_deductions = frappe.utils.sum($.map(frm.doc.deductions || [],
|
||||||
unallocated_amount = party_amount - frm.doc.total_allocated_amount;
|
function(d) { return flt(d.amount) }));
|
||||||
}
|
|
||||||
|
|
||||||
|
if(frm.doc.total_allocated_amount < party_amount) {
|
||||||
|
if(frm.doc.payment_type == "Receive") {
|
||||||
|
unallocated_amount = party_amount - (frm.doc.total_allocated_amount - total_deductions);
|
||||||
|
} else {
|
||||||
|
unallocated_amount = party_amount - (frm.doc.total_allocated_amount + total_deductions);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
frm.set_value("unallocated_amount", unallocated_amount);
|
frm.set_value("unallocated_amount", unallocated_amount);
|
||||||
|
|
||||||
var difference_amount = 0;
|
var difference_amount = 0;
|
||||||
|
|||||||
@@ -247,8 +247,13 @@ class PaymentEntry(AccountsController):
|
|||||||
if self.party:
|
if self.party:
|
||||||
party_amount = self.paid_amount if self.payment_type=="Receive" else self.received_amount
|
party_amount = self.paid_amount if self.payment_type=="Receive" else self.received_amount
|
||||||
|
|
||||||
|
total_deductions = sum([flt(d.amount) for d in self.get("deductions")])
|
||||||
|
|
||||||
if self.total_allocated_amount < party_amount:
|
if self.total_allocated_amount < party_amount:
|
||||||
self.unallocated_amount = party_amount - self.total_allocated_amount
|
if self.payment_type == "Receive":
|
||||||
|
self.unallocated_amount = party_amount - (self.total_allocated_amount - total_deductions)
|
||||||
|
else:
|
||||||
|
self.unallocated_amount = party_amount - (self.total_allocated_amount + total_deductions)
|
||||||
|
|
||||||
def set_difference_amount(self):
|
def set_difference_amount(self):
|
||||||
base_unallocated_amount = flt(self.unallocated_amount) * (flt(self.source_exchange_rate)
|
base_unallocated_amount = flt(self.unallocated_amount) * (flt(self.source_exchange_rate)
|
||||||
@@ -569,10 +574,9 @@ def get_company_defaults(company):
|
|||||||
@frappe.whitelist()
|
@frappe.whitelist()
|
||||||
def get_reference_details(reference_doctype, reference_name, party_account_currency):
|
def get_reference_details(reference_doctype, reference_name, party_account_currency):
|
||||||
total_amount = outstanding_amount = exchange_rate = None
|
total_amount = outstanding_amount = exchange_rate = None
|
||||||
|
|
||||||
if reference_doctype != "Journal Entry":
|
|
||||||
ref_doc = frappe.get_doc(reference_doctype, reference_name)
|
ref_doc = frappe.get_doc(reference_doctype, reference_name)
|
||||||
|
|
||||||
|
if reference_doctype != "Journal Entry":
|
||||||
if party_account_currency == ref_doc.company_currency:
|
if party_account_currency == ref_doc.company_currency:
|
||||||
total_amount = ref_doc.base_grand_total
|
total_amount = ref_doc.base_grand_total
|
||||||
exchange_rate = 1
|
exchange_rate = 1
|
||||||
|
|||||||
@@ -1,21 +1,37 @@
|
|||||||
// Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors
|
// Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors
|
||||||
// License: GNU General Public License v3. See license.txt
|
// License: GNU General Public License v3. See license.txt
|
||||||
|
|
||||||
|
frappe.ui.form.on('Period Closing Voucher', {
|
||||||
|
onload: function(frm) {
|
||||||
|
if (!frm.doc.transaction_date) frm.doc.transaction_date = dateutil.obj_to_str(new Date());
|
||||||
|
},
|
||||||
|
|
||||||
//========================== On Load =================================================
|
setup: function(frm) {
|
||||||
cur_frm.cscript.onload = function(doc, cdt, cdn) {
|
frm.set_query("closing_account_head", function() {
|
||||||
if (!doc.transaction_date) doc.transaction_date = dateutil.obj_to_str(new Date());
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// ***************** Get Account Head *****************
|
|
||||||
cur_frm.fields_dict['closing_account_head'].get_query = function(doc, cdt, cdn) {
|
|
||||||
return {
|
return {
|
||||||
filters: [
|
filters: [
|
||||||
['Account', 'company', '=', doc.company],
|
['Account', 'company', '=', frm.doc.company],
|
||||||
['Account', 'is_group', '=', '0'],
|
['Account', 'is_group', '=', '0'],
|
||||||
['Account', 'freeze_account', '=', 'No'],
|
['Account', 'freeze_account', '=', 'No'],
|
||||||
['Account', 'root_type', 'in', 'Liability, Equity']
|
['Account', 'root_type', 'in', 'Liability, Equity']
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
});
|
||||||
|
},
|
||||||
|
|
||||||
|
refresh: function(frm) {
|
||||||
|
if(frm.doc.docstatus==1) {
|
||||||
|
frm.add_custom_button(__('Ledger'), function() {
|
||||||
|
frappe.route_options = {
|
||||||
|
"voucher_no": frm.doc.name,
|
||||||
|
"from_date": frm.doc.posting_date,
|
||||||
|
"to_date": frm.doc.posting_date,
|
||||||
|
"company": frm.doc.company,
|
||||||
|
group_by_voucher: 0
|
||||||
|
};
|
||||||
|
frappe.set_route("query-report", "General Ledger");
|
||||||
|
}, "icon-table");
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
})
|
||||||
|
|||||||
@@ -55,9 +55,8 @@ class TestPeriodClosingVoucher(unittest.TestCase):
|
|||||||
if random_expense_account:
|
if random_expense_account:
|
||||||
# Check posted value for teh above random_expense_account
|
# Check posted value for teh above random_expense_account
|
||||||
gle_for_random_expense_account = frappe.db.sql("""
|
gle_for_random_expense_account = frappe.db.sql("""
|
||||||
select debit - credit as amount,
|
select sum(debit - credit) as amount,
|
||||||
debit_in_account_currency - credit_in_account_currency
|
sum(debit_in_account_currency - credit_in_account_currency) as amount_in_account_currency
|
||||||
as amount_in_account_currency
|
|
||||||
from `tabGL Entry`
|
from `tabGL Entry`
|
||||||
where voucher_type='Period Closing Voucher' and voucher_no=%s and account =%s""",
|
where voucher_type='Period Closing Voucher' and voucher_no=%s and account =%s""",
|
||||||
(pcv.name, random_expense_account[0].account), as_dict=True)
|
(pcv.name, random_expense_account[0].account), as_dict=True)
|
||||||
|
|||||||
@@ -8,6 +8,7 @@
|
|||||||
"custom": 0,
|
"custom": 0,
|
||||||
"docstatus": 0,
|
"docstatus": 0,
|
||||||
"doctype": "DocType",
|
"doctype": "DocType",
|
||||||
|
"editable_grid": 0,
|
||||||
"fields": [
|
"fields": [
|
||||||
{
|
{
|
||||||
"allow_on_submit": 0,
|
"allow_on_submit": 0,
|
||||||
@@ -832,7 +833,7 @@
|
|||||||
"issingle": 0,
|
"issingle": 0,
|
||||||
"istable": 0,
|
"istable": 0,
|
||||||
"max_attachments": 0,
|
"max_attachments": 0,
|
||||||
"modified": "2016-06-13 21:20:13.805101",
|
"modified": "2016-08-06 17:05:59.990031",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "Accounts",
|
"module": "Accounts",
|
||||||
"name": "POS Profile",
|
"name": "POS Profile",
|
||||||
@@ -879,7 +880,7 @@
|
|||||||
"write": 0
|
"write": 0
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"quick_entry": 1,
|
"quick_entry": 0,
|
||||||
"read_only": 0,
|
"read_only": 0,
|
||||||
"read_only_onload": 0,
|
"read_only_onload": 0,
|
||||||
"sort_field": "modified",
|
"sort_field": "modified",
|
||||||
|
|||||||
@@ -301,7 +301,7 @@ class PurchaseInvoice(BuyingController):
|
|||||||
asset.flags.ignore_validate_update_after_submit = True
|
asset.flags.ignore_validate_update_after_submit = True
|
||||||
asset.save()
|
asset.save()
|
||||||
|
|
||||||
def make_gl_entries(self, repost_future_gle=False):
|
def make_gl_entries(self, repost_future_gle=True):
|
||||||
self.auto_accounting_for_stock = \
|
self.auto_accounting_for_stock = \
|
||||||
cint(frappe.defaults.get_global_default("auto_accounting_for_stock"))
|
cint(frappe.defaults.get_global_default("auto_accounting_for_stock"))
|
||||||
|
|
||||||
|
|||||||
@@ -91,7 +91,7 @@ def update_multi_mode_option(doc, pos_profile):
|
|||||||
|
|
||||||
def get_mode_of_payment(doc):
|
def get_mode_of_payment(doc):
|
||||||
return frappe.db.sql(""" select mpa.default_account, mpa.parent, mp.type as type from `tabMode of Payment Account` mpa,
|
return frappe.db.sql(""" select mpa.default_account, mpa.parent, mp.type as type from `tabMode of Payment Account` mpa,
|
||||||
`tabMode of Payment` mp where mpa.parent = mp.name and company = %(company)s""", {'company': doc.company}, as_dict=1)
|
`tabMode of Payment` mp where mpa.parent = mp.name and mpa.company = %(company)s""", {'company': doc.company}, as_dict=1)
|
||||||
|
|
||||||
def update_tax_table(doc):
|
def update_tax_table(doc):
|
||||||
taxes = get_taxes_and_charges('Sales Taxes and Charges Template', doc.taxes_and_charges)
|
taxes = get_taxes_and_charges('Sales Taxes and Charges Template', doc.taxes_and_charges)
|
||||||
@@ -108,13 +108,14 @@ def get_items(doc, pos_profile):
|
|||||||
|
|
||||||
item.price_list_rate = frappe.db.get_value('Item Price', {'item_code': item.name,
|
item.price_list_rate = frappe.db.get_value('Item Price', {'item_code': item.name,
|
||||||
'price_list': doc.selling_price_list}, 'price_list_rate') or 0
|
'price_list': doc.selling_price_list}, 'price_list_rate') or 0
|
||||||
item.default_warehouse = pos_profile.get('warehouse') or item.default_warehouse or None
|
item.default_warehouse = pos_profile.get('warehouse') or \
|
||||||
|
get_item_warehouse_for_company(doc.company, item.default_warehouse) or None
|
||||||
item.expense_account = pos_profile.get('expense_account') or item.expense_account
|
item.expense_account = pos_profile.get('expense_account') or item.expense_account
|
||||||
item.income_account = pos_profile.get('income_account') or item_doc.income_account
|
item.income_account = pos_profile.get('income_account') or item_doc.income_account
|
||||||
item.cost_center = pos_profile.get('cost_center') or item_doc.selling_cost_center
|
item.cost_center = pos_profile.get('cost_center') or item_doc.selling_cost_center
|
||||||
item.actual_qty = frappe.db.get_value('Bin', {'item_code': item.name,
|
item.actual_qty = frappe.db.get_value('Bin', {'item_code': item.name,
|
||||||
'warehouse': item.default_warehouse}, 'actual_qty') or 0
|
'warehouse': item.default_warehouse}, 'actual_qty') or 0
|
||||||
item.serial_nos = get_serial_nos(item, pos_profile)
|
item.serial_nos = get_serial_nos(item, pos_profile, doc.company)
|
||||||
item.batch_nos = frappe.db.sql_list("""select name from `tabBatch` where ifnull(expiry_date, '4000-10-10') > curdate()
|
item.batch_nos = frappe.db.sql_list("""select name from `tabBatch` where ifnull(expiry_date, '4000-10-10') > curdate()
|
||||||
and item = %(item_code)s""", {'item_code': item.item_code})
|
and item = %(item_code)s""", {'item_code': item.item_code})
|
||||||
|
|
||||||
@@ -122,13 +123,19 @@ def get_items(doc, pos_profile):
|
|||||||
|
|
||||||
return item_list
|
return item_list
|
||||||
|
|
||||||
def get_serial_nos(item, pos_profile):
|
def get_item_warehouse_for_company(company, warehouse):
|
||||||
|
if frappe.db.get_value('Warehouse', warehouse, 'company') != company:
|
||||||
|
warehouse = None
|
||||||
|
return warehouse
|
||||||
|
|
||||||
|
def get_serial_nos(item, pos_profile, company):
|
||||||
cond = "1=1"
|
cond = "1=1"
|
||||||
if pos_profile.get('update_stock') and pos_profile.get('warehouse'):
|
if pos_profile.get('update_stock') and pos_profile.get('warehouse'):
|
||||||
cond = "warehouse = '{0}'".format(pos_profile.get('warehouse'))
|
cond = "warehouse = '{0}'".format(pos_profile.get('warehouse'))
|
||||||
|
|
||||||
serial_nos = frappe.db.sql("""select name, warehouse from `tabSerial No` where {0}
|
serial_nos = frappe.db.sql("""select name, warehouse from `tabSerial No` where {0}
|
||||||
and item_code = %(item_code)s""".format(cond), {'item_code': item.item_code}, as_dict=1)
|
and item_code = %(item_code)s and company = %(company)s
|
||||||
|
""".format(cond), {'item_code': item.item_code, 'company': company}, as_dict=1)
|
||||||
|
|
||||||
serial_no_list = {}
|
serial_no_list = {}
|
||||||
for serial_no in serial_nos:
|
for serial_no in serial_nos:
|
||||||
@@ -214,9 +221,9 @@ def submit_invoice(si_doc, name):
|
|||||||
save_invoice(e, si_doc, name)
|
save_invoice(e, si_doc, name)
|
||||||
|
|
||||||
def save_invoice(e, si_doc, name):
|
def save_invoice(e, si_doc, name):
|
||||||
si_doc.docstatus = 0
|
if not frappe.db.exists('Sales Invoice', {'offline_pos_name': name}):
|
||||||
si_doc.name = ''
|
si_doc.flags.ignore_mandatory = True
|
||||||
si_doc.save(ignore_permissions=True)
|
si_doc.insert()
|
||||||
make_scheduler_log(e, si_doc.name)
|
make_scheduler_log(e, si_doc.name)
|
||||||
|
|
||||||
def make_scheduler_log(e, sales_invoice):
|
def make_scheduler_log(e, sales_invoice):
|
||||||
|
|||||||
@@ -10,6 +10,7 @@
|
|||||||
"docstatus": 0,
|
"docstatus": 0,
|
||||||
"doctype": "DocType",
|
"doctype": "DocType",
|
||||||
"document_type": "",
|
"document_type": "",
|
||||||
|
"editable_grid": 0,
|
||||||
"fields": [
|
"fields": [
|
||||||
{
|
{
|
||||||
"allow_on_submit": 0,
|
"allow_on_submit": 0,
|
||||||
@@ -1135,7 +1136,7 @@
|
|||||||
"no_copy": 0,
|
"no_copy": 0,
|
||||||
"permlevel": 0,
|
"permlevel": 0,
|
||||||
"precision": "2",
|
"precision": "2",
|
||||||
"print_hide": 0,
|
"print_hide": 1,
|
||||||
"print_hide_if_no_value": 0,
|
"print_hide_if_no_value": 0,
|
||||||
"read_only": 1,
|
"read_only": 1,
|
||||||
"report_hide": 0,
|
"report_hide": 0,
|
||||||
@@ -3676,7 +3677,7 @@
|
|||||||
"istable": 0,
|
"istable": 0,
|
||||||
"max_attachments": 0,
|
"max_attachments": 0,
|
||||||
"menu_index": 0,
|
"menu_index": 0,
|
||||||
"modified": "2016-07-07 13:40:27.977803",
|
"modified": "2016-08-03 11:50:49.680278",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "Accounts",
|
"module": "Accounts",
|
||||||
"name": "Sales Invoice",
|
"name": "Sales Invoice",
|
||||||
|
|||||||
@@ -87,15 +87,6 @@ class SalesInvoice(SellingController):
|
|||||||
def before_save(self):
|
def before_save(self):
|
||||||
set_account_for_mode_of_payment(self)
|
set_account_for_mode_of_payment(self)
|
||||||
|
|
||||||
def update_change_amount(self):
|
|
||||||
self.base_paid_amount = 0.0
|
|
||||||
if self.paid_amount:
|
|
||||||
self.base_paid_amount = flt(self.paid_amount * self.conversion_rate, self.precision("base_paid_amount"))
|
|
||||||
self.change_amount = self.base_change_amount = 0.0
|
|
||||||
if self.paid_amount > self.grand_total:
|
|
||||||
self.change_amount = flt(self.paid_amount - self.grand_total, self.precision("change_amount"))
|
|
||||||
self.base_change_amount = flt(self.change_amount * self.conversion_rate, self.precision("base_change_amount"))
|
|
||||||
|
|
||||||
def on_submit(self):
|
def on_submit(self):
|
||||||
if not self.recurring_id:
|
if not self.recurring_id:
|
||||||
frappe.get_doc('Authorization Control').validate_approving_authority(self.doctype,
|
frappe.get_doc('Authorization Control').validate_approving_authority(self.doctype,
|
||||||
@@ -110,6 +101,7 @@ class SalesInvoice(SellingController):
|
|||||||
self.update_status_updater_args()
|
self.update_status_updater_args()
|
||||||
self.update_prevdoc_status()
|
self.update_prevdoc_status()
|
||||||
self.update_billing_status_in_dn()
|
self.update_billing_status_in_dn()
|
||||||
|
self.clear_unallocated_mode_of_payments()
|
||||||
|
|
||||||
# Updating stock ledger should always be called after updating prevdoc status,
|
# Updating stock ledger should always be called after updating prevdoc status,
|
||||||
# because updating reserved qty in bin depends upon updated delivered qty in SO
|
# because updating reserved qty in bin depends upon updated delivered qty in SO
|
||||||
@@ -297,6 +289,12 @@ class SalesInvoice(SellingController):
|
|||||||
|
|
||||||
self.party_account_currency = account.account_currency
|
self.party_account_currency = account.account_currency
|
||||||
|
|
||||||
|
def clear_unallocated_mode_of_payments(self):
|
||||||
|
self.set("payments", self.get("payments", {"amount": ["not in", [0, None, ""]]}))
|
||||||
|
|
||||||
|
frappe.db.sql("""delete from `tabSales Invoice Payment` where parent = %s
|
||||||
|
and amount = 0""", self.name)
|
||||||
|
|
||||||
def validate_with_previous_doc(self):
|
def validate_with_previous_doc(self):
|
||||||
super(SalesInvoice, self).validate_with_previous_doc({
|
super(SalesInvoice, self).validate_with_previous_doc({
|
||||||
"Sales Order": {
|
"Sales Order": {
|
||||||
@@ -504,6 +502,7 @@ class SalesInvoice(SellingController):
|
|||||||
gl_entries = merge_similar_entries(gl_entries)
|
gl_entries = merge_similar_entries(gl_entries)
|
||||||
|
|
||||||
self.make_pos_gl_entries(gl_entries)
|
self.make_pos_gl_entries(gl_entries)
|
||||||
|
self.make_gle_for_change(gl_entries)
|
||||||
|
|
||||||
self.make_write_off_gl_entry(gl_entries)
|
self.make_write_off_gl_entry(gl_entries)
|
||||||
|
|
||||||
@@ -578,27 +577,24 @@ class SalesInvoice(SellingController):
|
|||||||
|
|
||||||
def make_pos_gl_entries(self, gl_entries):
|
def make_pos_gl_entries(self, gl_entries):
|
||||||
if cint(self.is_pos) and self.paid_amount:
|
if cint(self.is_pos) and self.paid_amount:
|
||||||
|
for payment_mode in self.payments:
|
||||||
|
if payment_mode.base_amount > 0:
|
||||||
# POS, make payment entries
|
# POS, make payment entries
|
||||||
gl_entries.append(
|
gl_entries.append(
|
||||||
self.get_gl_dict({
|
self.get_gl_dict({
|
||||||
"account": self.debit_to,
|
"account": self.debit_to,
|
||||||
"party_type": "Customer",
|
"party_type": "Customer",
|
||||||
"party": self.customer,
|
"party": self.customer,
|
||||||
"against": self.cash_bank_account,
|
"against": payment_mode.account,
|
||||||
"credit": flt(self.base_paid_amount - self.base_change_amount),
|
"credit": payment_mode.base_amount,
|
||||||
"credit_in_account_currency": flt(self.base_paid_amount - self.base_change_amount) \
|
"credit_in_account_currency": payment_mode.base_amount \
|
||||||
if self.party_account_currency==self.company_currency else flt(self.paid_amount - self.change_amount),
|
if self.party_account_currency==self.company_currency \
|
||||||
|
else payment_mode.amount,
|
||||||
"against_voucher": self.return_against if cint(self.is_return) else self.name,
|
"against_voucher": self.return_against if cint(self.is_return) else self.name,
|
||||||
"against_voucher_type": self.doctype,
|
"against_voucher_type": self.doctype,
|
||||||
}, self.party_account_currency)
|
}, self.party_account_currency)
|
||||||
)
|
)
|
||||||
|
|
||||||
cash_account = ''
|
|
||||||
for payment_mode in self.payments:
|
|
||||||
if payment_mode.type == 'Cash':
|
|
||||||
cash_account = payment_mode.account
|
|
||||||
|
|
||||||
if payment_mode.base_amount > 0:
|
|
||||||
payment_mode_account_currency = get_account_currency(payment_mode.account)
|
payment_mode_account_currency = get_account_currency(payment_mode.account)
|
||||||
gl_entries.append(
|
gl_entries.append(
|
||||||
self.get_gl_dict({
|
self.get_gl_dict({
|
||||||
@@ -610,19 +606,43 @@ class SalesInvoice(SellingController):
|
|||||||
}, payment_mode_account_currency)
|
}, payment_mode_account_currency)
|
||||||
)
|
)
|
||||||
|
|
||||||
if self.change_amount:
|
def make_gle_for_change(self, gl_entries):
|
||||||
cash_account = cash_account or self.payments[0].account
|
if cint(self.is_pos) and self.change_amount:
|
||||||
cash_account_currency = get_account_currency(cash_account)
|
cash_account = self.get_cash_account()
|
||||||
|
if cash_account:
|
||||||
|
gl_entries.append(
|
||||||
|
self.get_gl_dict({
|
||||||
|
"account": self.debit_to,
|
||||||
|
"party_type": "Customer",
|
||||||
|
"party": self.customer,
|
||||||
|
"against": cash_account,
|
||||||
|
"debit": flt(self.base_change_amount),
|
||||||
|
"debit_in_account_currency": flt(self.base_change_amount) \
|
||||||
|
if self.party_account_currency==self.company_currency else flt(self.change_amount),
|
||||||
|
"against_voucher": self.return_against if cint(self.is_return) else self.name,
|
||||||
|
"against_voucher_type": self.doctype
|
||||||
|
}, self.party_account_currency)
|
||||||
|
)
|
||||||
|
|
||||||
gl_entries.append(
|
gl_entries.append(
|
||||||
self.get_gl_dict({
|
self.get_gl_dict({
|
||||||
"account": cash_account,
|
"account": cash_account,
|
||||||
"against": self.customer,
|
"against": self.customer,
|
||||||
"credit": self.base_change_amount,
|
"credit": self.base_change_amount
|
||||||
"credit_in_account_currency": self.base_change_amount \
|
})
|
||||||
if payment_mode_account_currency==self.company_currency else self.change_amount
|
|
||||||
}, payment_mode_account_currency)
|
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def get_cash_account(self):
|
||||||
|
cash_account = [d.account for d in self.payments if d.type=="Cash"]
|
||||||
|
if cash_account:
|
||||||
|
cash_account = cash_account[0]
|
||||||
|
else:
|
||||||
|
cash_account = frappe.db.get_value("Account",
|
||||||
|
filters={"company": self.company, "account_type": "Cash", "is_group": 0})
|
||||||
|
|
||||||
|
return cash_account
|
||||||
|
|
||||||
def make_write_off_gl_entry(self, gl_entries):
|
def make_write_off_gl_entry(self, gl_entries):
|
||||||
# write off entries, applicable if only pos
|
# write off entries, applicable if only pos
|
||||||
if self.write_off_account and self.write_off_amount:
|
if self.write_off_account and self.write_off_amount:
|
||||||
|
|||||||
@@ -503,7 +503,8 @@ class TestSalesInvoice(unittest.TestCase):
|
|||||||
[pos["taxes"][1]["account_head"], 0.0, 50.0],
|
[pos["taxes"][1]["account_head"], 0.0, 50.0],
|
||||||
[stock_in_hand, 0.0, abs(sle.stock_value_difference)],
|
[stock_in_hand, 0.0, abs(sle.stock_value_difference)],
|
||||||
[pos["items"][0]["expense_account"], abs(sle.stock_value_difference), 0.0],
|
[pos["items"][0]["expense_account"], abs(sle.stock_value_difference), 0.0],
|
||||||
[si.debit_to, 0.0, si.paid_amount],
|
[si.debit_to, 0.0, 300.0],
|
||||||
|
[si.debit_to, 0.0, cash_amount],
|
||||||
["_Test Bank - _TC", 300.0, 0.0],
|
["_Test Bank - _TC", 300.0, 0.0],
|
||||||
["Cash - _TC", cash_amount, 0.0]
|
["Cash - _TC", cash_amount, 0.0]
|
||||||
])
|
])
|
||||||
|
|||||||
@@ -177,6 +177,7 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
|
|||||||
doc = JSON.parse(localStorage.getItem('doc'))
|
doc = JSON.parse(localStorage.getItem('doc'))
|
||||||
if(this.frm.doc.payments.length == 0){
|
if(this.frm.doc.payments.length == 0){
|
||||||
this.frm.doc.payments = doc.payments;
|
this.frm.doc.payments = doc.payments;
|
||||||
|
this.calculate_outstanding_amount();
|
||||||
}
|
}
|
||||||
|
|
||||||
if(this.frm.doc.customer){
|
if(this.frm.doc.customer){
|
||||||
@@ -869,6 +870,7 @@ erpnext.pos.PointOfSale = erpnext.taxes_and_totals.extend({
|
|||||||
for(key in data){
|
for(key in data){
|
||||||
if(data[key].docstatus == 1 && index < 50){
|
if(data[key].docstatus == 1 && index < 50){
|
||||||
index++
|
index++
|
||||||
|
data[key].docstatus = 0;
|
||||||
return data
|
return data
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -52,10 +52,10 @@ class ReceivablePayableReport(object):
|
|||||||
if not "range3" in self.filters:
|
if not "range3" in self.filters:
|
||||||
self.filters["range3"] = "90"
|
self.filters["range3"] = "90"
|
||||||
|
|
||||||
for label in ("0-{range1}".format(**self.filters),
|
for label in ("0-{range1}".format(range1=self.filters["range1"]),
|
||||||
"{range1}-{range2}".format(**self.filters),
|
"{range1}-{range2}".format(range1=self.filters["range1"]+1, range2=self.filters["range2"]),
|
||||||
"{range2}-{range3}".format(**self.filters),
|
"{range2}-{range3}".format(range2=self.filters["range2"]+1, range3=self.filters["range3"]),
|
||||||
"{range3}-{above}".format(range3=self.filters.range3, above=_("Above"))):
|
"{range3}-{above}".format(range3=self.filters["range3"] + 1, above=_("Above"))):
|
||||||
columns.append({
|
columns.append({
|
||||||
"label": label,
|
"label": label,
|
||||||
"fieldtype": "Currency",
|
"fieldtype": "Currency",
|
||||||
|
|||||||
@@ -30,7 +30,7 @@ frappe.ui.form.on("Request for Quotation",{
|
|||||||
},
|
},
|
||||||
|
|
||||||
onload: function(frm) {
|
onload: function(frm) {
|
||||||
frm.add_fetch('standard_reply', 'response', 'response');
|
frm.add_fetch('standard_reply', 'response', 'message_for_supplier');
|
||||||
|
|
||||||
if(!frm.doc.message_for_supplier) {
|
if(!frm.doc.message_for_supplier) {
|
||||||
frm.set_value("message_for_supplier", __("Please supply the specified items at the best possible rates"))
|
frm.set_value("message_for_supplier", __("Please supply the specified items at the best possible rates"))
|
||||||
|
|||||||
@@ -9,6 +9,7 @@
|
|||||||
"docstatus": 0,
|
"docstatus": 0,
|
||||||
"doctype": "DocType",
|
"doctype": "DocType",
|
||||||
"document_type": "Document",
|
"document_type": "Document",
|
||||||
|
"editable_grid": 0,
|
||||||
"fields": [
|
"fields": [
|
||||||
{
|
{
|
||||||
"allow_on_submit": 0,
|
"allow_on_submit": 0,
|
||||||
@@ -296,7 +297,7 @@
|
|||||||
"options": "Standard Reply",
|
"options": "Standard Reply",
|
||||||
"permlevel": 0,
|
"permlevel": 0,
|
||||||
"precision": "",
|
"precision": "",
|
||||||
"print_hide": 0,
|
"print_hide": 1,
|
||||||
"print_hide_if_no_value": 0,
|
"print_hide_if_no_value": 0,
|
||||||
"read_only": 0,
|
"read_only": 0,
|
||||||
"report_hide": 0,
|
"report_hide": 0,
|
||||||
@@ -638,7 +639,7 @@
|
|||||||
"issingle": 0,
|
"issingle": 0,
|
||||||
"istable": 0,
|
"istable": 0,
|
||||||
"max_attachments": 0,
|
"max_attachments": 0,
|
||||||
"modified": "2016-06-30 01:57:49.233065",
|
"modified": "2016-08-01 08:45:39.777405",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "Buying",
|
"module": "Buying",
|
||||||
"name": "Request for Quotation",
|
"name": "Request for Quotation",
|
||||||
|
|||||||
@@ -26,6 +26,12 @@ def get_data():
|
|||||||
"name": "Payment Entry",
|
"name": "Payment Entry",
|
||||||
"description": _("Bank/Cash transactions against party or for internal transfer")
|
"description": _("Bank/Cash transactions against party or for internal transfer")
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"type": "page",
|
||||||
|
"name": "pos",
|
||||||
|
"label": _("POS"),
|
||||||
|
"description": _("Point of Sale")
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"type": "report",
|
"type": "report",
|
||||||
"name": "Accounts Receivable",
|
"name": "Accounts Receivable",
|
||||||
|
|||||||
@@ -229,12 +229,12 @@ def get_data():
|
|||||||
"type": "list"
|
"type": "list"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"module_name": "Examination",
|
"module_name": "Assessment",
|
||||||
"color": "#8a70be",
|
"color": "#8a70be",
|
||||||
"icon": "icon-file-text-alt",
|
"icon": "icon-file-text-alt",
|
||||||
"label": _("Examination"),
|
"label": _("Assessment"),
|
||||||
"link": "List/Examination",
|
"link": "List/Assessment",
|
||||||
"_doctype": "Examination",
|
"_doctype": "Assessment",
|
||||||
"type": "list"
|
"type": "list"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@@ -261,7 +261,7 @@ def get_data():
|
|||||||
"icon": "icon-map-marker",
|
"icon": "icon-map-marker",
|
||||||
"label": _("Room"),
|
"label": _("Room"),
|
||||||
"link": "List/Room",
|
"link": "List/Room",
|
||||||
"_doctype": "Examination",
|
"_doctype": "Room",
|
||||||
"type": "list"
|
"type": "list"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ You can create Custom Form, Fields, Scripts and can also create your own Apps
|
|||||||
to extend ERPNext functionality.
|
to extend ERPNext functionality.
|
||||||
|
|
||||||
ERPNext is Open Source under the GNU General Public Licence v3 and has been
|
ERPNext is Open Source under the GNU General Public Licence v3 and has been
|
||||||
listed as one of the Best Open Source Softwares in the world by my online
|
listed as one of the Best Open Source Softwares in the world by many online
|
||||||
blogs."""
|
blogs."""
|
||||||
|
|
||||||
docs_version = "6.x.x"
|
docs_version = "6.x.x"
|
||||||
|
|||||||
@@ -61,7 +61,11 @@ def get_data():
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
"type": "doctype",
|
"type": "doctype",
|
||||||
"name": "Examination"
|
"name": "Assessment"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"type": "doctype",
|
||||||
|
"name": "Assessment Group"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"type": "doctype",
|
"type": "doctype",
|
||||||
|
|||||||
@@ -38,6 +38,7 @@ class StockController(AccountsController):
|
|||||||
|
|
||||||
gl_list = []
|
gl_list = []
|
||||||
warehouse_with_no_account = []
|
warehouse_with_no_account = []
|
||||||
|
|
||||||
for detail in voucher_details:
|
for detail in voucher_details:
|
||||||
sle_list = sle_map.get(detail.name)
|
sle_list = sle_map.get(detail.name)
|
||||||
if sle_list:
|
if sle_list:
|
||||||
@@ -266,8 +267,7 @@ def update_gl_entries_after(posting_date, posting_time, for_warehouses=None, for
|
|||||||
voucher_obj = frappe.get_doc(voucher_type, voucher_no)
|
voucher_obj = frappe.get_doc(voucher_type, voucher_no)
|
||||||
expected_gle = voucher_obj.get_gl_entries(warehouse_account)
|
expected_gle = voucher_obj.get_gl_entries(warehouse_account)
|
||||||
if expected_gle:
|
if expected_gle:
|
||||||
if not existing_gle or not compare_existing_and_expected_gle(existing_gle,
|
if not existing_gle or not compare_existing_and_expected_gle(existing_gle, expected_gle):
|
||||||
expected_gle):
|
|
||||||
_delete_gl_entries(voucher_type, voucher_no)
|
_delete_gl_entries(voucher_type, voucher_no)
|
||||||
voucher_obj.make_gl_entries(repost_future_gle=False)
|
voucher_obj.make_gl_entries(repost_future_gle=False)
|
||||||
else:
|
else:
|
||||||
|
|||||||
@@ -440,11 +440,10 @@ class calculate_taxes_and_totals(object):
|
|||||||
paid_amount = self.doc.paid_amount \
|
paid_amount = self.doc.paid_amount \
|
||||||
if self.doc.party_account_currency == self.doc.currency else self.doc.base_paid_amount
|
if self.doc.party_account_currency == self.doc.currency else self.doc.base_paid_amount
|
||||||
|
|
||||||
self.doc.outstanding_amount = 0
|
self.calculate_change_amount()
|
||||||
if total_amount_to_pay > paid_amount:
|
|
||||||
self.doc.outstanding_amount = flt(total_amount_to_pay - flt(paid_amount),
|
self.doc.outstanding_amount = flt(total_amount_to_pay - flt(paid_amount) +
|
||||||
self.doc.precision("outstanding_amount"))
|
flt(self.doc.change_amount), self.doc.precision("outstanding_amount"))
|
||||||
self.change_amount()
|
|
||||||
|
|
||||||
elif self.doc.doctype == "Purchase Invoice":
|
elif self.doc.doctype == "Purchase Invoice":
|
||||||
self.doc.outstanding_amount = flt(total_amount_to_pay, self.doc.precision("outstanding_amount"))
|
self.doc.outstanding_amount = flt(total_amount_to_pay, self.doc.precision("outstanding_amount"))
|
||||||
@@ -452,6 +451,7 @@ class calculate_taxes_and_totals(object):
|
|||||||
def calculate_paid_amount(self):
|
def calculate_paid_amount(self):
|
||||||
paid_amount = base_paid_amount = 0.0
|
paid_amount = base_paid_amount = 0.0
|
||||||
for payment in self.doc.get('payments'):
|
for payment in self.doc.get('payments'):
|
||||||
|
if flt(payment.amount) > 0:
|
||||||
payment.base_amount = flt(payment.amount * self.doc.conversion_rate)
|
payment.base_amount = flt(payment.amount * self.doc.conversion_rate)
|
||||||
paid_amount += payment.amount
|
paid_amount += payment.amount
|
||||||
base_paid_amount += payment.base_amount
|
base_paid_amount += payment.base_amount
|
||||||
@@ -459,14 +459,13 @@ class calculate_taxes_and_totals(object):
|
|||||||
self.doc.paid_amount = flt(paid_amount, self.doc.precision("paid_amount"))
|
self.doc.paid_amount = flt(paid_amount, self.doc.precision("paid_amount"))
|
||||||
self.doc.base_paid_amount = flt(base_paid_amount, self.doc.precision("base_paid_amount"))
|
self.doc.base_paid_amount = flt(base_paid_amount, self.doc.precision("base_paid_amount"))
|
||||||
|
|
||||||
def change_amount(self):
|
def calculate_change_amount(self):
|
||||||
change_amount = 0.0
|
self.doc.change_amount = 0.0
|
||||||
if self.doc.paid_amount > self.doc.grand_total:
|
if self.doc.paid_amount > self.doc.grand_total:
|
||||||
change_amount = flt(self.doc.paid_amount - self.doc.grand_total,
|
self.doc.change_amount = flt(self.doc.paid_amount - self.doc.grand_total +
|
||||||
self.doc.precision("change_amount"))
|
self.doc.write_off_amount, self.doc.precision("change_amount"))
|
||||||
|
|
||||||
self.doc.change_amount = change_amount;
|
self.doc.base_change_amount = flt(self.doc.change_amount * self.doc.conversion_rate,
|
||||||
self.doc.base_change_amount = flt(change_amount * self.doc.conversion_rate,
|
|
||||||
self.doc.precision("base_change_amount"))
|
self.doc.precision("base_change_amount"))
|
||||||
|
|
||||||
def calculate_margin(self, item):
|
def calculate_margin(self, item):
|
||||||
|
|||||||
@@ -38,6 +38,7 @@ class Lead(SellingController):
|
|||||||
frappe.throw(_("Campaign Name is required"))
|
frappe.throw(_("Campaign Name is required"))
|
||||||
|
|
||||||
if self.email_id:
|
if self.email_id:
|
||||||
|
if not self.flags.ignore_email_validation:
|
||||||
validate_email_add(self.email_id, True)
|
validate_email_add(self.email_id, True)
|
||||||
|
|
||||||
if self.email_id == self.lead_owner:
|
if self.email_id == self.lead_owner:
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
|
|
||||||
from __future__ import unicode_literals
|
from __future__ import unicode_literals
|
||||||
import frappe, json
|
import frappe, json
|
||||||
from frappe.utils import cstr, cint, get_fullname, validate_email_add
|
from frappe.utils import cstr, cint, get_fullname
|
||||||
from frappe import msgprint, _
|
from frappe import msgprint, _
|
||||||
from frappe.model.mapper import get_mapped_doc
|
from frappe.model.mapper import get_mapped_doc
|
||||||
from erpnext.setup.utils import get_exchange_rate
|
from erpnext.setup.utils import get_exchange_rate
|
||||||
@@ -43,7 +43,7 @@ class Opportunity(TransactionBase):
|
|||||||
|
|
||||||
def make_new_lead_if_required(self):
|
def make_new_lead_if_required(self):
|
||||||
"""Set lead against new opportunity"""
|
"""Set lead against new opportunity"""
|
||||||
if not (self.lead or self.customer) and self.contact_email and validate_email_add(self.contact_email):
|
if not (self.lead or self.customer) and self.contact_email:
|
||||||
lead_name = frappe.db.get_value("Lead", {"email_id": self.contact_email})
|
lead_name = frappe.db.get_value("Lead", {"email_id": self.contact_email})
|
||||||
if not lead_name:
|
if not lead_name:
|
||||||
sender_name = get_fullname(self.contact_email)
|
sender_name = get_fullname(self.contact_email)
|
||||||
@@ -64,6 +64,7 @@ class Opportunity(TransactionBase):
|
|||||||
"lead_name": sender_name
|
"lead_name": sender_name
|
||||||
})
|
})
|
||||||
|
|
||||||
|
lead.flags.ignore_email_validation = True
|
||||||
lead.insert(ignore_permissions=True)
|
lead.insert(ignore_permissions=True)
|
||||||
lead_name = lead.name
|
lead_name = lead.name
|
||||||
|
|
||||||
|
|||||||
@@ -72,9 +72,6 @@ def simulate():
|
|||||||
stock.work()
|
stock.work()
|
||||||
accounts.work()
|
accounts.work()
|
||||||
projects.run_projects(current_date)
|
projects.run_projects(current_date)
|
||||||
# run_stock()
|
|
||||||
# run_accounts()
|
|
||||||
# run_projects()
|
|
||||||
# run_messages()
|
# run_messages()
|
||||||
|
|
||||||
current_date = frappe.utils.add_days(current_date, 1)
|
current_date = frappe.utils.add_days(current_date, 1)
|
||||||
|
|||||||
@@ -212,7 +212,7 @@ def setup_user():
|
|||||||
user = frappe.new_doc("User")
|
user = frappe.new_doc("User")
|
||||||
user.update(u)
|
user.update(u)
|
||||||
user.flags.no_welcome_mail
|
user.flags.no_welcome_mail
|
||||||
user.password = 'demo'
|
user.new_password = 'demo'
|
||||||
user.insert()
|
user.insert()
|
||||||
|
|
||||||
def import_json(doctype, submit=False, values=None):
|
def import_json(doctype, submit=False, values=None):
|
||||||
@@ -377,6 +377,12 @@ def setup_budget():
|
|||||||
|
|
||||||
|
|
||||||
def setup_user_roles():
|
def setup_user_roles():
|
||||||
|
user = frappe.get_doc('User', 'demo@erpnext.com')
|
||||||
|
user.add_roles('HR User', 'HR Manager', 'Accounts User', 'Accounts Manager',
|
||||||
|
'Stock User', 'Stock Manager', 'Sales User', 'Sales Manager', 'Purchase User',
|
||||||
|
'Purchase Manager', 'Projects User', 'Manufacturing User', 'Manufacturing Manager',
|
||||||
|
'Support Team')
|
||||||
|
|
||||||
if not frappe.db.get_global('demo_hr_user'):
|
if not frappe.db.get_global('demo_hr_user'):
|
||||||
user = frappe.get_doc('User', 'CharmaineGaudreau@example.com')
|
user = frappe.get_doc('User', 'CharmaineGaudreau@example.com')
|
||||||
user.add_roles('HR User', 'HR Manager', 'Accounts User')
|
user.add_roles('HR User', 'HR Manager', 'Accounts User')
|
||||||
|
|||||||
BIN
erpnext/docs/assets/img/accounts/asset-item.png
Normal file
|
After Width: | Height: | Size: 68 KiB |
BIN
erpnext/docs/assets/img/accounts/opening-2.png
Normal file
|
After Width: | Height: | Size: 89 KiB |
BIN
erpnext/docs/assets/img/accounts/opening-3.png
Normal file
|
After Width: | Height: | Size: 43 KiB |
BIN
erpnext/docs/assets/img/accounts/opening-4.png
Normal file
|
After Width: | Height: | Size: 88 KiB |
BIN
erpnext/docs/assets/img/accounts/opening-5.png
Normal file
|
After Width: | Height: | Size: 105 KiB |
BIN
erpnext/docs/assets/img/accounts/opening-6.png
Normal file
|
After Width: | Height: | Size: 105 KiB |
BIN
erpnext/docs/assets/img/accounts/opening-7.png
Normal file
|
After Width: | Height: | Size: 70 KiB |
BIN
erpnext/docs/assets/img/accounts/perpetual-1.png
Normal file
|
After Width: | Height: | Size: 78 KiB |
BIN
erpnext/docs/assets/img/accounts/pos-customer.png
Normal file
|
After Width: | Height: | Size: 45 KiB |
BIN
erpnext/docs/assets/img/accounts/pos-item.png
Normal file
|
After Width: | Height: | Size: 143 KiB |
BIN
erpnext/docs/assets/img/accounts/pos-payment.png
Normal file
|
After Width: | Height: | Size: 46 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/assign-1.png
Normal file
|
After Width: | Height: | Size: 67 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/assign-2.png
Normal file
|
After Width: | Height: | Size: 82 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/assign-3.png
Normal file
|
After Width: | Height: | Size: 82 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/assign-4.png
Normal file
|
After Width: | Height: | Size: 61 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/calendar-1.png
Normal file
|
After Width: | Height: | Size: 70 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/calendar-2.gif
Normal file
|
After Width: | Height: | Size: 136 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/calendar-3.png
Normal file
|
After Width: | Height: | Size: 67 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/calendar-4.png
Normal file
|
After Width: | Height: | Size: 74 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/calendar-5.png
Normal file
|
After Width: | Height: | Size: 50 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/calendar-6.png
Normal file
|
After Width: | Height: | Size: 68 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/calendar-7.png
Normal file
|
After Width: | Height: | Size: 76 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/chat-1.png
Normal file
|
After Width: | Height: | Size: 86 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/chat-2.png
Normal file
|
After Width: | Height: | Size: 51 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/comments-1.png
Normal file
|
After Width: | Height: | Size: 80 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/note-1.png
Normal file
|
After Width: | Height: | Size: 79 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/share-1.gif
Normal file
|
After Width: | Height: | Size: 252 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/tags-1.png
Normal file
|
After Width: | Height: | Size: 62 KiB |
BIN
erpnext/docs/assets/img/collaboration-tools/tags-2.png
Normal file
|
After Width: | Height: | Size: 78 KiB |
0
erpnext/docs/assets/img/schools/fees/__init__.py
Normal file
BIN
erpnext/docs/assets/img/schools/fees/fee-category.png
Normal file
|
After Width: | Height: | Size: 73 KiB |
BIN
erpnext/docs/assets/img/schools/fees/fee-structure.png
Normal file
|
After Width: | Height: | Size: 77 KiB |
BIN
erpnext/docs/assets/img/schools/fees/fees-section.png
Normal file
|
After Width: | Height: | Size: 36 KiB |
BIN
erpnext/docs/assets/img/schools/fees/fees.png
Normal file
|
After Width: | Height: | Size: 104 KiB |
BIN
erpnext/docs/assets/img/schools/home.png
Normal file
|
After Width: | Height: | Size: 58 KiB |
|
After Width: | Height: | Size: 76 KiB |
BIN
erpnext/docs/assets/img/schools/schedule/course-schedule-att.png
Normal file
|
After Width: | Height: | Size: 101 KiB |
BIN
erpnext/docs/assets/img/schools/schedule/course-schedule.png
Normal file
|
After Width: | Height: | Size: 112 KiB |
BIN
erpnext/docs/assets/img/schools/schedule/examination.png
Normal file
|
After Width: | Height: | Size: 75 KiB |
BIN
erpnext/docs/assets/img/schools/schedule/schedule-section.png
Normal file
|
After Width: | Height: | Size: 43 KiB |
BIN
erpnext/docs/assets/img/schools/schedule/scheduling-tool.png
Normal file
|
After Width: | Height: | Size: 85 KiB |
BIN
erpnext/docs/assets/img/schools/schedule/student-attendance.png
Normal file
|
After Width: | Height: | Size: 54 KiB |
0
erpnext/docs/assets/img/schools/setup/__init__.py
Normal file
BIN
erpnext/docs/assets/img/schools/setup/academic-term.png
Normal file
|
After Width: | Height: | Size: 63 KiB |
BIN
erpnext/docs/assets/img/schools/setup/academic-year.png
Normal file
|
After Width: | Height: | Size: 48 KiB |
BIN
erpnext/docs/assets/img/schools/setup/course.png
Normal file
|
After Width: | Height: | Size: 58 KiB |
BIN
erpnext/docs/assets/img/schools/setup/instructor.png
Normal file
|
After Width: | Height: | Size: 106 KiB |
BIN
erpnext/docs/assets/img/schools/setup/program.png
Normal file
|
After Width: | Height: | Size: 119 KiB |
BIN
erpnext/docs/assets/img/schools/setup/room.png
Normal file
|
After Width: | Height: | Size: 55 KiB |
BIN
erpnext/docs/assets/img/schools/setup/setup-section.png
Normal file
|
After Width: | Height: | Size: 46 KiB |
0
erpnext/docs/assets/img/schools/student/__init__.py
Normal file
BIN
erpnext/docs/assets/img/schools/student/program-enrollment.png
Normal file
|
After Width: | Height: | Size: 60 KiB |
|
After Width: | Height: | Size: 72 KiB |
BIN
erpnext/docs/assets/img/schools/student/student-applicant.png
Normal file
|
After Width: | Height: | Size: 158 KiB |
|
After Width: | Height: | Size: 87 KiB |
BIN
erpnext/docs/assets/img/schools/student/student-group.png
Normal file
|
After Width: | Height: | Size: 102 KiB |
BIN
erpnext/docs/assets/img/schools/student/student-section.png
Normal file
|
After Width: | Height: | Size: 38 KiB |
BIN
erpnext/docs/assets/img/schools/student/student.png
Normal file
|
After Width: | Height: | Size: 124 KiB |
BIN
erpnext/docs/assets/img/setup/print/cheque-1.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
BIN
erpnext/docs/assets/img/setup/print/cheque-2.png
Normal file
|
After Width: | Height: | Size: 60 KiB |
BIN
erpnext/docs/assets/img/setup/print/cheque-3.png
Normal file
|
After Width: | Height: | Size: 48 KiB |
BIN
erpnext/docs/assets/img/setup/print/cheque-4.png
Normal file
|
After Width: | Height: | Size: 119 KiB |
BIN
erpnext/docs/assets/img/setup/print/cheque-5.gif
Normal file
|
After Width: | Height: | Size: 146 KiB |
BIN
erpnext/docs/assets/img/setup/print/sample-cheque.jpg
Normal file
|
After Width: | Height: | Size: 30 KiB |
|
Before Width: | Height: | Size: 21 KiB |
|
Before Width: | Height: | Size: 13 KiB |
|
Before Width: | Height: | Size: 15 KiB |
|
Before Width: | Height: | Size: 23 KiB |
|
Before Width: | Height: | Size: 19 KiB |
|
Before Width: | Height: | Size: 28 KiB |