diff --git a/erpnext/accounts/doctype/accounts_settings/accounts_settings.json b/erpnext/accounts/doctype/accounts_settings/accounts_settings.json index e4b96ae67e..8ca8b71ef8 100644 --- a/erpnext/accounts/doctype/accounts_settings/accounts_settings.json +++ b/erpnext/accounts/doctype/accounts_settings/accounts_settings.json @@ -19,7 +19,6 @@ "unlink_payment_on_cancellation_of_invoice", "unlink_advance_payment_on_cancelation_of_order", "book_asset_depreciation_entry_automatically", - "allow_cost_center_in_entry_of_bs_account", "add_taxes_from_item_tax_template", "automatically_fetch_payment_terms", "deferred_accounting_settings_section", @@ -113,12 +112,6 @@ "fieldtype": "Check", "label": "Book Asset Depreciation Entry Automatically" }, - { - "default": "0", - "fieldname": "allow_cost_center_in_entry_of_bs_account", - "fieldtype": "Check", - "label": "Allow Cost Center In Entry of Balance Sheet Account" - }, { "default": "1", "fieldname": "add_taxes_from_item_tax_template", diff --git a/erpnext/accounts/doctype/accounts_settings/accounts_settings.py b/erpnext/accounts/doctype/accounts_settings/accounts_settings.py index 2473d715d0..5593466fc2 100644 --- a/erpnext/accounts/doctype/accounts_settings/accounts_settings.py +++ b/erpnext/accounts/doctype/accounts_settings/accounts_settings.py @@ -20,7 +20,6 @@ class AccountsSettings(Document): self.validate_stale_days() self.enable_payment_schedule_in_print() - self.enable_fields_for_cost_center_settings() def validate_stale_days(self): if not self.allow_stale and cint(self.stale_days) <= 0: @@ -33,8 +32,3 @@ class AccountsSettings(Document): for doctype in ("Sales Order", "Sales Invoice", "Purchase Order", "Purchase Invoice"): make_property_setter(doctype, "due_date", "print_hide", show_in_print, "Check") make_property_setter(doctype, "payment_schedule", "print_hide", 0 if show_in_print else 1, "Check") - - def enable_fields_for_cost_center_settings(self): - show_field = 0 if cint(self.allow_cost_center_in_entry_of_bs_account) else 1 - for doctype in ("Sales Invoice", "Purchase Invoice", "Payment Entry"): - make_property_setter(doctype, "cost_center", "hidden", show_field, "Check") diff --git a/erpnext/accounts/doctype/gl_entry/gl_entry.py b/erpnext/accounts/doctype/gl_entry/gl_entry.py index 645da341a3..def9ed6803 100644 --- a/erpnext/accounts/doctype/gl_entry/gl_entry.py +++ b/erpnext/accounts/doctype/gl_entry/gl_entry.py @@ -72,12 +72,6 @@ class GLEntry(Document): if not self.cost_center and self.voucher_type != 'Period Closing Voucher': frappe.throw(_("{0} {1}: Cost Center is required for 'Profit and Loss' account {2}. Please set up a default Cost Center for the Company.") .format(self.voucher_type, self.voucher_no, self.account)) - else: - from erpnext.accounts.utils import get_allow_cost_center_in_entry_of_bs_account - if not get_allow_cost_center_in_entry_of_bs_account() and self.cost_center: - self.cost_center = None - if self.project: - self.project = None def validate_dimensions_for_pl_and_bs(self): diff --git a/erpnext/accounts/doctype/invoice_discounting/invoice_discounting.py b/erpnext/accounts/doctype/invoice_discounting/invoice_discounting.py index 594b4d4a22..8083b21f75 100644 --- a/erpnext/accounts/doctype/invoice_discounting/invoice_discounting.py +++ b/erpnext/accounts/doctype/invoice_discounting/invoice_discounting.py @@ -3,7 +3,7 @@ # For license information, please see license.txt from __future__ import unicode_literals -import frappe, json +import frappe, json, erpnext from frappe import _ from frappe.utils import flt, getdate, nowdate, add_days from erpnext.controllers.accounts_controller import AccountsController @@ -134,16 +134,19 @@ class InvoiceDiscounting(AccountsController): je.append("accounts", { "account": self.bank_account, "debit_in_account_currency": flt(self.total_amount) - flt(self.bank_charges), + "cost_center": erpnext.get_default_cost_center(self.company) }) je.append("accounts", { "account": self.bank_charges_account, - "debit_in_account_currency": flt(self.bank_charges) + "debit_in_account_currency": flt(self.bank_charges), + "cost_center": erpnext.get_default_cost_center(self.company) }) je.append("accounts", { "account": self.short_term_loan, "credit_in_account_currency": flt(self.total_amount), + "cost_center": erpnext.get_default_cost_center(self.company), "reference_type": "Invoice Discounting", "reference_name": self.name }) @@ -151,6 +154,7 @@ class InvoiceDiscounting(AccountsController): je.append("accounts", { "account": self.accounts_receivable_discounted, "debit_in_account_currency": flt(d.outstanding_amount), + "cost_center": erpnext.get_default_cost_center(self.company), "reference_type": "Invoice Discounting", "reference_name": self.name, "party_type": "Customer", @@ -160,6 +164,7 @@ class InvoiceDiscounting(AccountsController): je.append("accounts", { "account": self.accounts_receivable_credit, "credit_in_account_currency": flt(d.outstanding_amount), + "cost_center": erpnext.get_default_cost_center(self.company), "reference_type": "Invoice Discounting", "reference_name": self.name, "party_type": "Customer", @@ -177,13 +182,15 @@ class InvoiceDiscounting(AccountsController): je.append("accounts", { "account": self.short_term_loan, "debit_in_account_currency": flt(self.total_amount), + "cost_center": erpnext.get_default_cost_center(self.company), "reference_type": "Invoice Discounting", "reference_name": self.name, }) je.append("accounts", { "account": self.bank_account, - "credit_in_account_currency": flt(self.total_amount) + "credit_in_account_currency": flt(self.total_amount), + "cost_center": erpnext.get_default_cost_center(self.company) }) if getdate(self.loan_end_date) > getdate(nowdate()): @@ -193,6 +200,7 @@ class InvoiceDiscounting(AccountsController): je.append("accounts", { "account": self.accounts_receivable_discounted, "credit_in_account_currency": flt(outstanding_amount), + "cost_center": erpnext.get_default_cost_center(self.company), "reference_type": "Invoice Discounting", "reference_name": self.name, "party_type": "Customer", @@ -202,6 +210,7 @@ class InvoiceDiscounting(AccountsController): je.append("accounts", { "account": self.accounts_receivable_unpaid, "debit_in_account_currency": flt(outstanding_amount), + "cost_center": erpnext.get_default_cost_center(self.company), "reference_type": "Invoice Discounting", "reference_name": self.name, "party_type": "Customer", diff --git a/erpnext/accounts/doctype/journal_entry/test_journal_entry.py b/erpnext/accounts/doctype/journal_entry/test_journal_entry.py index 6996c775b3..23ad1eef14 100644 --- a/erpnext/accounts/doctype/journal_entry/test_journal_entry.py +++ b/erpnext/accounts/doctype/journal_entry/test_journal_entry.py @@ -204,11 +204,8 @@ class TestJournalEntry(unittest.TestCase): self.assertEqual(jv.inter_company_journal_entry_reference, "") self.assertEqual(jv1.inter_company_journal_entry_reference, "") - def test_jv_for_enable_allow_cost_center_in_entry_of_bs_account(self): + def test_jv_with_cost_centre(self): from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 1 - accounts_settings.save() cost_center = "_Test Cost Center for BS Account - _TC" create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company") jv = make_journal_entry("_Test Cash - _TC", "_Test Bank - _TC", 100, cost_center = cost_center, save=False) @@ -237,15 +234,45 @@ class TestJournalEntry(unittest.TestCase): for gle in gl_entries: self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center) - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() + def test_jv_with_project(self): + from erpnext.projects.doctype.project.test_project import make_project + project = make_project({ + 'project_name': 'Journal Entry Project', + 'project_template_name': 'Test Project Template', + 'start_date': '2020-01-01' + }) - def test_jv_account_and_party_balance_for_enable_allow_cost_center_in_entry_of_bs_account(self): + jv = make_journal_entry("_Test Cash - _TC", "_Test Bank - _TC", 100, save=False) + for d in jv.accounts: + d.project = project.project_name + jv.voucher_type = "Bank Entry" + jv.multi_currency = 0 + jv.cheque_no = "112233" + jv.cheque_date = nowdate() + jv.insert() + jv.submit() + + expected_values = { + "_Test Cash - _TC": { + "project": project.project_name + }, + "_Test Bank - _TC": { + "project": project.project_name + } + } + + gl_entries = frappe.db.sql("""select account, project, debit, credit + from `tabGL Entry` where voucher_type='Journal Entry' and voucher_no=%s + order by account asc""", jv.name, as_dict=1) + + self.assertTrue(gl_entries) + + for gle in gl_entries: + self.assertEqual(expected_values[gle.account]["project"], gle.project) + + def test_jv_account_and_party_balance_with_cost_centre(self): from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center from erpnext.accounts.utils import get_balance_on - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 1 - accounts_settings.save() cost_center = "_Test Cost Center for BS Account - _TC" create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company") jv = make_journal_entry("_Test Cash - _TC", "_Test Bank - _TC", 100, cost_center = cost_center, save=False) @@ -261,9 +288,6 @@ class TestJournalEntry(unittest.TestCase): account_balance = get_balance_on(account="_Test Bank - _TC", cost_center=cost_center) self.assertEqual(expected_account_balance, account_balance) - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() - def make_journal_entry(account1, account2, amount, cost_center=None, posting_date=None, exchange_rate=1, save=True, submit=False, project=None): if not cost_center: cost_center = "_Test Cost Center - _TC" diff --git a/erpnext/accounts/doctype/payment_entry/payment_entry.py b/erpnext/accounts/doctype/payment_entry/payment_entry.py index 59611bc74c..c7912ce227 100644 --- a/erpnext/accounts/doctype/payment_entry/payment_entry.py +++ b/erpnext/accounts/doctype/payment_entry/payment_entry.py @@ -6,7 +6,7 @@ from __future__ import unicode_literals import frappe, erpnext, json from frappe import _, scrub, ValidationError from frappe.utils import flt, comma_or, nowdate, getdate -from erpnext.accounts.utils import get_outstanding_invoices, get_account_currency, get_balance_on, get_allow_cost_center_in_entry_of_bs_account +from erpnext.accounts.utils import get_outstanding_invoices, get_account_currency, get_balance_on from erpnext.accounts.party import get_party_account from erpnext.accounts.doctype.journal_entry.journal_entry import get_default_bank_cash_account from erpnext.setup.utils import get_exchange_rate @@ -658,7 +658,7 @@ def get_outstanding_reference_documents(args): .format(frappe.db.escape(args["voucher_type"]), frappe.db.escape(args["voucher_no"])) # Add cost center condition - if args.get("cost_center") and get_allow_cost_center_in_entry_of_bs_account(): + if args.get("cost_center"): condition += " and cost_center='%s'" % args.get("cost_center") date_fields_dict = { diff --git a/erpnext/accounts/doctype/payment_entry/test_payment_entry.py b/erpnext/accounts/doctype/payment_entry/test_payment_entry.py index 8bb741f0b2..772fc1a252 100644 --- a/erpnext/accounts/doctype/payment_entry/test_payment_entry.py +++ b/erpnext/accounts/doctype/payment_entry/test_payment_entry.py @@ -460,11 +460,8 @@ class TestPaymentEntry(unittest.TestCase): outstanding_amount = flt(frappe.db.get_value("Sales Invoice", si.name, "outstanding_amount")) self.assertEqual(outstanding_amount, 0) - def test_payment_entry_against_sales_invoice_for_enable_allow_cost_center_in_entry_of_bs_account(self): + def test_payment_entry_against_sales_invoice_with_cost_centre(self): from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 1 - accounts_settings.save() cost_center = "_Test Cost Center for BS Account - _TC" create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company") @@ -499,39 +496,8 @@ class TestPaymentEntry(unittest.TestCase): for gle in gl_entries: self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center) - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() - - def test_payment_entry_against_sales_invoice_for_disable_allow_cost_center_in_entry_of_bs_account(self): - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() - si = create_sales_invoice(debit_to="Debtors - _TC") - - pe = get_payment_entry("Sales Invoice", si.name, bank_account="_Test Bank - _TC") - - pe.reference_no = "112211-2" - pe.reference_date = nowdate() - pe.paid_to = "_Test Bank - _TC" - pe.paid_amount = si.grand_total - pe.insert() - pe.submit() - - gl_entries = frappe.db.sql("""select account, cost_center, account_currency, debit, credit, - debit_in_account_currency, credit_in_account_currency - from `tabGL Entry` where voucher_type='Payment Entry' and voucher_no=%s - order by account asc""", pe.name, as_dict=1) - - self.assertTrue(gl_entries) - - for gle in gl_entries: - self.assertEqual(gle.cost_center, None) - - def test_payment_entry_against_purchase_invoice_for_enable_allow_cost_center_in_entry_of_bs_account(self): + def test_payment_entry_against_purchase_invoice_with_cost_center(self): from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 1 - accounts_settings.save() cost_center = "_Test Cost Center for BS Account - _TC" create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company") @@ -566,40 +532,9 @@ class TestPaymentEntry(unittest.TestCase): for gle in gl_entries: self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center) - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() - - def test_payment_entry_against_purchase_invoice_for_disable_allow_cost_center_in_entry_of_bs_account(self): - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() - pi = make_purchase_invoice(credit_to="Creditors - _TC") - - pe = get_payment_entry("Purchase Invoice", pi.name, bank_account="_Test Bank - _TC") - - pe.reference_no = "112222-2" - pe.reference_date = nowdate() - pe.paid_from = "_Test Bank - _TC" - pe.paid_amount = pi.grand_total - pe.insert() - pe.submit() - - gl_entries = frappe.db.sql("""select account, cost_center, account_currency, debit, credit, - debit_in_account_currency, credit_in_account_currency - from `tabGL Entry` where voucher_type='Payment Entry' and voucher_no=%s - order by account asc""", pe.name, as_dict=1) - - self.assertTrue(gl_entries) - - for gle in gl_entries: - self.assertEqual(gle.cost_center, None) - - def test_payment_entry_account_and_party_balance_for_enable_allow_cost_center_in_entry_of_bs_account(self): + def test_payment_entry_account_and_party_balance_with_cost_center(self): from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center from erpnext.accounts.utils import get_balance_on - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 1 - accounts_settings.save() cost_center = "_Test Cost Center for BS Account - _TC" create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company") @@ -630,9 +565,6 @@ class TestPaymentEntry(unittest.TestCase): self.assertEqual(expected_party_balance, party_balance) self.assertEqual(expected_party_account_balance, party_account_balance) - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() - def create_payment_terms_template(): create_payment_term('Basic Amount Receivable') @@ -665,4 +597,4 @@ def create_payment_term(name): frappe.get_doc({ 'doctype': 'Payment Term', 'payment_term_name': name - }).insert() \ No newline at end of file + }).insert() diff --git a/erpnext/accounts/doctype/purchase_invoice/purchase_invoice.json b/erpnext/accounts/doctype/purchase_invoice/purchase_invoice.json index 829c34da67..eb1ccd95af 100644 --- a/erpnext/accounts/doctype/purchase_invoice/purchase_invoice.json +++ b/erpnext/accounts/doctype/purchase_invoice/purchase_invoice.json @@ -26,6 +26,7 @@ "accounting_dimensions_section", "cost_center", "dimension_col_break", + "project", "supplier_invoice_details", "bill_no", "column_break_15", @@ -1598,6 +1599,12 @@ "show_days": 1, "show_seconds": 1 }, + { + "fieldname": "project", + "fieldtype": "Link", + "label": "Project", + "options": "Project" + }, { "fieldname": "tax_withholding_category", "fieldtype": "Link", diff --git a/erpnext/accounts/doctype/purchase_invoice/purchase_invoice.py b/erpnext/accounts/doctype/purchase_invoice/purchase_invoice.py index 3cd57d403a..98d68f894a 100644 --- a/erpnext/accounts/doctype/purchase_invoice/purchase_invoice.py +++ b/erpnext/accounts/doctype/purchase_invoice/purchase_invoice.py @@ -476,6 +476,7 @@ class PurchaseInvoice(BuyingController): if self.party_account_currency==self.company_currency else grand_total, "against_voucher": self.return_against if cint(self.is_return) and self.return_against else self.name, "against_voucher_type": self.doctype, + "project": self.project, "cost_center": self.cost_center }, self.party_account_currency, item=self) ) @@ -516,6 +517,7 @@ class PurchaseInvoice(BuyingController): "account": warehouse_account[item.warehouse]['account'], "against": warehouse_account[item.from_warehouse]["account"], "cost_center": item.cost_center, + "project": item.project or self.project, "remarks": self.get("remarks") or _("Accounting Entry for Stock"), "debit": warehouse_debit_amount, }, warehouse_account[item.warehouse]["account_currency"], item=item)) @@ -525,6 +527,7 @@ class PurchaseInvoice(BuyingController): "account": warehouse_account[item.from_warehouse]['account'], "against": warehouse_account[item.warehouse]["account"], "cost_center": item.cost_center, + "project": item.project or self.project, "remarks": self.get("remarks") or _("Accounting Entry for Stock"), "debit": -1 * flt(item.base_net_amount, item.precision("base_net_amount")), }, warehouse_account[item.from_warehouse]["account_currency"], item=item)) @@ -548,7 +551,7 @@ class PurchaseInvoice(BuyingController): "debit": warehouse_debit_amount, "remarks": self.get("remarks") or _("Accounting Entry for Stock"), "cost_center": item.cost_center, - "project": item.project + "project": item.project or self.project }, account_currency, item=item) ) @@ -561,7 +564,7 @@ class PurchaseInvoice(BuyingController): "cost_center": item.cost_center, "remarks": self.get("remarks") or _("Accounting Entry for Stock"), "credit": flt(amount), - "project": item.project + "project": item.project or self.project }, item=item)) # sub-contracting warehouse @@ -574,6 +577,7 @@ class PurchaseInvoice(BuyingController): "account": supplier_warehouse_account, "against": item.expense_account, "cost_center": item.cost_center, + "project": item.project or self.project, "remarks": self.get("remarks") or _("Accounting Entry for Stock"), "credit": flt(item.rm_supp_cost) }, warehouse_account[self.supplier_warehouse]["account_currency"], item=item)) @@ -606,7 +610,7 @@ class PurchaseInvoice(BuyingController): "against": self.supplier, "debit": amount, "cost_center": item.cost_center, - "project": item.project + "project": item.project or self.project }, account_currency, item=item)) # If asset is bought through this document and not linked to PR @@ -619,7 +623,7 @@ class PurchaseInvoice(BuyingController): "cost_center": item.cost_center, "remarks": self.get("remarks") or _("Accounting Entry for Stock"), "credit": flt(item.landed_cost_voucher_amount), - "project": item.project + "project": item.project or self.project }, item=item)) gl_entries.append(self.get_gl_dict({ @@ -628,7 +632,7 @@ class PurchaseInvoice(BuyingController): "cost_center": item.cost_center, "remarks": self.get("remarks") or _("Accounting Entry for Stock"), "debit": flt(item.landed_cost_voucher_amount), - "project": item.project + "project": item.project or self.project }, item=item)) # update gross amount of asset bought through this document @@ -654,7 +658,8 @@ class PurchaseInvoice(BuyingController): "against": self.supplier, "debit": flt(item.item_tax_amount, item.precision("item_tax_amount")), "remarks": self.remarks or "Accounting Entry for Stock", - "cost_center": self.cost_center + "cost_center": self.cost_center, + "project": item.project or self.project }, item=item) ) @@ -683,7 +688,8 @@ class PurchaseInvoice(BuyingController): "debit": base_asset_amount, "debit_in_account_currency": (base_asset_amount if arbnb_currency == self.company_currency else asset_amount), - "cost_center": item.cost_center + "cost_center": item.cost_center, + "project": item.project or self.project }, item=item)) if item.item_tax_amount: @@ -693,6 +699,7 @@ class PurchaseInvoice(BuyingController): "against": self.supplier, "remarks": self.get("remarks") or _("Accounting Entry for Asset"), "cost_center": item.cost_center, + "project": item.project or self.project, "credit": item.item_tax_amount, "credit_in_account_currency": (item.item_tax_amount if asset_eiiav_currency == self.company_currency else @@ -709,7 +716,8 @@ class PurchaseInvoice(BuyingController): "debit": base_asset_amount, "debit_in_account_currency": (base_asset_amount if cwip_account_currency == self.company_currency else asset_amount), - "cost_center": self.cost_center + "cost_center": self.cost_center, + "project": item.project or self.project }, item=item)) if item.item_tax_amount and not cint(erpnext.is_perpetual_inventory_enabled(self.company)): @@ -720,6 +728,7 @@ class PurchaseInvoice(BuyingController): "remarks": self.get("remarks") or _("Accounting Entry for Asset"), "cost_center": item.cost_center, "credit": item.item_tax_amount, + "project": item.project or self.project, "credit_in_account_currency": (item.item_tax_amount if asset_eiiav_currency == self.company_currency else item.item_tax_amount / self.conversion_rate) @@ -735,7 +744,7 @@ class PurchaseInvoice(BuyingController): "cost_center": item.cost_center, "remarks": self.get("remarks") or _("Accounting Entry for Stock"), "credit": flt(item.landed_cost_voucher_amount), - "project": item.project + "project": item.project or self.project }, item=item)) gl_entries.append(self.get_gl_dict({ @@ -744,7 +753,7 @@ class PurchaseInvoice(BuyingController): "cost_center": item.cost_center, "remarks": self.get("remarks") or _("Accounting Entry for Stock"), "debit": flt(item.landed_cost_voucher_amount), - "project": item.project + "project": item.project or self.project }, item=item)) # update gross amount of assets bought through this document @@ -779,7 +788,7 @@ class PurchaseInvoice(BuyingController): "debit": stock_adjustment_amt, "remarks": self.get("remarks") or _("Stock Adjustment"), "cost_center": item.cost_center, - "project": item.project + "project": item.project or self.project }, account_currency, item=item) ) @@ -871,7 +880,8 @@ class PurchaseInvoice(BuyingController): if self.party_account_currency==self.company_currency else self.paid_amount, "against_voucher": self.return_against if cint(self.is_return) and self.return_against else self.name, "against_voucher_type": self.doctype, - "cost_center": self.cost_center + "cost_center": self.cost_center, + "project": self.project }, self.party_account_currency, item=self) ) @@ -903,7 +913,8 @@ class PurchaseInvoice(BuyingController): if self.party_account_currency==self.company_currency else self.write_off_amount, "against_voucher": self.return_against if cint(self.is_return) and self.return_against else self.name, "against_voucher_type": self.doctype, - "cost_center": self.cost_center + "cost_center": self.cost_center, + "project": self.project }, self.party_account_currency, item=self) ) gl_entries.append( diff --git a/erpnext/accounts/doctype/purchase_invoice/test_purchase_invoice.py b/erpnext/accounts/doctype/purchase_invoice/test_purchase_invoice.py index b5955ca258..9a666bf9f8 100644 --- a/erpnext/accounts/doctype/purchase_invoice/test_purchase_invoice.py +++ b/erpnext/accounts/doctype/purchase_invoice/test_purchase_invoice.py @@ -14,6 +14,7 @@ from erpnext.stock.doctype.purchase_receipt.test_purchase_receipt import set_per from erpnext.controllers.accounts_controller import get_payment_terms from erpnext.exceptions import InvalidCurrency from erpnext.stock.doctype.stock_entry.test_stock_entry import get_qty_after_transaction +from erpnext.projects.doctype.project.test_project import make_project from erpnext.accounts.doctype.account.test_account import get_inventory_account, create_account from erpnext.stock.doctype.item.test_item import create_item @@ -435,6 +436,8 @@ class TestPurchaseInvoice(unittest.TestCase): ) def test_total_purchase_cost_for_project(self): + make_project({'project_name':'_Test Project'}) + existing_purchase_cost = frappe.db.sql("""select sum(base_net_amount) from `tabPurchase Invoice Item` where project = '_Test Project' and docstatus=1""") existing_purchase_cost = existing_purchase_cost and existing_purchase_cost[0][0] or 0 @@ -808,11 +811,8 @@ class TestPurchaseInvoice(unittest.TestCase): pi_doc = frappe.get_doc('Purchase Invoice', pi.name) self.assertEqual(pi_doc.outstanding_amount, 0) - def test_purchase_invoice_for_enable_allow_cost_center_in_entry_of_bs_account(self): + def test_purchase_invoice_with_cost_center(self): from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 1 - accounts_settings.save() cost_center = "_Test Cost Center for BS Account - _TC" create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company") @@ -838,13 +838,7 @@ class TestPurchaseInvoice(unittest.TestCase): for gle in gl_entries: self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center) - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() - - def test_purchase_invoice_for_disable_allow_cost_center_in_entry_of_bs_account(self): - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() + def test_purchase_invoice_without_cost_center(self): cost_center = "_Test Cost Center - _TC" pi = make_purchase_invoice(credit_to="Creditors - _TC") @@ -867,6 +861,43 @@ class TestPurchaseInvoice(unittest.TestCase): for gle in gl_entries: self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center) + def test_purchase_invoice_with_project_link(self): + project = make_project({ + 'project_name': 'Purchase Invoice Project', + 'project_template_name': 'Test Project Template', + 'start_date': '2020-01-01' + }) + item_project = make_project({ + 'project_name': 'Purchase Invoice Item Project', + 'project_template_name': 'Test Project Template', + 'start_date': '2019-06-01' + }) + + pi = make_purchase_invoice(credit_to="Creditors - _TC" ,do_not_save=1) + pi.items[0].project = item_project.project_name + pi.project = project.project_name + + pi.submit() + + expected_values = { + "Creditors - _TC": { + "project": project.project_name + }, + "_Test Account Cost for Goods Sold - _TC": { + "project": item_project.project_name + } + } + + gl_entries = frappe.db.sql("""select account, cost_center, project, account_currency, debit, credit, + debit_in_account_currency, credit_in_account_currency + from `tabGL Entry` where voucher_type='Purchase Invoice' and voucher_no=%s + order by account asc""", pi.name, as_dict=1) + + self.assertTrue(gl_entries) + + for gle in gl_entries: + self.assertEqual(expected_values[gle.account]["project"], gle.project) + def test_deferred_expense_via_journal_entry(self): deferred_account = create_account(account_name="Deferred Expense", parent_account="Current Assets - _TC", company="_Test Company") diff --git a/erpnext/accounts/doctype/sales_invoice/sales_invoice.py b/erpnext/accounts/doctype/sales_invoice/sales_invoice.py index 5e8279bb08..b2b4cb1ea7 100644 --- a/erpnext/accounts/doctype/sales_invoice/sales_invoice.py +++ b/erpnext/accounts/doctype/sales_invoice/sales_invoice.py @@ -790,7 +790,8 @@ class SalesInvoice(SellingController): if self.party_account_currency==self.company_currency else grand_total, "against_voucher": self.return_against if cint(self.is_return) and self.return_against else self.name, "against_voucher_type": self.doctype, - "cost_center": self.cost_center + "cost_center": self.cost_center, + "project": self.project }, self.party_account_currency, item=self) ) @@ -845,7 +846,8 @@ class SalesInvoice(SellingController): "credit_in_account_currency": (flt(item.base_net_amount, item.precision("base_net_amount")) if account_currency==self.company_currency else flt(item.net_amount, item.precision("net_amount"))), - "cost_center": item.cost_center + "cost_center": item.cost_center, + "project": item.project or self.project }, account_currency, item=item) ) @@ -926,7 +928,8 @@ class SalesInvoice(SellingController): if self.party_account_currency==self.company_currency else flt(self.change_amount), "against_voucher": self.return_against if cint(self.is_return) and self.return_against else self.name, "against_voucher_type": self.doctype, - "cost_center": self.cost_center + "cost_center": self.cost_center, + "project": self.project }, self.party_account_currency, item=self) ) @@ -959,7 +962,8 @@ class SalesInvoice(SellingController): else flt(self.write_off_amount, self.precision("write_off_amount"))), "against_voucher": self.return_against if cint(self.is_return) else self.name, "against_voucher_type": self.doctype, - "cost_center": self.cost_center + "cost_center": self.cost_center, + "project": self.project }, self.party_account_currency, item=self) ) gl_entries.append( diff --git a/erpnext/accounts/doctype/sales_invoice/test_records.json b/erpnext/accounts/doctype/sales_invoice/test_records.json index ebe6e3da8d..11ebe6a573 100644 --- a/erpnext/accounts/doctype/sales_invoice/test_records.json +++ b/erpnext/accounts/doctype/sales_invoice/test_records.json @@ -3,6 +3,7 @@ "company": "_Test Company", "conversion_rate": 1.0, "currency": "INR", + "cost_center": "_Test Cost Center - _TC", "customer": "_Test Customer", "customer_name": "_Test Customer", "debit_to": "_Test Receivable - _TC", @@ -37,7 +38,8 @@ "charge_type": "On Net Total", "description": "VAT", "doctype": "Sales Taxes and Charges", - "parentfield": "taxes", + "parentfield": "taxes", + "cost_center": "_Test Cost Center - _TC", "rate": 6 }, { @@ -45,7 +47,8 @@ "charge_type": "On Net Total", "description": "Service Tax", "doctype": "Sales Taxes and Charges", - "parentfield": "taxes", + "parentfield": "taxes", + "cost_center": "_Test Cost Center - _TC", "rate": 6.36 } ], @@ -76,6 +79,7 @@ "customer_name": "_Test Customer", "debit_to": "_Test Receivable - _TC", "doctype": "Sales Invoice", + "cost_center": "_Test Cost Center - _TC", "items": [ { "amount": 500.0, @@ -107,7 +111,8 @@ "charge_type": "On Net Total", "description": "VAT", "doctype": "Sales Taxes and Charges", - "parentfield": "taxes", + "parentfield": "taxes", + "cost_center": "_Test Cost Center - _TC", "rate": 16 }, { @@ -115,7 +120,8 @@ "charge_type": "On Net Total", "description": "Service Tax", "doctype": "Sales Taxes and Charges", - "parentfield": "taxes", + "parentfield": "taxes", + "cost_center": "_Test Cost Center - _TC", "rate": 10 } ], @@ -132,6 +138,7 @@ "customer_name": "_Test Customer", "debit_to": "_Test Receivable - _TC", "doctype": "Sales Invoice", + "cost_center": "_Test Cost Center - _TC", "items": [ { "cost_center": "_Test Cost Center - _TC", @@ -259,6 +266,7 @@ "customer_name": "_Test Customer", "debit_to": "_Test Receivable - _TC", "doctype": "Sales Invoice", + "cost_center": "_Test Cost Center - _TC", "items": [ { "cost_center": "_Test Cost Center - _TC", diff --git a/erpnext/accounts/doctype/sales_invoice/test_sales_invoice.py b/erpnext/accounts/doctype/sales_invoice/test_sales_invoice.py index 311cc12dd8..ff4d6136e9 100644 --- a/erpnext/accounts/doctype/sales_invoice/test_sales_invoice.py +++ b/erpnext/accounts/doctype/sales_invoice/test_sales_invoice.py @@ -1640,11 +1640,8 @@ class TestSalesInvoice(unittest.TestCase): si_doc = frappe.get_doc('Sales Invoice', si.name) self.assertEqual(si_doc.outstanding_amount, 0) - def test_sales_invoice_for_enable_allow_cost_center_in_entry_of_bs_account(self): + def test_sales_invoice_with_cost_center(self): from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 1 - accounts_settings.save() cost_center = "_Test Cost Center for BS Account - _TC" create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company") @@ -1669,14 +1666,47 @@ class TestSalesInvoice(unittest.TestCase): for gle in gl_entries: self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center) + + def test_sales_invoice_with_project_link(self): + from erpnext.projects.doctype.project.test_project import make_project - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() + project = make_project({ + 'project_name': 'Sales Invoice Project', + 'project_template_name': 'Test Project Template', + 'start_date': '2020-01-01' + }) + item_project = make_project({ + 'project_name': 'Sales Invoice Item Project', + 'project_template_name': 'Test Project Template', + 'start_date': '2019-06-01' + }) - def test_sales_invoice_for_disable_allow_cost_center_in_entry_of_bs_account(self): - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 1 - accounts_settings.save() + sales_invoice = create_sales_invoice(do_not_save=1) + sales_invoice.items[0].project = item_project.project_name + sales_invoice.project = project.project_name + + sales_invoice.submit() + + expected_values = { + "Debtors - _TC": { + "project": project.project_name + }, + "Sales - _TC": { + "project": item_project.project_name + } + } + + gl_entries = frappe.db.sql("""select account, cost_center, project, account_currency, debit, credit, + debit_in_account_currency, credit_in_account_currency + from `tabGL Entry` where voucher_type='Sales Invoice' and voucher_no=%s + order by account asc""", sales_invoice.name, as_dict=1) + + self.assertTrue(gl_entries) + + for gle in gl_entries: + self.assertEqual(expected_values[gle.account]["project"], gle.project) + + def test_sales_invoice_without_cost_center(self): cost_center = "_Test Cost Center - _TC" si = create_sales_invoice(debit_to="Debtors - _TC") @@ -1699,9 +1729,6 @@ class TestSalesInvoice(unittest.TestCase): for gle in gl_entries: self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center) - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() - def test_deferred_revenue(self): deferred_account = create_account(account_name="Deferred Revenue", parent_account="Current Liabilities - _TC", company="_Test Company") diff --git a/erpnext/accounts/doctype/sales_invoice_item/sales_invoice_item.json b/erpnext/accounts/doctype/sales_invoice_item/sales_invoice_item.json index b2294e4318..9bc24664d1 100644 --- a/erpnext/accounts/doctype/sales_invoice_item/sales_invoice_item.json +++ b/erpnext/accounts/doctype/sales_invoice_item/sales_invoice_item.json @@ -94,6 +94,7 @@ "accounting_dimensions_section", "cost_center", "dimension_col_break", + "project", "section_break_54", "page_break" ], @@ -783,12 +784,18 @@ "fieldtype": "Link", "label": "Finance Book", "options": "Finance Book" + }, + { + "fieldname": "project", + "fieldtype": "Link", + "label": "Project", + "options": "Project" } ], "idx": 1, "istable": 1, "links": [], - "modified": "2019-12-04 12:22:38.517710", + "modified": "2020-03-11 12:24:41.749986", "modified_by": "Administrator", "module": "Accounts", "name": "Sales Invoice Item", diff --git a/erpnext/accounts/utils.py b/erpnext/accounts/utils.py index 69866e1566..013c30d6ff 100644 --- a/erpnext/accounts/utils.py +++ b/erpnext/accounts/utils.py @@ -144,14 +144,12 @@ def get_balance_on(account=None, date=None, party_type=None, party=None, company # hence, assuming balance as 0.0 return 0.0 - allow_cost_center_in_entry_of_bs_account = get_allow_cost_center_in_entry_of_bs_account() - if account: report_type = acc.report_type else: report_type = "" - if cost_center and (allow_cost_center_in_entry_of_bs_account or report_type =='Profit and Loss'): + if cost_center and report_type == 'Profit and Loss': cc = frappe.get_doc("Cost Center", cost_center) if cc.is_group: cond.append(""" exists ( @@ -897,11 +895,6 @@ def get_coa(doctype, parent, is_root, chart=None): return accounts -def get_allow_cost_center_in_entry_of_bs_account(): - def generator(): - return cint(frappe.db.get_value('Accounts Settings', None, 'allow_cost_center_in_entry_of_bs_account')) - return frappe.local_cache("get_allow_cost_center_in_entry_of_bs_account", (), generator, regenerate_if_none=True) - def get_stock_accounts(company): return frappe.get_all("Account", filters = { "account_type": "Stock", diff --git a/erpnext/assets/doctype/asset/depreciation.py b/erpnext/assets/doctype/asset/depreciation.py index 522c1fef67..8f0afb42b2 100644 --- a/erpnext/assets/doctype/asset/depreciation.py +++ b/erpnext/assets/doctype/asset/depreciation.py @@ -10,7 +10,7 @@ from erpnext.accounts.doctype.accounting_dimension.accounting_dimension import g def post_depreciation_entries(date=None): # Return if automatic booking of asset depreciation is disabled - if not cint(frappe.db.get_single_value("Accounts Settings", "book_asset_depreciation_entry_automatically")): + if not cint(frappe.db.get_value("Accounts Settings", None, "book_asset_depreciation_entry_automatically")): return if not date: @@ -58,7 +58,8 @@ def make_depreciation_entry(asset_name, date=None): "account": accumulated_depreciation_account, "credit_in_account_currency": d.depreciation_amount, "reference_type": "Asset", - "reference_name": asset.name + "reference_name": asset.name, + "cost_center": "" } debit_entry = { @@ -196,12 +197,14 @@ def get_gl_entries_on_asset_disposal(asset, selling_amount=0, finance_book=None) { "account": fixed_asset_account, "credit_in_account_currency": asset.gross_purchase_amount, - "credit": asset.gross_purchase_amount + "credit": asset.gross_purchase_amount, + "cost_center": depreciation_cost_center }, { "account": accumulated_depr_account, "debit_in_account_currency": accumulated_depr_amount, - "debit": accumulated_depr_amount + "debit": accumulated_depr_amount, + "cost_center": depreciation_cost_center } ] diff --git a/erpnext/buying/report/procurement_tracker/test_procurement_tracker.py b/erpnext/buying/report/procurement_tracker/test_procurement_tracker.py index c7204a1f34..44ab767c0a 100644 --- a/erpnext/buying/report/procurement_tracker/test_procurement_tracker.py +++ b/erpnext/buying/report/procurement_tracker/test_procurement_tracker.py @@ -67,4 +67,5 @@ class TestProcurementTracker(unittest.TestCase): "expected_delivery_date": date_obj, "actual_delivery_date": date_obj } + return expected_data \ No newline at end of file diff --git a/erpnext/controllers/stock_controller.py b/erpnext/controllers/stock_controller.py index 759c6cd73e..e8483da544 100644 --- a/erpnext/controllers/stock_controller.py +++ b/erpnext/controllers/stock_controller.py @@ -96,6 +96,7 @@ class StockController(AccountsController): "account": warehouse_account[sle.warehouse]["account"], "against": item_row.expense_account, "cost_center": item_row.cost_center, + "project": item_row.project or self.get('project'), "remarks": self.get("remarks") or "Accounting Entry for Stock", "debit": flt(sle.stock_value_difference, precision), "is_opening": item_row.get("is_opening") or self.get("is_opening") or "No", @@ -106,6 +107,7 @@ class StockController(AccountsController): "account": item_row.expense_account, "against": warehouse_account[sle.warehouse]["account"], "cost_center": item_row.cost_center, + "project": item_row.project or self.get('project'), "remarks": self.get("remarks") or "Accounting Entry for Stock", "credit": flt(sle.stock_value_difference, precision), "project": item_row.get("project") or self.get("project"), diff --git a/erpnext/hr/doctype/employee_advance/employee_advance.py b/erpnext/hr/doctype/employee_advance/employee_advance.py index 76195812c8..3c435b8cc3 100644 --- a/erpnext/hr/doctype/employee_advance/employee_advance.py +++ b/erpnext/hr/doctype/employee_advance/employee_advance.py @@ -120,12 +120,14 @@ def make_bank_entry(dt, dn): "reference_type": "Employee Advance", "reference_name": doc.name, "party_type": "Employee", + "cost_center": erpnext.get_default_cost_center(doc.company), "party": doc.employee, "is_advance": "Yes" }) je.append("accounts", { "account": payment_account.account, + "cost_center": erpnext.get_default_cost_center(doc.company), "credit_in_account_currency": flt(doc.advance_amount), "account_currency": payment_account.account_currency, "account_type": payment_account.account_type diff --git a/erpnext/hr/doctype/expense_claim/expense_claim.py b/erpnext/hr/doctype/expense_claim/expense_claim.py index 5563c245f4..bf893d5fab 100644 --- a/erpnext/hr/doctype/expense_claim/expense_claim.py +++ b/erpnext/hr/doctype/expense_claim/expense_claim.py @@ -295,7 +295,7 @@ def make_bank_entry(dt, dn): je = frappe.new_doc("Journal Entry") je.voucher_type = 'Bank Entry' je.company = expense_claim.company - je.remark = 'Payment against Expense Claim: ' + dn; + je.remark = 'Payment against Expense Claim: ' + dn je.append("accounts", { "account": expense_claim.payable_account, @@ -303,6 +303,7 @@ def make_bank_entry(dt, dn): "reference_type": "Expense Claim", "party_type": "Employee", "party": expense_claim.employee, + "cost_center": erpnext.get_default_cost_center(expense_claim.company), "reference_name": expense_claim.name }) @@ -313,6 +314,7 @@ def make_bank_entry(dt, dn): "reference_name": expense_claim.name, "balance": default_bank_cash_account.balance, "account_currency": default_bank_cash_account.account_currency, + "cost_center": erpnext.get_default_cost_center(expense_claim.company), "account_type": default_bank_cash_account.account_type }) diff --git a/erpnext/maintenance/doctype/maintenance_schedule/maintenance_schedule.py b/erpnext/maintenance/doctype/maintenance_schedule/maintenance_schedule.py index b58f999cfb..add7bbfa57 100644 --- a/erpnext/maintenance/doctype/maintenance_schedule/maintenance_schedule.py +++ b/erpnext/maintenance/doctype/maintenance_schedule/maintenance_schedule.py @@ -44,7 +44,7 @@ class MaintenanceSchedule(TransactionBase): for d in self.get('items'): if d.serial_no: serial_nos = get_valid_serial_nos(d.serial_no) - self.validate_serial_no(serial_nos, d.start_date) + self.validate_serial_no(d.item_code, serial_nos, d.start_date) self.update_amc_date(serial_nos, d.end_date) no_email_sp = [] @@ -178,14 +178,18 @@ class MaintenanceSchedule(TransactionBase): serial_no_doc.amc_expiry_date = amc_expiry_date serial_no_doc.save() - def validate_serial_no(self, serial_nos, amc_start_date): + def validate_serial_no(self, item_code, serial_nos, amc_start_date): for serial_no in serial_nos: sr_details = frappe.db.get_value("Serial No", serial_no, - ["warranty_expiry_date", "amc_expiry_date", "warehouse", "delivery_date"], as_dict=1) + ["warranty_expiry_date", "amc_expiry_date", "warehouse", "delivery_date", "item_code"], as_dict=1) if not sr_details: frappe.throw(_("Serial No {0} not found").format(serial_no)) + if sr_details.get("item_code") != item_code: + frappe.throw(_("Serial No {0} does not belong to Item {1}") + .format(frappe.bold(serial_no), frappe.bold(item_code)), title="Invalid") + if sr_details.warranty_expiry_date \ and getdate(sr_details.warranty_expiry_date) >= getdate(amc_start_date): throw(_("Serial No {0} is under warranty upto {1}") diff --git a/erpnext/patches.txt b/erpnext/patches.txt index cd4a221843..566b979ade 100644 --- a/erpnext/patches.txt +++ b/erpnext/patches.txt @@ -697,6 +697,7 @@ execute:frappe.rename_doc("Desk Page", "Loan Management", "Loan", force=True) erpnext.patches.v12_0.update_uom_conversion_factor erpnext.patches.v13_0.delete_old_purchase_reports erpnext.patches.v12_0.set_italian_import_supplier_invoice_permissions +erpnext.patches.v12_0.unhide_cost_center_field erpnext.patches.v13_0.update_sla_enhancements erpnext.patches.v12_0.update_address_template_for_india erpnext.patches.v13_0.update_deferred_settings diff --git a/erpnext/patches/v12_0/unhide_cost_center_field.py b/erpnext/patches/v12_0/unhide_cost_center_field.py new file mode 100644 index 0000000000..6005ab7072 --- /dev/null +++ b/erpnext/patches/v12_0/unhide_cost_center_field.py @@ -0,0 +1,13 @@ +# Copyright (c) 2017, Frappe and Contributors +# License: GNU General Public License v3. See license.txt + +from __future__ import unicode_literals +import frappe + +def execute(): + frappe.db.sql(""" + DELETE FROM `tabProperty Setter` + WHERE doc_type in ('Sales Invoice', 'Purchase Invoice', 'Payment Entry') + AND field_name = 'cost_center' + AND property = 'hidden' + """) \ No newline at end of file diff --git a/erpnext/projects/doctype/project/test_project.py b/erpnext/projects/doctype/project/test_project.py index 06c62b62d2..0c4f6f1bdf 100644 --- a/erpnext/projects/doctype/project/test_project.py +++ b/erpnext/projects/doctype/project/test_project.py @@ -7,7 +7,7 @@ import frappe, unittest test_records = frappe.get_test_records('Project') test_ignore = ["Sales Order"] -from erpnext.projects.doctype.project_template.test_project_template import get_project_template +from erpnext.projects.doctype.project_template.test_project_template import get_project_template, make_project_template from erpnext.projects.doctype.project.project import set_project_status from frappe.utils import getdate @@ -43,4 +43,24 @@ def get_project(name): expected_start_date = '2019-01-01' )).insert() + return project + +def make_project(args): + args = frappe._dict(args) + if args.project_template_name: + template = make_project_template(args.project_template_name) + else: + template = get_project_template() + + project = frappe.get_doc(dict( + doctype = 'Project', + project_name = args.project_name, + status = 'Open', + project_template = template.name, + expected_start_date = args.start_date + )) + + if not frappe.db.exists("Project", args.project_name): + project.insert() + return project \ No newline at end of file diff --git a/erpnext/projects/doctype/project_template/test_project_template.py b/erpnext/projects/doctype/project_template/test_project_template.py index efcb2eab68..2c5831a5dc 100644 --- a/erpnext/projects/doctype/project_template/test_project_template.py +++ b/erpnext/projects/doctype/project_template/test_project_template.py @@ -26,4 +26,23 @@ def get_project_template(): ] )).insert() - return frappe.get_doc('Project Template', 'Test Project Template') \ No newline at end of file + return frappe.get_doc('Project Template', 'Test Project Template') + +def make_project_template(project_template_name, project_tasks=[]): + if not frappe.db.exists('Project Template', project_template_name): + frappe.get_doc(dict( + doctype = 'Project Template', + name = project_template_name, + tasks = project_tasks or [ + dict(subject='Task 1', description='Task 1 description', + start=0, duration=3), + dict(subject='Task 2', description='Task 2 description', + start=0, duration=2), + dict(subject='Task 3', description='Task 3 description', + start=2, duration=4), + dict(subject='Task 4', description='Task 4 description', + start=3, duration=2), + ] + )).insert() + + return frappe.get_doc('Project Template', project_template_name) \ No newline at end of file diff --git a/erpnext/projects/doctype/task/task.py b/erpnext/projects/doctype/task/task.py index 3b75cf4215..4bdda68b69 100755 --- a/erpnext/projects/doctype/task/task.py +++ b/erpnext/projects/doctype/task/task.py @@ -9,7 +9,7 @@ import frappe from frappe import _, throw from frappe.desk.form.assign_to import clear, close_all_assignments from frappe.model.mapper import get_mapped_doc -from frappe.utils import add_days, cstr, date_diff, get_link_to_form, getdate, today +from frappe.utils import add_days, cstr, date_diff, get_link_to_form, getdate, today, flt from frappe.utils.nestedset import NestedSet @@ -63,10 +63,10 @@ class Task(NestedSet): close_all_assignments(self.doctype, self.name) def validate_progress(self): - if (self.progress or 0) > 100: + if flt(self.progress or 0) > 100: frappe.throw(_("Progress % for a task cannot be more than 100.")) - if self.progress == 100: + if flt(self.progress) == 100: self.status = 'Completed' if self.status == 'Completed': diff --git a/erpnext/public/js/help_links.js b/erpnext/public/js/help_links.js index 17b726ee18..66ff46405d 100644 --- a/erpnext/public/js/help_links.js +++ b/erpnext/public/js/help_links.js @@ -450,7 +450,7 @@ frappe.help.help_links['Form/Opportunity'] = [ ] frappe.help.help_links['Form/Address'] = [ - { label: 'Address', url: docsUrl + 'user/manual/en/CRM/contact' }, + { label: 'Address', url: docsUrl + 'user/manual/en/CRM/address' }, ] frappe.help.help_links['Form/Contact'] = [ diff --git a/erpnext/regional/report/datev/test_datev.py b/erpnext/regional/report/datev/test_datev.py index 3cc65fe9d3..eed62a8690 100644 --- a/erpnext/regional/report/datev/test_datev.py +++ b/erpnext/regional/report/datev/test_datev.py @@ -90,7 +90,7 @@ def make_customer_with_account(customer_name, company): if not frappe.db.exists("Customer", customer_name): customer = frappe.get_doc({ - "doctype": "Customer", + "doctype": "Customer", "customer_name": customer_name, "customer_type": "Company", "accounts": [{ @@ -155,17 +155,17 @@ class TestDatev(TestCase): setup_fiscal_year() warehouse = frappe.db.get_value("Item Default", { - "parent": item.name, + "parent": item.name, "company": self.company.name }, "default_warehouse") income_account = frappe.db.get_value("Account", { - "account_number": "4200", + "account_number": "4200", "company": self.company.name }, "name") tax_account = frappe.db.get_value("Account", { - "account_number": "3806", + "account_number": "3806", "company": self.company.name }, "name") @@ -186,9 +186,12 @@ class TestDatev(TestCase): "charge_type": "On Net Total", "account_head": tax_account, "description": "Umsatzsteuer 19 %", - "rate": 19 + "rate": 19, + "cost_center": self.company.cost_center }) + si.cost_center = self.company.cost_center + si.save() si.submit() @@ -196,7 +199,7 @@ class TestDatev(TestCase): def is_subset(get_data, allowed_keys): """ Validate that the dict contains only allowed keys. - + Params: get_data -- Function that returns a list of dicts. allowed_keys -- List of allowed keys diff --git a/erpnext/selling/doctype/quotation/quotation_list.js b/erpnext/selling/doctype/quotation/quotation_list.js index 802c0ba641..f425acf180 100644 --- a/erpnext/selling/doctype/quotation/quotation_list.js +++ b/erpnext/selling/doctype/quotation/quotation_list.js @@ -3,13 +3,15 @@ frappe.listview_settings['Quotation'] = { "company", "currency", 'valid_till'], onload: function(listview) { - listview.page.fields_dict.quotation_to.get_query = function() { - return { - "filters": { - "name": ["in", ["Customer", "Lead"]], - } + if (listview.page.fields_dict.quotation_to) { + listview.page.fields_dict.quotation_to.get_query = function() { + return { + "filters": { + "name": ["in", ["Customer", "Lead"]], + } + }; }; - }; + } }, get_indicator: function(doc) { diff --git a/erpnext/stock/doctype/delivery_note/test_delivery_note.py b/erpnext/stock/doctype/delivery_note/test_delivery_note.py index a921a56f53..4b04a0a8c3 100644 --- a/erpnext/stock/doctype/delivery_note/test_delivery_note.py +++ b/erpnext/stock/doctype/delivery_note/test_delivery_note.py @@ -537,11 +537,8 @@ class TestDeliveryNote(unittest.TestCase): dt = make_delivery_trip(dn.name) self.assertEqual(dn.name, dt.delivery_stops[0].delivery_note) - def test_delivery_note_for_enable_allow_cost_center_in_entry_of_bs_account(self): + def test_delivery_note_with_cost_center(self): from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 1 - accounts_settings.save() cost_center = "_Test Cost Center for BS Account - TCP1" create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company with perpetual inventory") @@ -567,13 +564,8 @@ class TestDeliveryNote(unittest.TestCase): } for i, gle in enumerate(gl_entries): self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center) - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() - def test_delivery_note_for_disable_allow_cost_center_in_entry_of_bs_account(self): - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() + def test_delivery_note_cost_center_with_balance_sheet_account(self): cost_center = "Main - TCP1" company = frappe.db.get_value('Warehouse', 'Stores - TCP1', 'company') @@ -583,7 +575,11 @@ class TestDeliveryNote(unittest.TestCase): make_stock_entry(target="Stores - TCP1", qty=5, basic_rate=100) stock_in_hand_account = get_inventory_account('_Test Company with perpetual inventory') - dn = create_delivery_note(company='_Test Company with perpetual inventory', warehouse='Stores - TCP1', cost_center = 'Main - TCP1', expense_account = "Cost of Goods Sold - TCP1") + dn = create_delivery_note(company='_Test Company with perpetual inventory', warehouse='Stores - TCP1', cost_center = 'Main - TCP1', expense_account = "Cost of Goods Sold - TCP1", + do_not_submit=1) + + dn.get('items')[0].cost_center = None + dn.submit() gl_entries = get_gl_entries("Delivery Note", dn.name) @@ -593,7 +589,7 @@ class TestDeliveryNote(unittest.TestCase): "cost_center": cost_center }, stock_in_hand_account: { - "cost_center": None + "cost_center": cost_center } } for i, gle in enumerate(gl_entries): diff --git a/erpnext/stock/doctype/delivery_note_item/delivery_note_item.json b/erpnext/stock/doctype/delivery_note_item/delivery_note_item.json index 7ea2de2753..7c92ac7dbb 100644 --- a/erpnext/stock/doctype/delivery_note_item/delivery_note_item.json +++ b/erpnext/stock/doctype/delivery_note_item/delivery_note_item.json @@ -1,5 +1,4 @@ { - "actions": [], "autoname": "hash", "creation": "2013-04-22 13:15:44", "doctype": "DocType", @@ -82,6 +81,7 @@ "accounting_dimensions_section", "cost_center", "dimension_col_break", + "project", "section_break_72", "page_break" ], @@ -701,6 +701,12 @@ "fieldname": "dimension_col_break", "fieldtype": "Column Break" }, + { + "fieldname": "project", + "fieldtype": "Link", + "label": "Project", + "options": "Project" + }, { "fieldname": "dn_detail", "fieldtype": "Data", @@ -714,7 +720,7 @@ "idx": 1, "istable": 1, "links": [], - "modified": "2020-03-05 14:18:33.131672", + "modified": "2020-03-11 12:25:06.177894", "modified_by": "Administrator", "module": "Stock", "name": "Delivery Note Item", diff --git a/erpnext/stock/doctype/purchase_receipt/purchase_receipt.json b/erpnext/stock/doctype/purchase_receipt/purchase_receipt.json index 44d5f69028..3b92dac220 100755 --- a/erpnext/stock/doctype/purchase_receipt/purchase_receipt.json +++ b/erpnext/stock/doctype/purchase_receipt/purchase_receipt.json @@ -1,5 +1,4 @@ { - "actions": [], "allow_import": 1, "autoname": "naming_series:", "creation": "2013-05-21 16:16:39", @@ -108,6 +107,7 @@ "amended_from", "range", "column_break4", + "project", "per_billed", "is_internal_supplier", "inter_company_reference", @@ -1125,6 +1125,12 @@ "show_seconds": 1, "width": "50%" }, + { + "fieldname": "project", + "fieldtype": "Link", + "label": "Project", + "options": "Project" + }, { "fieldname": "per_billed", "fieldtype": "Percent", diff --git a/erpnext/stock/doctype/purchase_receipt/test_purchase_receipt.py b/erpnext/stock/doctype/purchase_receipt/test_purchase_receipt.py index 649cfdcaac..d97b9e82c3 100644 --- a/erpnext/stock/doctype/purchase_receipt/test_purchase_receipt.py +++ b/erpnext/stock/doctype/purchase_receipt/test_purchase_receipt.py @@ -403,11 +403,8 @@ class TestPurchaseReceipt(unittest.TestCase): pr_return.submit() - def test_purchase_receipt_for_enable_allow_cost_center_in_entry_of_bs_account(self): + def test_purchase_receipt_cost_center(self): from erpnext.accounts.doctype.cost_center.test_cost_center import create_cost_center - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 1 - accounts_settings.save() cost_center = "_Test Cost Center for BS Account - TCP1" create_cost_center(cost_center_name="_Test Cost Center for BS Account", company="_Test Company with perpetual inventory") @@ -435,14 +432,7 @@ class TestPurchaseReceipt(unittest.TestCase): for i, gle in enumerate(gl_entries): self.assertEqual(expected_values[gle.account]["cost_center"], gle.cost_center) - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() - - def test_purchase_receipt_for_disable_allow_cost_center_in_entry_of_bs_account(self): - accounts_settings = frappe.get_doc('Accounts Settings', 'Accounts Settings') - accounts_settings.allow_cost_center_in_entry_of_bs_account = 0 - accounts_settings.save() - + def test_purchase_receipt_cost_center_with_balance_sheet_account(self): if not frappe.db.exists('Location', 'Test Location'): frappe.get_doc({ 'doctype': 'Location', @@ -454,13 +444,14 @@ class TestPurchaseReceipt(unittest.TestCase): gl_entries = get_gl_entries("Purchase Receipt", pr.name) self.assertTrue(gl_entries) + cost_center = pr.get('items')[0].cost_center expected_values = { "Stock Received But Not Billed - TCP1": { - "cost_center": None + "cost_center": cost_center }, stock_in_hand_account: { - "cost_center": None + "cost_center": cost_center } } for i, gle in enumerate(gl_entries): diff --git a/erpnext/www/book-appointment/__init__.py b/erpnext/www/book-appointment/__init__.py deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/erpnext/www/book-appointment/verify/__init__.py b/erpnext/www/book-appointment/verify/__init__.py deleted file mode 100644 index e69de29bb2..0000000000