mirror of
https://github.com/frappe/erpnext.git
synced 2026-05-14 18:51:21 +00:00
Merge branch 'version-13-hotfix' of https://github.com/frappe/erpnext into gstr_1_cdnr_unregistered_json
This commit is contained in:
@@ -1010,21 +1010,21 @@ class TestPurchaseInvoice(unittest.TestCase):
|
|||||||
# Check GLE for Purchase Invoice
|
# Check GLE for Purchase Invoice
|
||||||
# Zero net effect on final TDS Payable on invoice
|
# Zero net effect on final TDS Payable on invoice
|
||||||
expected_gle = [
|
expected_gle = [
|
||||||
['_Test Account Cost for Goods Sold - _TC', 30000, 0],
|
['_Test Account Cost for Goods Sold - _TC', 30000],
|
||||||
['_Test Account Excise Duty - _TC', 0, 3000],
|
['_Test Account Excise Duty - _TC', -3000],
|
||||||
['Creditors - _TC', 0, 27000],
|
['Creditors - _TC', -27000],
|
||||||
['TDS Payable - _TC', 3000, 3000]
|
['TDS Payable - _TC', 0]
|
||||||
]
|
]
|
||||||
|
|
||||||
gl_entries = frappe.db.sql("""select account, debit, credit
|
gl_entries = frappe.db.sql("""select account, sum(debit - credit) as amount
|
||||||
from `tabGL Entry`
|
from `tabGL Entry`
|
||||||
where voucher_type='Purchase Invoice' and voucher_no=%s
|
where voucher_type='Purchase Invoice' and voucher_no=%s
|
||||||
|
group by account
|
||||||
order by account asc""", (purchase_invoice.name), as_dict=1)
|
order by account asc""", (purchase_invoice.name), as_dict=1)
|
||||||
|
|
||||||
for i, gle in enumerate(gl_entries):
|
for i, gle in enumerate(gl_entries):
|
||||||
self.assertEqual(expected_gle[i][0], gle.account)
|
self.assertEqual(expected_gle[i][0], gle.account)
|
||||||
self.assertEqual(expected_gle[i][1], gle.debit)
|
self.assertEqual(expected_gle[i][1], gle.amount)
|
||||||
self.assertEqual(expected_gle[i][2], gle.credit)
|
|
||||||
|
|
||||||
def update_tax_witholding_category(company, account, date):
|
def update_tax_witholding_category(company, account, date):
|
||||||
from erpnext.accounts.utils import get_fiscal_year
|
from erpnext.accounts.utils import get_fiscal_year
|
||||||
|
|||||||
@@ -1957,6 +1957,33 @@ class TestSalesInvoice(unittest.TestCase):
|
|||||||
einvoice = make_einvoice(si)
|
einvoice = make_einvoice(si)
|
||||||
validate_totals(einvoice)
|
validate_totals(einvoice)
|
||||||
|
|
||||||
|
def test_item_tax_net_range(self):
|
||||||
|
item = create_item("T Shirt")
|
||||||
|
|
||||||
|
item.set('taxes', [])
|
||||||
|
item.append("taxes", {
|
||||||
|
"item_tax_template": "_Test Account Excise Duty @ 10 - _TC",
|
||||||
|
"minimum_net_rate": 0,
|
||||||
|
"maximum_net_rate": 500
|
||||||
|
})
|
||||||
|
|
||||||
|
item.append("taxes", {
|
||||||
|
"item_tax_template": "_Test Account Excise Duty @ 12 - _TC",
|
||||||
|
"minimum_net_rate": 501,
|
||||||
|
"maximum_net_rate": 1000
|
||||||
|
})
|
||||||
|
|
||||||
|
item.save()
|
||||||
|
|
||||||
|
sales_invoice = create_sales_invoice(item = "T Shirt", rate=700, do_not_submit=True)
|
||||||
|
self.assertEqual(sales_invoice.items[0].item_tax_template, "_Test Account Excise Duty @ 12 - _TC")
|
||||||
|
|
||||||
|
# Apply discount
|
||||||
|
sales_invoice.apply_discount_on = 'Net Total'
|
||||||
|
sales_invoice.discount_amount = 300
|
||||||
|
sales_invoice.save()
|
||||||
|
self.assertEqual(sales_invoice.items[0].item_tax_template, "_Test Account Excise Duty @ 10 - _TC")
|
||||||
|
|
||||||
def get_sales_invoice_for_e_invoice():
|
def get_sales_invoice_for_e_invoice():
|
||||||
si = make_sales_invoice_for_ewaybill()
|
si = make_sales_invoice_for_ewaybill()
|
||||||
si.naming_series = 'INV-2020-.#####'
|
si.naming_series = 'INV-2020-.#####'
|
||||||
@@ -1985,32 +2012,6 @@ def get_sales_invoice_for_e_invoice():
|
|||||||
|
|
||||||
return si
|
return si
|
||||||
|
|
||||||
def test_item_tax_net_range(self):
|
|
||||||
item = create_item("T Shirt")
|
|
||||||
|
|
||||||
item.set('taxes', [])
|
|
||||||
item.append("taxes", {
|
|
||||||
"item_tax_template": "_Test Account Excise Duty @ 10 - _TC",
|
|
||||||
"minimum_net_rate": 0,
|
|
||||||
"maximum_net_rate": 500
|
|
||||||
})
|
|
||||||
|
|
||||||
item.append("taxes", {
|
|
||||||
"item_tax_template": "_Test Account Excise Duty @ 12 - _TC",
|
|
||||||
"minimum_net_rate": 501,
|
|
||||||
"maximum_net_rate": 1000
|
|
||||||
})
|
|
||||||
|
|
||||||
item.save()
|
|
||||||
|
|
||||||
sales_invoice = create_sales_invoice(item = "T Shirt", rate=700, do_not_submit=True)
|
|
||||||
self.assertEqual(sales_invoice.items[0].item_tax_template, "_Test Account Excise Duty @ 12 - _TC")
|
|
||||||
|
|
||||||
# Apply discount
|
|
||||||
sales_invoice.apply_discount_on = 'Net Total'
|
|
||||||
sales_invoice.discount_amount = 300
|
|
||||||
sales_invoice.save()
|
|
||||||
self.assertEqual(sales_invoice.items[0].item_tax_template, "_Test Account Excise Duty @ 10 - _TC")
|
|
||||||
|
|
||||||
def make_test_address_for_ewaybill():
|
def make_test_address_for_ewaybill():
|
||||||
if not frappe.db.exists('Address', '_Test Address for Eway bill-Billing'):
|
if not frappe.db.exists('Address', '_Test Address for Eway bill-Billing'):
|
||||||
@@ -2087,9 +2088,9 @@ def make_sales_invoice_for_ewaybill():
|
|||||||
if not gst_account:
|
if not gst_account:
|
||||||
gst_settings.append("gst_accounts", {
|
gst_settings.append("gst_accounts", {
|
||||||
"company": "_Test Company",
|
"company": "_Test Company",
|
||||||
"cgst_account": "CGST - _TC",
|
"cgst_account": "Output Tax CGST - _TC",
|
||||||
"sgst_account": "SGST - _TC",
|
"sgst_account": "Output Tax SGST - _TC",
|
||||||
"igst_account": "IGST - _TC",
|
"igst_account": "Output Tax IGST - _TC",
|
||||||
})
|
})
|
||||||
|
|
||||||
gst_settings.save()
|
gst_settings.save()
|
||||||
@@ -2106,7 +2107,7 @@ def make_sales_invoice_for_ewaybill():
|
|||||||
|
|
||||||
si.append("taxes", {
|
si.append("taxes", {
|
||||||
"charge_type": "On Net Total",
|
"charge_type": "On Net Total",
|
||||||
"account_head": "CGST - _TC",
|
"account_head": "Output Tax CGST - _TC",
|
||||||
"cost_center": "Main - _TC",
|
"cost_center": "Main - _TC",
|
||||||
"description": "CGST @ 9.0",
|
"description": "CGST @ 9.0",
|
||||||
"rate": 9
|
"rate": 9
|
||||||
@@ -2114,7 +2115,7 @@ def make_sales_invoice_for_ewaybill():
|
|||||||
|
|
||||||
si.append("taxes", {
|
si.append("taxes", {
|
||||||
"charge_type": "On Net Total",
|
"charge_type": "On Net Total",
|
||||||
"account_head": "SGST - _TC",
|
"account_head": "Output Tax SGST - _TC",
|
||||||
"cost_center": "Main - _TC",
|
"cost_center": "Main - _TC",
|
||||||
"description": "SGST @ 9.0",
|
"description": "SGST @ 9.0",
|
||||||
"rate": 9
|
"rate": 9
|
||||||
|
|||||||
@@ -380,7 +380,7 @@ def set_gl_entries_by_account(from_date, to_date, root_lft, root_rgt, filters, g
|
|||||||
gl_entries = frappe.db.sql("""select gl.posting_date, gl.account, gl.debit, gl.credit, gl.is_opening, gl.company,
|
gl_entries = frappe.db.sql("""select gl.posting_date, gl.account, gl.debit, gl.credit, gl.is_opening, gl.company,
|
||||||
gl.fiscal_year, gl.debit_in_account_currency, gl.credit_in_account_currency, gl.account_currency,
|
gl.fiscal_year, gl.debit_in_account_currency, gl.credit_in_account_currency, gl.account_currency,
|
||||||
acc.account_name, acc.account_number
|
acc.account_name, acc.account_number
|
||||||
from `tabGL Entry` gl, `tabAccount` acc where acc.name = gl.account and gl.company = %(company)s
|
from `tabGL Entry` gl, `tabAccount` acc where acc.name = gl.account and gl.company = %(company)s and gl.is_cancelled = 0
|
||||||
{additional_conditions} and gl.posting_date <= %(to_date)s and acc.lft >= %(lft)s and acc.rgt <= %(rgt)s
|
{additional_conditions} and gl.posting_date <= %(to_date)s and acc.lft >= %(lft)s and acc.rgt <= %(rgt)s
|
||||||
order by gl.account, gl.posting_date""".format(additional_conditions=additional_conditions),
|
order by gl.account, gl.posting_date""".format(additional_conditions=additional_conditions),
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -784,7 +784,7 @@ def get_children(doctype, parent, company, is_root=False):
|
|||||||
return acc
|
return acc
|
||||||
|
|
||||||
def create_payment_gateway_account(gateway, payment_channel="Email"):
|
def create_payment_gateway_account(gateway, payment_channel="Email"):
|
||||||
from erpnext.setup.setup_wizard.operations.company_setup import create_bank_account
|
from erpnext.setup.setup_wizard.operations.install_fixtures import create_bank_account
|
||||||
|
|
||||||
company = frappe.db.get_value("Global Defaults", None, "default_company")
|
company = frappe.db.get_value("Global Defaults", None, "default_company")
|
||||||
if not company:
|
if not company:
|
||||||
|
|||||||
@@ -7,16 +7,21 @@ import frappe
|
|||||||
import unittest
|
import unittest
|
||||||
from erpnext.erpnext_integrations.doctype.mpesa_settings.mpesa_settings import process_balance_info, verify_transaction
|
from erpnext.erpnext_integrations.doctype.mpesa_settings.mpesa_settings import process_balance_info, verify_transaction
|
||||||
from erpnext.accounts.doctype.pos_invoice.test_pos_invoice import create_pos_invoice
|
from erpnext.accounts.doctype.pos_invoice.test_pos_invoice import create_pos_invoice
|
||||||
|
from erpnext.erpnext_integrations.utils import create_mode_of_payment
|
||||||
|
|
||||||
class TestMpesaSettings(unittest.TestCase):
|
class TestMpesaSettings(unittest.TestCase):
|
||||||
|
def setUp(self):
|
||||||
|
# create payment gateway in setup
|
||||||
|
create_mpesa_settings(payment_gateway_name="_Test")
|
||||||
|
create_mpesa_settings(payment_gateway_name="_Account Balance")
|
||||||
|
create_mpesa_settings(payment_gateway_name="Payment")
|
||||||
|
|
||||||
def tearDown(self):
|
def tearDown(self):
|
||||||
frappe.db.sql('delete from `tabMpesa Settings`')
|
frappe.db.sql('delete from `tabMpesa Settings`')
|
||||||
frappe.db.sql('delete from `tabIntegration Request` where integration_request_service = "Mpesa"')
|
frappe.db.sql('delete from `tabIntegration Request` where integration_request_service = "Mpesa"')
|
||||||
|
|
||||||
def test_creation_of_payment_gateway(self):
|
def test_creation_of_payment_gateway(self):
|
||||||
create_mpesa_settings(payment_gateway_name="_Test")
|
mode_of_payment = create_mode_of_payment('Mpesa-_Test', payment_type="Phone")
|
||||||
|
|
||||||
mode_of_payment = frappe.get_doc("Mode of Payment", "Mpesa-_Test")
|
|
||||||
self.assertTrue(frappe.db.exists("Payment Gateway Account", {'payment_gateway': "Mpesa-_Test"}))
|
self.assertTrue(frappe.db.exists("Payment Gateway Account", {'payment_gateway': "Mpesa-_Test"}))
|
||||||
self.assertTrue(mode_of_payment.name)
|
self.assertTrue(mode_of_payment.name)
|
||||||
self.assertEqual(mode_of_payment.type, "Phone")
|
self.assertEqual(mode_of_payment.type, "Phone")
|
||||||
@@ -47,7 +52,6 @@ class TestMpesaSettings(unittest.TestCase):
|
|||||||
integration_request.delete()
|
integration_request.delete()
|
||||||
|
|
||||||
def test_processing_of_callback_payload(self):
|
def test_processing_of_callback_payload(self):
|
||||||
create_mpesa_settings(payment_gateway_name="Payment")
|
|
||||||
mpesa_account = frappe.db.get_value("Payment Gateway Account", {"payment_gateway": 'Mpesa-Payment'}, "payment_account")
|
mpesa_account = frappe.db.get_value("Payment Gateway Account", {"payment_gateway": 'Mpesa-Payment'}, "payment_account")
|
||||||
frappe.db.set_value("Account", mpesa_account, "account_currency", "KES")
|
frappe.db.set_value("Account", mpesa_account, "account_currency", "KES")
|
||||||
frappe.db.set_value("Customer", "_Test Customer", "default_currency", "KES")
|
frappe.db.set_value("Customer", "_Test Customer", "default_currency", "KES")
|
||||||
@@ -90,7 +94,6 @@ class TestMpesaSettings(unittest.TestCase):
|
|||||||
pos_invoice.delete()
|
pos_invoice.delete()
|
||||||
|
|
||||||
def test_processing_of_multiple_callback_payload(self):
|
def test_processing_of_multiple_callback_payload(self):
|
||||||
create_mpesa_settings(payment_gateway_name="Payment")
|
|
||||||
mpesa_account = frappe.db.get_value("Payment Gateway Account", {"payment_gateway": 'Mpesa-Payment'}, "payment_account")
|
mpesa_account = frappe.db.get_value("Payment Gateway Account", {"payment_gateway": 'Mpesa-Payment'}, "payment_account")
|
||||||
frappe.db.set_value("Account", mpesa_account, "account_currency", "KES")
|
frappe.db.set_value("Account", mpesa_account, "account_currency", "KES")
|
||||||
frappe.db.set_value("Mpesa Settings", "Payment", "transaction_limit", "500")
|
frappe.db.set_value("Mpesa Settings", "Payment", "transaction_limit", "500")
|
||||||
@@ -141,7 +144,6 @@ class TestMpesaSettings(unittest.TestCase):
|
|||||||
pos_invoice.delete()
|
pos_invoice.delete()
|
||||||
|
|
||||||
def test_processing_of_only_one_succes_callback_payload(self):
|
def test_processing_of_only_one_succes_callback_payload(self):
|
||||||
create_mpesa_settings(payment_gateway_name="Payment")
|
|
||||||
mpesa_account = frappe.db.get_value("Payment Gateway Account", {"payment_gateway": 'Mpesa-Payment'}, "payment_account")
|
mpesa_account = frappe.db.get_value("Payment Gateway Account", {"payment_gateway": 'Mpesa-Payment'}, "payment_account")
|
||||||
frappe.db.set_value("Account", mpesa_account, "account_currency", "KES")
|
frappe.db.set_value("Account", mpesa_account, "account_currency", "KES")
|
||||||
frappe.db.set_value("Mpesa Settings", "Payment", "transaction_limit", "500")
|
frappe.db.set_value("Mpesa Settings", "Payment", "transaction_limit", "500")
|
||||||
@@ -202,6 +204,7 @@ def create_mpesa_settings(payment_gateway_name="Express"):
|
|||||||
|
|
||||||
doc = frappe.get_doc(dict( #nosec
|
doc = frappe.get_doc(dict( #nosec
|
||||||
doctype="Mpesa Settings",
|
doctype="Mpesa Settings",
|
||||||
|
sandbox=1,
|
||||||
payment_gateway_name=payment_gateway_name,
|
payment_gateway_name=payment_gateway_name,
|
||||||
consumer_key="5sMu9LVI1oS3oBGPJfh3JyvLHwZOdTKn",
|
consumer_key="5sMu9LVI1oS3oBGPJfh3JyvLHwZOdTKn",
|
||||||
consumer_secret="VI1oS3oBGPJfh3JyvLHw",
|
consumer_secret="VI1oS3oBGPJfh3JyvLHw",
|
||||||
|
|||||||
@@ -52,7 +52,8 @@ def create_mode_of_payment(gateway, payment_type="General"):
|
|||||||
"payment_gateway": gateway
|
"payment_gateway": gateway
|
||||||
}, ['payment_account'])
|
}, ['payment_account'])
|
||||||
|
|
||||||
if not frappe.db.exists("Mode of Payment", gateway) and payment_gateway_account:
|
mode_of_payment = frappe.db.exists("Mode of Payment", gateway)
|
||||||
|
if not mode_of_payment and payment_gateway_account:
|
||||||
mode_of_payment = frappe.get_doc({
|
mode_of_payment = frappe.get_doc({
|
||||||
"doctype": "Mode of Payment",
|
"doctype": "Mode of Payment",
|
||||||
"mode_of_payment": gateway,
|
"mode_of_payment": gateway,
|
||||||
@@ -66,6 +67,10 @@ def create_mode_of_payment(gateway, payment_type="General"):
|
|||||||
})
|
})
|
||||||
mode_of_payment.insert(ignore_permissions=True)
|
mode_of_payment.insert(ignore_permissions=True)
|
||||||
|
|
||||||
|
return mode_of_payment
|
||||||
|
elif mode_of_payment:
|
||||||
|
return frappe.get_doc("Mode of Payment", mode_of_payment)
|
||||||
|
|
||||||
def get_tracking_url(carrier, tracking_number):
|
def get_tracking_url(carrier, tracking_number):
|
||||||
# Return the formatted Tracking URL.
|
# Return the formatted Tracking URL.
|
||||||
tracking_url = ''
|
tracking_url = ''
|
||||||
|
|||||||
@@ -72,7 +72,8 @@ class TestExpenseClaim(unittest.TestCase):
|
|||||||
def test_expense_claim_gl_entry(self):
|
def test_expense_claim_gl_entry(self):
|
||||||
payable_account = get_payable_account(company_name)
|
payable_account = get_payable_account(company_name)
|
||||||
taxes = generate_taxes()
|
taxes = generate_taxes()
|
||||||
expense_claim = make_expense_claim(payable_account, 300, 200, company_name, "Travel Expenses - _TC4", do_not_submit=True, taxes=taxes)
|
expense_claim = make_expense_claim(payable_account, 300, 200, company_name, "Travel Expenses - _TC4",
|
||||||
|
do_not_submit=True, taxes=taxes)
|
||||||
expense_claim.submit()
|
expense_claim.submit()
|
||||||
|
|
||||||
gl_entries = frappe.db.sql("""select account, debit, credit
|
gl_entries = frappe.db.sql("""select account, debit, credit
|
||||||
@@ -82,7 +83,7 @@ class TestExpenseClaim(unittest.TestCase):
|
|||||||
self.assertTrue(gl_entries)
|
self.assertTrue(gl_entries)
|
||||||
|
|
||||||
expected_values = dict((d[0], d) for d in [
|
expected_values = dict((d[0], d) for d in [
|
||||||
['CGST - _TC4',18.0, 0.0],
|
['Output Tax CGST - _TC4',18.0, 0.0],
|
||||||
[payable_account, 0.0, 218.0],
|
[payable_account, 0.0, 218.0],
|
||||||
["Travel Expenses - _TC4", 200.0, 0.0]
|
["Travel Expenses - _TC4", 200.0, 0.0]
|
||||||
])
|
])
|
||||||
@@ -145,7 +146,7 @@ def generate_taxes():
|
|||||||
parent_account = frappe.db.get_value('Account',
|
parent_account = frappe.db.get_value('Account',
|
||||||
{'company': company_name, 'is_group':1, 'account_type': 'Tax'},
|
{'company': company_name, 'is_group':1, 'account_type': 'Tax'},
|
||||||
'name')
|
'name')
|
||||||
account = create_account(company=company_name, account_name="CGST", account_type="Tax", parent_account=parent_account)
|
account = create_account(company=company_name, account_name="Output Tax CGST", account_type="Tax", parent_account=parent_account)
|
||||||
return {'taxes':[{
|
return {'taxes':[{
|
||||||
"account_head": account,
|
"account_head": account,
|
||||||
"rate": 0,
|
"rate": 0,
|
||||||
|
|||||||
@@ -70,12 +70,12 @@ def get_bom_stock(filters):
|
|||||||
ON bom_item.item_code = ledger.item_code
|
ON bom_item.item_code = ledger.item_code
|
||||||
{conditions}
|
{conditions}
|
||||||
WHERE
|
WHERE
|
||||||
bom_item.parent = '{bom}' and bom_item.parenttype='BOM'
|
bom_item.parent = {bom} and bom_item.parenttype='BOM'
|
||||||
|
|
||||||
GROUP BY bom_item.item_code""".format(
|
GROUP BY bom_item.item_code""".format(
|
||||||
qty_field=qty_field,
|
qty_field=qty_field,
|
||||||
table=table,
|
table=table,
|
||||||
conditions=conditions,
|
conditions=conditions,
|
||||||
bom=bom,
|
bom=frappe.db.escape(bom),
|
||||||
qty_to_produce=qty_to_produce or 1)
|
qty_to_produce=qty_to_produce or 1)
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -147,7 +147,7 @@ erpnext.setup.slides_settings = [
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Validate bank name
|
// Validate bank name
|
||||||
if(me.values.bank_account){
|
if(me.values.bank_account) {
|
||||||
frappe.call({
|
frappe.call({
|
||||||
async: false,
|
async: false,
|
||||||
method: "erpnext.accounts.doctype.account.chart_of_accounts.chart_of_accounts.validate_bank_account",
|
method: "erpnext.accounts.doctype.account.chart_of_accounts.chart_of_accounts.validate_bank_account",
|
||||||
|
|||||||
@@ -35,6 +35,7 @@ frappe.ui.form.on('GST Settings', {
|
|||||||
return {
|
return {
|
||||||
filters: {
|
filters: {
|
||||||
company: row.company,
|
company: row.company,
|
||||||
|
account_type: "Tax",
|
||||||
is_group: 0
|
is_group: 0
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -19,6 +19,21 @@ class GSTSettings(Document):
|
|||||||
from tabAddress where country = "India" and ifnull(gstin, '')!='' ''')
|
from tabAddress where country = "India" and ifnull(gstin, '')!='' ''')
|
||||||
self.set_onload('data', data)
|
self.set_onload('data', data)
|
||||||
|
|
||||||
|
def validate(self):
|
||||||
|
# Validate duplicate accounts
|
||||||
|
self.validate_duplicate_accounts()
|
||||||
|
|
||||||
|
def validate_duplicate_accounts(self):
|
||||||
|
account_list = []
|
||||||
|
for account in self.get('gst_accounts'):
|
||||||
|
for fieldname in ['cgst_account', 'sgst_account', 'igst_account', 'cess_account']:
|
||||||
|
if account.get(fieldname) in account_list:
|
||||||
|
frappe.throw(_("Account {0} appears multiple times").format(
|
||||||
|
frappe.bold(account.get(fieldname))))
|
||||||
|
|
||||||
|
if account.get(fieldname):
|
||||||
|
account_list.append(account.get(fieldname))
|
||||||
|
|
||||||
@frappe.whitelist()
|
@frappe.whitelist()
|
||||||
def send_reminder():
|
def send_reminder():
|
||||||
frappe.has_permission('GST Settings', throw=True)
|
frappe.has_permission('GST Settings', throw=True)
|
||||||
|
|||||||
@@ -46,14 +46,14 @@ class TestGSTR3BReport(unittest.TestCase):
|
|||||||
make_sales_invoice()
|
make_sales_invoice()
|
||||||
create_purchase_invoices()
|
create_purchase_invoices()
|
||||||
|
|
||||||
if frappe.db.exists("GSTR 3B Report", "GSTR3B-March-2019-_Test Address-Billing"):
|
if frappe.db.exists("GSTR 3B Report", "GSTR3B-March-2019-_Test Address GST-Billing"):
|
||||||
report = frappe.get_doc("GSTR 3B Report", "GSTR3B-March-2019-_Test Address-Billing")
|
report = frappe.get_doc("GSTR 3B Report", "GSTR3B-March-2019-_Test Address GST-Billing")
|
||||||
report.save()
|
report.save()
|
||||||
else:
|
else:
|
||||||
report = frappe.get_doc({
|
report = frappe.get_doc({
|
||||||
"doctype": "GSTR 3B Report",
|
"doctype": "GSTR 3B Report",
|
||||||
"company": "_Test Company GST",
|
"company": "_Test Company GST",
|
||||||
"company_address": "_Test Address-Billing",
|
"company_address": "_Test Address GST-Billing",
|
||||||
"year": getdate().year,
|
"year": getdate().year,
|
||||||
"month": month_number_mapping.get(getdate().month)
|
"month": month_number_mapping.get(getdate().month)
|
||||||
}).insert()
|
}).insert()
|
||||||
@@ -89,7 +89,7 @@ class TestGSTR3BReport(unittest.TestCase):
|
|||||||
|
|
||||||
si.append("taxes", {
|
si.append("taxes", {
|
||||||
"charge_type": "On Net Total",
|
"charge_type": "On Net Total",
|
||||||
"account_head": "IGST - _GST",
|
"account_head": "Output Tax IGST - _GST",
|
||||||
"cost_center": "Main - _GST",
|
"cost_center": "Main - _GST",
|
||||||
"description": "IGST @ 18.0",
|
"description": "IGST @ 18.0",
|
||||||
"rate": 18
|
"rate": 18
|
||||||
@@ -117,7 +117,7 @@ def make_sales_invoice():
|
|||||||
|
|
||||||
si.append("taxes", {
|
si.append("taxes", {
|
||||||
"charge_type": "On Net Total",
|
"charge_type": "On Net Total",
|
||||||
"account_head": "IGST - _GST",
|
"account_head": "Output Tax IGST - _GST",
|
||||||
"cost_center": "Main - _GST",
|
"cost_center": "Main - _GST",
|
||||||
"description": "IGST @ 18.0",
|
"description": "IGST @ 18.0",
|
||||||
"rate": 18
|
"rate": 18
|
||||||
@@ -138,7 +138,7 @@ def make_sales_invoice():
|
|||||||
|
|
||||||
si1.append("taxes", {
|
si1.append("taxes", {
|
||||||
"charge_type": "On Net Total",
|
"charge_type": "On Net Total",
|
||||||
"account_head": "IGST - _GST",
|
"account_head": "Output Tax IGST - _GST",
|
||||||
"cost_center": "Main - _GST",
|
"cost_center": "Main - _GST",
|
||||||
"description": "IGST @ 18.0",
|
"description": "IGST @ 18.0",
|
||||||
"rate": 18
|
"rate": 18
|
||||||
@@ -159,7 +159,7 @@ def make_sales_invoice():
|
|||||||
|
|
||||||
si2.append("taxes", {
|
si2.append("taxes", {
|
||||||
"charge_type": "On Net Total",
|
"charge_type": "On Net Total",
|
||||||
"account_head": "IGST - _GST",
|
"account_head": "Output Tax IGST - _GST",
|
||||||
"cost_center": "Main - _GST",
|
"cost_center": "Main - _GST",
|
||||||
"description": "IGST @ 18.0",
|
"description": "IGST @ 18.0",
|
||||||
"rate": 18
|
"rate": 18
|
||||||
@@ -195,7 +195,7 @@ def create_purchase_invoices():
|
|||||||
|
|
||||||
pi.append("taxes", {
|
pi.append("taxes", {
|
||||||
"charge_type": "On Net Total",
|
"charge_type": "On Net Total",
|
||||||
"account_head": "CGST - _GST",
|
"account_head": "Input Tax CGST - _GST",
|
||||||
"cost_center": "Main - _GST",
|
"cost_center": "Main - _GST",
|
||||||
"description": "CGST @ 9.0",
|
"description": "CGST @ 9.0",
|
||||||
"rate": 9
|
"rate": 9
|
||||||
@@ -203,7 +203,7 @@ def create_purchase_invoices():
|
|||||||
|
|
||||||
pi.append("taxes", {
|
pi.append("taxes", {
|
||||||
"charge_type": "On Net Total",
|
"charge_type": "On Net Total",
|
||||||
"account_head": "SGST - _GST",
|
"account_head": "Input Tax SGST - _GST",
|
||||||
"cost_center": "Main - _GST",
|
"cost_center": "Main - _GST",
|
||||||
"description": "SGST @ 9.0",
|
"description": "SGST @ 9.0",
|
||||||
"rate": 9
|
"rate": 9
|
||||||
@@ -410,10 +410,10 @@ def make_company():
|
|||||||
company.country = "India"
|
company.country = "India"
|
||||||
company.insert()
|
company.insert()
|
||||||
|
|
||||||
if not frappe.db.exists('Address', '_Test Address-Billing'):
|
if not frappe.db.exists('Address', '_Test Address GST-Billing'):
|
||||||
address = frappe.get_doc({
|
address = frappe.get_doc({
|
||||||
|
"address_title": "_Test Address GST",
|
||||||
"address_line1": "_Test Address Line 1",
|
"address_line1": "_Test Address Line 1",
|
||||||
"address_title": "_Test Address",
|
|
||||||
"address_type": "Billing",
|
"address_type": "Billing",
|
||||||
"city": "_Test City",
|
"city": "_Test City",
|
||||||
"state": "Test State",
|
"state": "Test State",
|
||||||
@@ -444,9 +444,9 @@ def set_account_heads():
|
|||||||
if not gst_account:
|
if not gst_account:
|
||||||
gst_settings.append("gst_accounts", {
|
gst_settings.append("gst_accounts", {
|
||||||
"company": "_Test Company GST",
|
"company": "_Test Company GST",
|
||||||
"cgst_account": "CGST - _GST",
|
"cgst_account": "Output Tax CGST - _GST",
|
||||||
"sgst_account": "SGST - _GST",
|
"sgst_account": "Output Tax SGST - _GST",
|
||||||
"igst_account": "IGST - _GST",
|
"igst_account": "Output Tax IGST - _GST"
|
||||||
})
|
})
|
||||||
|
|
||||||
gst_settings.save()
|
gst_settings.save()
|
||||||
|
|||||||
@@ -25,6 +25,7 @@ def setup_company_independent_fixtures(patch=False):
|
|||||||
frappe.enqueue('erpnext.regional.india.setup.add_hsn_sac_codes', now=frappe.flags.in_test)
|
frappe.enqueue('erpnext.regional.india.setup.add_hsn_sac_codes', now=frappe.flags.in_test)
|
||||||
create_gratuity_rule()
|
create_gratuity_rule()
|
||||||
add_print_formats()
|
add_print_formats()
|
||||||
|
update_accounts_settings_for_taxes()
|
||||||
|
|
||||||
def add_hsn_sac_codes():
|
def add_hsn_sac_codes():
|
||||||
if frappe.flags.in_test and frappe.flags.created_hsn_codes:
|
if frappe.flags.in_test and frappe.flags.created_hsn_codes:
|
||||||
@@ -680,7 +681,7 @@ def make_custom_fields(update=True):
|
|||||||
|
|
||||||
def make_fixtures(company=None):
|
def make_fixtures(company=None):
|
||||||
docs = []
|
docs = []
|
||||||
company = company.name if company else frappe.db.get_value("Global Defaults", None, "default_company")
|
company = company or frappe.db.get_value("Global Defaults", None, "default_company")
|
||||||
|
|
||||||
set_salary_components(docs)
|
set_salary_components(docs)
|
||||||
set_tds_account(docs, company)
|
set_tds_account(docs, company)
|
||||||
@@ -698,6 +699,53 @@ def make_fixtures(company=None):
|
|||||||
# create records for Tax Withholding Category
|
# create records for Tax Withholding Category
|
||||||
set_tax_withholding_category(company)
|
set_tax_withholding_category(company)
|
||||||
|
|
||||||
|
def update_regional_tax_settings(country, company):
|
||||||
|
# Will only add default GST accounts if present
|
||||||
|
input_account_names = ['Input Tax CGST', 'Input Tax SGST', 'Input Tax IGST']
|
||||||
|
output_account_names = ['Output Tax CGST', 'Output Tax SGST', 'Output Tax IGST']
|
||||||
|
rcm_accounts = ['Input Tax CGST RCM', 'Input Tax SGST RCM', 'Input Tax IGST RCM']
|
||||||
|
gst_settings = frappe.get_single('GST Settings')
|
||||||
|
existing_account_list = []
|
||||||
|
|
||||||
|
for account in gst_settings.get('gst_accounts'):
|
||||||
|
for key in ['cgst_account', 'sgst_account', 'igst_account']:
|
||||||
|
existing_account_list.append(account.get(key))
|
||||||
|
|
||||||
|
gst_accounts = frappe._dict(frappe.get_all("Account",
|
||||||
|
{'company': company, 'account_name': ('in', input_account_names +
|
||||||
|
output_account_names + rcm_accounts)}, ['account_name', 'name'], as_list=1))
|
||||||
|
|
||||||
|
add_accounts_in_gst_settings(company, input_account_names, gst_accounts,
|
||||||
|
existing_account_list, gst_settings)
|
||||||
|
add_accounts_in_gst_settings(company, output_account_names, gst_accounts,
|
||||||
|
existing_account_list, gst_settings)
|
||||||
|
add_accounts_in_gst_settings(company, rcm_accounts, gst_accounts,
|
||||||
|
existing_account_list, gst_settings, is_reverse_charge=1)
|
||||||
|
|
||||||
|
gst_settings.save()
|
||||||
|
|
||||||
|
def add_accounts_in_gst_settings(company, account_names, gst_accounts,
|
||||||
|
existing_account_list, gst_settings, is_reverse_charge=0):
|
||||||
|
accounts_not_added = 1
|
||||||
|
|
||||||
|
for account in account_names:
|
||||||
|
# Default Account Added does not exists
|
||||||
|
if not gst_accounts.get(account):
|
||||||
|
accounts_not_added = 0
|
||||||
|
|
||||||
|
# Check if already added in GST Settings
|
||||||
|
if gst_accounts.get(account) in existing_account_list:
|
||||||
|
accounts_not_added = 0
|
||||||
|
|
||||||
|
if accounts_not_added:
|
||||||
|
gst_settings.append('gst_accounts', {
|
||||||
|
'company': company,
|
||||||
|
'cgst_account': gst_accounts.get(account_names[0]),
|
||||||
|
'sgst_account': gst_accounts.get(account_names[1]),
|
||||||
|
'igst_account': gst_accounts.get(account_names[2]),
|
||||||
|
'is_reverse_charge_account': is_reverse_charge
|
||||||
|
})
|
||||||
|
|
||||||
def set_salary_components(docs):
|
def set_salary_components(docs):
|
||||||
docs.extend([
|
docs.extend([
|
||||||
{'doctype': 'Salary Component', 'salary_component': 'Professional Tax',
|
{'doctype': 'Salary Component', 'salary_component': 'Professional Tax',
|
||||||
@@ -731,12 +779,13 @@ def set_tax_withholding_category(company):
|
|||||||
docs = get_tds_details(accounts, fiscal_year)
|
docs = get_tds_details(accounts, fiscal_year)
|
||||||
|
|
||||||
for d in docs:
|
for d in docs:
|
||||||
try:
|
if not frappe.db.exists("Tax Withholding Category", d.get("name")):
|
||||||
doc = frappe.get_doc(d)
|
doc = frappe.get_doc(d)
|
||||||
|
doc.flags.ignore_validate = True
|
||||||
doc.flags.ignore_permissions = True
|
doc.flags.ignore_permissions = True
|
||||||
doc.flags.ignore_mandatory = True
|
doc.flags.ignore_mandatory = True
|
||||||
doc.insert()
|
doc.insert()
|
||||||
except frappe.DuplicateEntryError:
|
else:
|
||||||
doc = frappe.get_doc("Tax Withholding Category", d.get("name"))
|
doc = frappe.get_doc("Tax Withholding Category", d.get("name"))
|
||||||
|
|
||||||
if accounts:
|
if accounts:
|
||||||
@@ -749,11 +798,12 @@ def set_tax_withholding_category(company):
|
|||||||
doc.append("rates", d.get('rates')[0])
|
doc.append("rates", d.get('rates')[0])
|
||||||
|
|
||||||
doc.flags.ignore_permissions = True
|
doc.flags.ignore_permissions = True
|
||||||
|
doc.flags.ignore_validate = True
|
||||||
doc.flags.ignore_mandatory = True
|
doc.flags.ignore_mandatory = True
|
||||||
|
doc.flags.ignore_links = True
|
||||||
doc.save()
|
doc.save()
|
||||||
|
|
||||||
def set_tds_account(docs, company):
|
def set_tds_account(docs, company):
|
||||||
abbr = frappe.get_value("Company", company, "abbr")
|
|
||||||
parent_account = frappe.db.get_value("Account", filters = {"account_name": "Duties and Taxes", "company": company})
|
parent_account = frappe.db.get_value("Account", filters = {"account_name": "Duties and Taxes", "company": company})
|
||||||
if parent_account:
|
if parent_account:
|
||||||
docs.extend([
|
docs.extend([
|
||||||
@@ -912,7 +962,6 @@ def get_tds_details(accounts, fiscal_year):
|
|||||||
]
|
]
|
||||||
|
|
||||||
def create_gratuity_rule():
|
def create_gratuity_rule():
|
||||||
|
|
||||||
# Standard Indain Gratuity Rule
|
# Standard Indain Gratuity Rule
|
||||||
if not frappe.db.exists("Gratuity Rule", "Indian Standard Gratuity Rule"):
|
if not frappe.db.exists("Gratuity Rule", "Indian Standard Gratuity Rule"):
|
||||||
rule = frappe.new_doc("Gratuity Rule")
|
rule = frappe.new_doc("Gratuity Rule")
|
||||||
@@ -930,3 +979,7 @@ def create_gratuity_rule():
|
|||||||
|
|
||||||
rule.flags.ignore_mandatory = True
|
rule.flags.ignore_mandatory = True
|
||||||
rule.save()
|
rule.save()
|
||||||
|
|
||||||
|
def update_accounts_settings_for_taxes():
|
||||||
|
if frappe.db.count('Company') == 1:
|
||||||
|
frappe.db.set_value('Accounts Settings', None, "add_taxes_from_item_tax_template", 0)
|
||||||
@@ -11,7 +11,7 @@
|
|||||||
"is_standard": "Yes",
|
"is_standard": "Yes",
|
||||||
"json": "{}",
|
"json": "{}",
|
||||||
"letter_head": "Logo",
|
"letter_head": "Logo",
|
||||||
"modified": "2021-03-12 12:36:48.689413",
|
"modified": "2021-03-13 12:36:48.689413",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "Regional",
|
"module": "Regional",
|
||||||
"name": "E-Invoice Summary",
|
"name": "E-Invoice Summary",
|
||||||
|
|||||||
@@ -110,7 +110,7 @@ class Company(NestedSet):
|
|||||||
self.create_default_warehouses()
|
self.create_default_warehouses()
|
||||||
|
|
||||||
if frappe.flags.country_change:
|
if frappe.flags.country_change:
|
||||||
install_country_fixtures(self.name)
|
install_country_fixtures(self.name, self.country)
|
||||||
self.create_default_tax_template()
|
self.create_default_tax_template()
|
||||||
|
|
||||||
if not frappe.db.get_value("Department", {"company": self.name}):
|
if not frappe.db.get_value("Department", {"company": self.name}):
|
||||||
@@ -440,16 +440,15 @@ def get_name_with_abbr(name, company):
|
|||||||
|
|
||||||
return " - ".join(parts)
|
return " - ".join(parts)
|
||||||
|
|
||||||
def install_country_fixtures(company):
|
def install_country_fixtures(company, country):
|
||||||
company_doc = frappe.get_doc("Company", company)
|
path = frappe.get_app_path('erpnext', 'regional', frappe.scrub(country))
|
||||||
path = frappe.get_app_path('erpnext', 'regional', frappe.scrub(company_doc.country))
|
|
||||||
if os.path.exists(path.encode("utf-8")):
|
if os.path.exists(path.encode("utf-8")):
|
||||||
try:
|
try:
|
||||||
module_name = "erpnext.regional.{0}.setup.setup".format(frappe.scrub(company_doc.country))
|
module_name = "erpnext.regional.{0}.setup.setup".format(frappe.scrub(country))
|
||||||
frappe.get_attr(module_name)(company_doc, False)
|
frappe.get_attr(module_name)(company, False)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
frappe.log_error()
|
frappe.log_error()
|
||||||
frappe.throw(_("Failed to setup defaults for country {0}. Please contact support@erpnext.com").format(frappe.bold(company_doc.country)))
|
frappe.throw(_("Failed to setup defaults for country {0}. Please contact support@erpnext.com").format(frappe.bold(country)))
|
||||||
|
|
||||||
|
|
||||||
def update_company_current_month_sales(company):
|
def update_company_current_month_sales(company):
|
||||||
|
|||||||
@@ -1164,33 +1164,292 @@
|
|||||||
},
|
},
|
||||||
|
|
||||||
"India": {
|
"India": {
|
||||||
|
"tax_categories": [
|
||||||
|
{
|
||||||
|
"title": "In-State",
|
||||||
|
"is_inter_state": 0,
|
||||||
|
"gst_state": ""
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "Out-State",
|
||||||
|
"is_inter_state": 1,
|
||||||
|
"gst_state": ""
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "Reverse Charge In-State",
|
||||||
|
"is_inter_state": 0,
|
||||||
|
"gst_state": ""
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "Reverse Charge Out-State",
|
||||||
|
"is_inter_state": 1,
|
||||||
|
"gst_state": ""
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "Registered Composition",
|
||||||
|
"is_inter_state": 0,
|
||||||
|
"gst_state": ""
|
||||||
|
}
|
||||||
|
],
|
||||||
"chart_of_accounts": {
|
"chart_of_accounts": {
|
||||||
"*": {
|
"*": {
|
||||||
"item_tax_templates": [
|
"item_tax_templates": [
|
||||||
{
|
{
|
||||||
"title": "In State GST",
|
"title": "GST 9%",
|
||||||
"taxes": [
|
"taxes": [
|
||||||
{
|
{
|
||||||
"tax_type": {
|
"tax_type": {
|
||||||
"account_name": "SGST",
|
"account_name": "Output Tax SGST",
|
||||||
"tax_rate": 9.00
|
"tax_rate": 9.00
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"tax_type": {
|
"tax_type": {
|
||||||
"account_name": "CGST",
|
"account_name": "Output Tax CGST",
|
||||||
"tax_rate": 9.00
|
"tax_rate": 9.00
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Output Tax IGST",
|
||||||
|
"tax_rate": 18.00
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax SGST",
|
||||||
|
"tax_rate": 9.00,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax CGST",
|
||||||
|
"tax_rate": 9.00,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax IGST",
|
||||||
|
"tax_rate": 18.00,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax SGST RCM",
|
||||||
|
"tax_rate": 9.00,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax CGST RCM",
|
||||||
|
"tax_rate": 9.00,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax IGST RCM",
|
||||||
|
"tax_rate": 18.00,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"title": "Out of State GST",
|
"title": "GST 5%",
|
||||||
"taxes": [
|
"taxes": [
|
||||||
{
|
{
|
||||||
"tax_type": {
|
"tax_type": {
|
||||||
"account_name": "IGST",
|
"account_name": "Output Tax SGST",
|
||||||
"tax_rate": 18.00
|
"tax_rate": 2.5
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Output Tax CGST",
|
||||||
|
"tax_rate": 2.5
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Output Tax IGST",
|
||||||
|
"tax_rate": 5.0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax SGST",
|
||||||
|
"tax_rate": 2.5,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax CGST",
|
||||||
|
"tax_rate": 2.5,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax IGST",
|
||||||
|
"tax_rate": 5.0,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax SGST RCM",
|
||||||
|
"tax_rate": 2.50,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax CGST RCM",
|
||||||
|
"tax_rate": 2.50,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax IGST RCM",
|
||||||
|
"tax_rate": 5.00,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "GST 12%",
|
||||||
|
"taxes": [
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Output Tax SGST",
|
||||||
|
"tax_rate": 6.0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Output Tax CGST",
|
||||||
|
"tax_rate": 6.0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Output Tax IGST",
|
||||||
|
"tax_rate": 12.0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax SGST",
|
||||||
|
"tax_rate": 6.0,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax CGST",
|
||||||
|
"tax_rate": 6.0,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax IGST",
|
||||||
|
"tax_rate": 12.0,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax SGST RCM",
|
||||||
|
"tax_rate": 6.00,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax CGST RCM",
|
||||||
|
"tax_rate": 6.00,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax IGST RCM",
|
||||||
|
"tax_rate": 12.00,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "GST 28%",
|
||||||
|
"taxes": [
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Output Tax SGST",
|
||||||
|
"tax_rate": 14.0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Output Tax CGST",
|
||||||
|
"tax_rate": 14.0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Output Tax IGST",
|
||||||
|
"tax_rate": 28.0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax SGST",
|
||||||
|
"tax_rate": 14.0,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax CGST",
|
||||||
|
"tax_rate": 14.0,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax IGST",
|
||||||
|
"tax_rate": 28.0,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax SGST RCM",
|
||||||
|
"tax_rate": 14.00,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax CGST RCM",
|
||||||
|
"tax_rate": 14.00,
|
||||||
|
"root_type": "Asset"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"tax_type": {
|
||||||
|
"account_name": "Input Tax IGST RCM",
|
||||||
|
"tax_rate": 28.00,
|
||||||
|
"root_type": "Asset"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
@@ -1229,35 +1488,116 @@
|
|||||||
]
|
]
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"*": [
|
"sales_tax_templates": [
|
||||||
{
|
{
|
||||||
"title": "In State GST",
|
"title": "Output GST In-state",
|
||||||
"taxes": [
|
"taxes": [
|
||||||
{
|
{
|
||||||
"account_head": {
|
"account_head": {
|
||||||
"account_name": "SGST",
|
"account_name": "Output Tax SGST",
|
||||||
"tax_rate": 9.00
|
"tax_rate": 9.00,
|
||||||
|
"account_type": "Tax"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"account_head": {
|
"account_head": {
|
||||||
"account_name": "CGST",
|
"account_name": "Output Tax CGST",
|
||||||
"tax_rate": 9.00
|
"tax_rate": 9.00,
|
||||||
|
"account_type": "Tax"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
]
|
],
|
||||||
|
"tax_category": "In-State"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"title": "Out of State GST",
|
"title": "Output GST Out-state",
|
||||||
"taxes": [
|
"taxes": [
|
||||||
{
|
{
|
||||||
"account_head": {
|
"account_head": {
|
||||||
"account_name": "IGST",
|
"account_name": "Output Tax IGST",
|
||||||
"tax_rate": 18.00
|
"tax_rate": 18.00,
|
||||||
|
"account_type": "Tax"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
]
|
],
|
||||||
|
"tax_category": "Out-State"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"purchase_tax_templates": [
|
||||||
|
{
|
||||||
|
"title": "Input GST In-state",
|
||||||
|
"taxes": [
|
||||||
|
{
|
||||||
|
"account_head": {
|
||||||
|
"account_name": "Input Tax SGST",
|
||||||
|
"tax_rate": 9.00,
|
||||||
|
"root_type": "Asset",
|
||||||
|
"account_type": "Tax"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"account_head": {
|
||||||
|
"account_name": "Input Tax CGST",
|
||||||
|
"tax_rate": 9.00,
|
||||||
|
"root_type": "Asset",
|
||||||
|
"account_type": "Tax"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"tax_category": "In-State"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"title": "Input GST Out-state",
|
||||||
|
"taxes": [
|
||||||
|
{
|
||||||
|
"account_head": {
|
||||||
|
"account_name": "Input Tax IGST",
|
||||||
|
"tax_rate": 18.00,
|
||||||
|
"root_type": "Asset",
|
||||||
|
"account_type": "Tax"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"tax_category": "Out-State"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "Input GST RCM In-state",
|
||||||
|
"taxes": [
|
||||||
|
{
|
||||||
|
"account_head": {
|
||||||
|
"account_name": "Input Tax SGST RCM",
|
||||||
|
"tax_rate": 9.00,
|
||||||
|
"root_type": "Asset",
|
||||||
|
"account_type": "Tax"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"account_head": {
|
||||||
|
"account_name": "Input Tax CGST RCM",
|
||||||
|
"tax_rate": 9.00,
|
||||||
|
"root_type": "Asset",
|
||||||
|
"account_type": "Tax"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"tax_category": "Reverse Charge In-State"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"title": "Input GST RCM Out-state",
|
||||||
|
"taxes": [
|
||||||
|
{
|
||||||
|
"account_head": {
|
||||||
|
"account_name": "Input Tax IGST RCM",
|
||||||
|
"tax_rate": 18.00,
|
||||||
|
"root_type": "Asset",
|
||||||
|
"account_type": "Tax"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"tax_category": "Reverse Charge Out-State"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"*": [
|
||||||
{
|
{
|
||||||
"title": "VAT 5%",
|
"title": "VAT 5%",
|
||||||
"taxes": [
|
"taxes": [
|
||||||
@@ -1349,7 +1689,7 @@
|
|||||||
"Italy VAT 4%":{
|
"Italy VAT 4%":{
|
||||||
"account_name": "IVA 4%",
|
"account_name": "IVA 4%",
|
||||||
"tax_rate": 4.00
|
"tax_rate": 4.00
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
"Ivory Coast": {
|
"Ivory Coast": {
|
||||||
|
|||||||
@@ -42,29 +42,6 @@ def enable_shopping_cart(args):
|
|||||||
'quotation_series': "QTN-",
|
'quotation_series': "QTN-",
|
||||||
}).insert()
|
}).insert()
|
||||||
|
|
||||||
def create_bank_account(args):
|
|
||||||
if args.get("bank_account"):
|
|
||||||
company_name = args.get('company_name')
|
|
||||||
bank_account_group = frappe.db.get_value("Account",
|
|
||||||
{"account_type": "Bank", "is_group": 1, "root_type": "Asset",
|
|
||||||
"company": company_name})
|
|
||||||
if bank_account_group:
|
|
||||||
bank_account = frappe.get_doc({
|
|
||||||
"doctype": "Account",
|
|
||||||
'account_name': args.get("bank_account"),
|
|
||||||
'parent_account': bank_account_group,
|
|
||||||
'is_group':0,
|
|
||||||
'company': company_name,
|
|
||||||
"account_type": "Bank",
|
|
||||||
})
|
|
||||||
try:
|
|
||||||
return bank_account.insert()
|
|
||||||
except RootNotEditable:
|
|
||||||
frappe.throw(_("Bank account cannot be named as {0}").format(args.get("bank_account")))
|
|
||||||
except frappe.DuplicateEntryError:
|
|
||||||
# bank account same as a CoA entry
|
|
||||||
pass
|
|
||||||
|
|
||||||
def create_email_digest():
|
def create_email_digest():
|
||||||
from frappe.utils.user import get_system_managers
|
from frappe.utils.user import get_system_managers
|
||||||
system_managers = get_system_managers(only_name=True)
|
system_managers = get_system_managers(only_name=True)
|
||||||
|
|||||||
@@ -449,6 +449,8 @@ def install_defaults(args=None):
|
|||||||
set_active_domains(args)
|
set_active_domains(args)
|
||||||
update_stock_settings()
|
update_stock_settings()
|
||||||
update_shopping_cart_settings(args)
|
update_shopping_cart_settings(args)
|
||||||
|
|
||||||
|
args.update({"set_default": 1})
|
||||||
create_bank_account(args)
|
create_bank_account(args)
|
||||||
|
|
||||||
def set_global_defaults(args):
|
def set_global_defaults(args):
|
||||||
@@ -480,17 +482,17 @@ def update_stock_settings():
|
|||||||
stock_settings.save()
|
stock_settings.save()
|
||||||
|
|
||||||
def create_bank_account(args):
|
def create_bank_account(args):
|
||||||
if not args.bank_account:
|
if not args.get('bank_account'):
|
||||||
return
|
return
|
||||||
|
|
||||||
company_name = args.company_name
|
company_name = args.get('company_name')
|
||||||
bank_account_group = frappe.db.get_value("Account",
|
bank_account_group = frappe.db.get_value("Account",
|
||||||
{"account_type": "Bank", "is_group": 1, "root_type": "Asset",
|
{"account_type": "Bank", "is_group": 1, "root_type": "Asset",
|
||||||
"company": company_name})
|
"company": company_name})
|
||||||
if bank_account_group:
|
if bank_account_group:
|
||||||
bank_account = frappe.get_doc({
|
bank_account = frappe.get_doc({
|
||||||
"doctype": "Account",
|
"doctype": "Account",
|
||||||
'account_name': args.bank_account,
|
'account_name': args.get('bank_account'),
|
||||||
'parent_account': bank_account_group,
|
'parent_account': bank_account_group,
|
||||||
'is_group':0,
|
'is_group':0,
|
||||||
'company': company_name,
|
'company': company_name,
|
||||||
@@ -499,10 +501,13 @@ def create_bank_account(args):
|
|||||||
try:
|
try:
|
||||||
doc = bank_account.insert()
|
doc = bank_account.insert()
|
||||||
|
|
||||||
frappe.db.set_value("Company", args.company_name, "default_bank_account", bank_account.name, update_modified=False)
|
if args.get('set_default'):
|
||||||
|
frappe.db.set_value("Company", args.get('company_name'), "default_bank_account", bank_account.name, update_modified=False)
|
||||||
|
|
||||||
|
return doc
|
||||||
|
|
||||||
except RootNotEditable:
|
except RootNotEditable:
|
||||||
frappe.throw(_("Bank account cannot be named as {0}").format(args.bank_account))
|
frappe.throw(_("Bank account cannot be named as {0}").format(args.get('bank_account')))
|
||||||
except frappe.DuplicateEntryError:
|
except frappe.DuplicateEntryError:
|
||||||
# bank account same as a CoA entry
|
# bank account same as a CoA entry
|
||||||
pass
|
pass
|
||||||
|
|||||||
@@ -27,6 +27,7 @@ def setup_taxes_and_charges(company_name: str, country: str):
|
|||||||
country_wise_tax = simple_to_detailed(country_wise_tax)
|
country_wise_tax = simple_to_detailed(country_wise_tax)
|
||||||
|
|
||||||
from_detailed_data(company_name, country_wise_tax)
|
from_detailed_data(company_name, country_wise_tax)
|
||||||
|
update_regional_tax_settings(country, company_name)
|
||||||
|
|
||||||
|
|
||||||
def simple_to_detailed(templates):
|
def simple_to_detailed(templates):
|
||||||
@@ -101,6 +102,17 @@ def from_detailed_data(company_name, data):
|
|||||||
make_item_tax_template(company_name, template)
|
make_item_tax_template(company_name, template)
|
||||||
|
|
||||||
|
|
||||||
|
def update_regional_tax_settings(country, company):
|
||||||
|
path = frappe.get_app_path('erpnext', 'regional', frappe.scrub(country))
|
||||||
|
if os.path.exists(path.encode("utf-8")):
|
||||||
|
try:
|
||||||
|
module_name = "erpnext.regional.{0}.setup.update_regional_tax_settings".format(frappe.scrub(country))
|
||||||
|
frappe.get_attr(module_name)(country, company)
|
||||||
|
except Exception as e:
|
||||||
|
# Log error and ignore if failed to setup regional tax settings
|
||||||
|
frappe.log_error()
|
||||||
|
pass
|
||||||
|
|
||||||
def make_taxes_and_charges_template(company_name, doctype, template):
|
def make_taxes_and_charges_template(company_name, doctype, template):
|
||||||
template['company'] = company_name
|
template['company'] = company_name
|
||||||
template['doctype'] = doctype
|
template['doctype'] = doctype
|
||||||
@@ -130,8 +142,14 @@ def make_taxes_and_charges_template(company_name, doctype, template):
|
|||||||
if fieldname not in tax_row:
|
if fieldname not in tax_row:
|
||||||
tax_row[fieldname] = default_value
|
tax_row[fieldname] = default_value
|
||||||
|
|
||||||
return frappe.get_doc(template).insert(ignore_permissions=True)
|
doc = frappe.get_doc(template)
|
||||||
|
|
||||||
|
# Data in country wise json is already pre validated, hence validations can be ignored
|
||||||
|
# Ingone validations to make doctypes faster
|
||||||
|
doc.flags.ignore_links = True
|
||||||
|
doc.flags.ignore_validate = True
|
||||||
|
doc.insert(ignore_permissions=True)
|
||||||
|
return doc
|
||||||
|
|
||||||
def make_item_tax_template(company_name, template):
|
def make_item_tax_template(company_name, template):
|
||||||
"""Create an Item Tax Template.
|
"""Create an Item Tax Template.
|
||||||
@@ -156,8 +174,24 @@ def make_item_tax_template(company_name, template):
|
|||||||
if 'tax_rate' not in tax_row:
|
if 'tax_rate' not in tax_row:
|
||||||
tax_row['tax_rate'] = account_data.get('tax_rate')
|
tax_row['tax_rate'] = account_data.get('tax_rate')
|
||||||
|
|
||||||
return frappe.get_doc(template).insert(ignore_permissions=True)
|
doc = frappe.get_doc(template)
|
||||||
|
|
||||||
|
# Data in country wise json is already pre validated, hence validations can be ignored
|
||||||
|
# Ingone validations to make doctypes faster
|
||||||
|
doc.flags.ignore_links = True
|
||||||
|
doc.flags.ignore_validate = True
|
||||||
|
doc.insert(ignore_permissions=True)
|
||||||
|
return doc
|
||||||
|
|
||||||
|
def make_tax_category(tax_category):
|
||||||
|
""" Make tax category based on title if not already created """
|
||||||
|
doctype = 'Tax Category'
|
||||||
|
if not frappe.db.exists(doctype, tax_category['title']):
|
||||||
|
tax_category['doctype'] = doctype
|
||||||
|
doc = frappe.get_doc(tax_category)
|
||||||
|
doc.flags.ignore_links = True
|
||||||
|
doc.flags.ignore_validate = True
|
||||||
|
doc.insert(ignore_permissions=True)
|
||||||
|
|
||||||
def get_or_create_account(company_name, account):
|
def get_or_create_account(company_name, account):
|
||||||
"""
|
"""
|
||||||
@@ -175,8 +209,7 @@ def get_or_create_account(company_name, account):
|
|||||||
or_filters={
|
or_filters={
|
||||||
'account_name': account.get('account_name'),
|
'account_name': account.get('account_name'),
|
||||||
'account_number': account.get('account_number')
|
'account_number': account.get('account_number')
|
||||||
}
|
})
|
||||||
)
|
|
||||||
|
|
||||||
if existing_accounts:
|
if existing_accounts:
|
||||||
return frappe.get_doc('Account', existing_accounts[0].name)
|
return frappe.get_doc('Account', existing_accounts[0].name)
|
||||||
@@ -191,8 +224,11 @@ def get_or_create_account(company_name, account):
|
|||||||
account['root_type'] = root_type
|
account['root_type'] = root_type
|
||||||
account['is_group'] = 0
|
account['is_group'] = 0
|
||||||
|
|
||||||
return frappe.get_doc(account).insert(ignore_permissions=True, ignore_mandatory=True)
|
doc = frappe.get_doc(account)
|
||||||
|
doc.flags.ignore_links = True
|
||||||
|
doc.flags.ignore_validate = True
|
||||||
|
doc.insert(ignore_permissions=True, ignore_mandatory=True)
|
||||||
|
return doc
|
||||||
|
|
||||||
def get_or_create_tax_group(company_name, root_type):
|
def get_or_create_tax_group(company_name, root_type):
|
||||||
# Look for a group account of type 'Tax'
|
# Look for a group account of type 'Tax'
|
||||||
@@ -237,7 +273,11 @@ def get_or_create_tax_group(company_name, root_type):
|
|||||||
'account_type': 'Tax',
|
'account_type': 'Tax',
|
||||||
'account_name': account_name,
|
'account_name': account_name,
|
||||||
'parent_account': root_account.name
|
'parent_account': root_account.name
|
||||||
}).insert(ignore_permissions=True)
|
})
|
||||||
|
|
||||||
|
tax_group_account.flags.ignore_links = True
|
||||||
|
tax_group_account.flags.ignore_validate = True
|
||||||
|
tax_group_account.insert(ignore_permissions=True)
|
||||||
|
|
||||||
tax_group_name = tax_group_account.name
|
tax_group_name = tax_group_account.name
|
||||||
|
|
||||||
|
|||||||
@@ -71,7 +71,8 @@ class ProductQuery:
|
|||||||
],
|
],
|
||||||
or_filters=self.or_filters,
|
or_filters=self.or_filters,
|
||||||
start=start,
|
start=start,
|
||||||
limit=self.page_length
|
limit=self.page_length,
|
||||||
|
order_by="weightage desc"
|
||||||
)
|
)
|
||||||
|
|
||||||
items_dict = {item.name: item for item in items}
|
items_dict = {item.name: item for item in items}
|
||||||
@@ -86,7 +87,8 @@ class ProductQuery:
|
|||||||
filters=self.filters,
|
filters=self.filters,
|
||||||
or_filters=self.or_filters,
|
or_filters=self.or_filters,
|
||||||
start=start,
|
start=start,
|
||||||
limit=self.page_length
|
limit=self.page_length,
|
||||||
|
order_by="weightage desc"
|
||||||
)
|
)
|
||||||
|
|
||||||
# Combine results having context of website item groups into item results
|
# Combine results having context of website item groups into item results
|
||||||
|
|||||||
@@ -386,6 +386,7 @@ class PurchaseReceipt(BuyingController):
|
|||||||
against_account = ", ".join([d.account for d in gl_entries if flt(d.debit) > 0])
|
against_account = ", ".join([d.account for d in gl_entries if flt(d.debit) > 0])
|
||||||
total_valuation_amount = sum(valuation_tax.values())
|
total_valuation_amount = sum(valuation_tax.values())
|
||||||
amount_including_divisional_loss = negative_expense_to_be_booked
|
amount_including_divisional_loss = negative_expense_to_be_booked
|
||||||
|
stock_rbnb = self.get_company_default("stock_received_but_not_billed")
|
||||||
i = 1
|
i = 1
|
||||||
for tax in self.get("taxes"):
|
for tax in self.get("taxes"):
|
||||||
if valuation_tax.get(tax.name):
|
if valuation_tax.get(tax.name):
|
||||||
|
|||||||
@@ -97,7 +97,7 @@ def apply_putaway_rule(doctype, items, company, sync=None, purpose=None):
|
|||||||
at_capacity, rules = get_ordered_putaway_rules(item_code, company, source_warehouse=source_warehouse)
|
at_capacity, rules = get_ordered_putaway_rules(item_code, company, source_warehouse=source_warehouse)
|
||||||
|
|
||||||
if not rules:
|
if not rules:
|
||||||
warehouse = source_warehouse or item.warehouse
|
warehouse = source_warehouse or item.get('warehouse')
|
||||||
if at_capacity:
|
if at_capacity:
|
||||||
# rules available, but no free space
|
# rules available, but no free space
|
||||||
items_not_accomodated.append([item_code, pending_qty])
|
items_not_accomodated.append([item_code, pending_qty])
|
||||||
|
|||||||
@@ -54,7 +54,7 @@ class TestStockLedgerEntry(unittest.TestCase):
|
|||||||
)
|
)
|
||||||
|
|
||||||
# _Test Item for Reposting transferred from Stores to FG warehouse on 30-04-2020
|
# _Test Item for Reposting transferred from Stores to FG warehouse on 30-04-2020
|
||||||
make_stock_entry(
|
se = make_stock_entry(
|
||||||
item_code="_Test Item for Reposting",
|
item_code="_Test Item for Reposting",
|
||||||
source="Stores - _TC",
|
source="Stores - _TC",
|
||||||
target="Finished Goods - _TC",
|
target="Finished Goods - _TC",
|
||||||
@@ -64,29 +64,29 @@ class TestStockLedgerEntry(unittest.TestCase):
|
|||||||
posting_date='2020-04-30',
|
posting_date='2020-04-30',
|
||||||
posting_time='14:00'
|
posting_time='14:00'
|
||||||
)
|
)
|
||||||
target_wh_sle = get_previous_sle({
|
target_wh_sle = frappe.db.get_value('Stock Ledger Entry', {
|
||||||
"item_code": "_Test Item for Reposting",
|
"item_code": "_Test Item for Reposting",
|
||||||
"warehouse": "Finished Goods - _TC",
|
"warehouse": "Finished Goods - _TC",
|
||||||
"posting_date": '2020-04-30',
|
"voucher_type": "Stock Entry",
|
||||||
"posting_time": '14:00'
|
"voucher_no": se.name
|
||||||
})
|
}, ["valuation_rate"], as_dict=1)
|
||||||
|
|
||||||
self.assertEqual(target_wh_sle.get("valuation_rate"), 150)
|
self.assertEqual(target_wh_sle.get("valuation_rate"), 150)
|
||||||
|
|
||||||
# Repack entry on 5-5-2020
|
# Repack entry on 5-5-2020
|
||||||
repack = create_repack_entry(company=company, posting_date='2020-05-05', posting_time='14:00')
|
repack = create_repack_entry(company=company, posting_date='2020-05-05', posting_time='14:00')
|
||||||
|
|
||||||
finished_item_sle = get_previous_sle({
|
finished_item_sle = frappe.db.get_value('Stock Ledger Entry', {
|
||||||
"item_code": "_Test Finished Item for Reposting",
|
"item_code": "_Test Finished Item for Reposting",
|
||||||
"warehouse": "Finished Goods - _TC",
|
"warehouse": "Finished Goods - _TC",
|
||||||
"posting_date": '2020-05-05',
|
"voucher_type": "Stock Entry",
|
||||||
"posting_time": '14:00'
|
"voucher_no": repack.name
|
||||||
})
|
}, ["incoming_rate", "valuation_rate"], as_dict=1)
|
||||||
self.assertEqual(finished_item_sle.get("incoming_rate"), 540)
|
self.assertEqual(finished_item_sle.get("incoming_rate"), 540)
|
||||||
self.assertEqual(finished_item_sle.get("valuation_rate"), 540)
|
self.assertEqual(finished_item_sle.get("valuation_rate"), 540)
|
||||||
|
|
||||||
# Reconciliation for _Test Item for Reposting at Stores on 12-04-2020: Qty = 50, Rate = 150
|
# Reconciliation for _Test Item for Reposting at Stores on 12-04-2020: Qty = 50, Rate = 150
|
||||||
create_stock_reconciliation(
|
sr = create_stock_reconciliation(
|
||||||
item_code="_Test Item for Reposting",
|
item_code="_Test Item for Reposting",
|
||||||
warehouse="Stores - _TC",
|
warehouse="Stores - _TC",
|
||||||
qty=50,
|
qty=50,
|
||||||
@@ -109,12 +109,12 @@ class TestStockLedgerEntry(unittest.TestCase):
|
|||||||
self.assertEqual(target_wh_sle.get("valuation_rate"), 175)
|
self.assertEqual(target_wh_sle.get("valuation_rate"), 175)
|
||||||
|
|
||||||
# Check valuation rate of repacked item after back-dated entry at Stores
|
# Check valuation rate of repacked item after back-dated entry at Stores
|
||||||
finished_item_sle = get_previous_sle({
|
finished_item_sle = frappe.db.get_value('Stock Ledger Entry', {
|
||||||
"item_code": "_Test Finished Item for Reposting",
|
"item_code": "_Test Finished Item for Reposting",
|
||||||
"warehouse": "Finished Goods - _TC",
|
"warehouse": "Finished Goods - _TC",
|
||||||
"posting_date": '2020-05-05',
|
"voucher_type": "Stock Entry",
|
||||||
"posting_time": '14:00'
|
"voucher_no": repack.name
|
||||||
})
|
}, ["incoming_rate", "valuation_rate"], as_dict=1)
|
||||||
self.assertEqual(finished_item_sle.get("incoming_rate"), 790)
|
self.assertEqual(finished_item_sle.get("incoming_rate"), 790)
|
||||||
self.assertEqual(finished_item_sle.get("valuation_rate"), 790)
|
self.assertEqual(finished_item_sle.get("valuation_rate"), 790)
|
||||||
|
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ import frappe
|
|||||||
import datetime
|
import datetime
|
||||||
import json
|
import json
|
||||||
import pytz
|
import pytz
|
||||||
|
from frappe import _
|
||||||
|
|
||||||
|
|
||||||
WEEKDAYS = ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"]
|
WEEKDAYS = ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"]
|
||||||
@@ -14,7 +15,8 @@ def get_context(context):
|
|||||||
if is_enabled:
|
if is_enabled:
|
||||||
return context
|
return context
|
||||||
else:
|
else:
|
||||||
frappe.local.flags.redirect_location = '/404'
|
frappe.redirect_to_message(_("Appointment Scheduling Disabled"), _("Appointment Scheduling has been disabled for this site"),
|
||||||
|
http_status_code=302, indicator_color="red")
|
||||||
raise frappe.Redirect
|
raise frappe.Redirect
|
||||||
|
|
||||||
@frappe.whitelist(allow_guest=True)
|
@frappe.whitelist(allow_guest=True)
|
||||||
|
|||||||
Reference in New Issue
Block a user