diff --git a/erpnext/accounts/report/consolidated_financial_statement/consolidated_financial_statement.py b/erpnext/accounts/report/consolidated_financial_statement/consolidated_financial_statement.py index 04625fc76fc..040ac6008c0 100644 --- a/erpnext/accounts/report/consolidated_financial_statement/consolidated_financial_statement.py +++ b/erpnext/accounts/report/consolidated_financial_statement/consolidated_financial_statement.py @@ -38,6 +38,7 @@ from erpnext.accounts.report.profit_and_loss_statement.profit_and_loss_statement get_report_summary as get_pl_summary, ) from erpnext.accounts.report.utils import convert, convert_to_presentation_currency +from erpnext.accounts.utils import get_zero_cutoff def execute(filters=None): @@ -563,7 +564,7 @@ def prepare_data(accounts, start_date, end_date, balance_must_be, companies, com row[company] = flt(d.get(company, 0.0), 3) - if abs(row[company]) >= 0.005: + if abs(row[company]) >= get_zero_cutoff(filters.presentation_currency): # ignore zero values has_value = True total += flt(row[company]) diff --git a/erpnext/accounts/report/dimension_wise_accounts_balance_report/dimension_wise_accounts_balance_report.py b/erpnext/accounts/report/dimension_wise_accounts_balance_report/dimension_wise_accounts_balance_report.py index ed30ad415d0..2d0015a461e 100644 --- a/erpnext/accounts/report/dimension_wise_accounts_balance_report/dimension_wise_accounts_balance_report.py +++ b/erpnext/accounts/report/dimension_wise_accounts_balance_report/dimension_wise_accounts_balance_report.py @@ -12,6 +12,7 @@ from erpnext.accounts.report.financial_statements import ( filter_out_zero_value_rows, ) from erpnext.accounts.report.trial_balance.trial_balance import validate_filters +from erpnext.accounts.utils import get_zero_cutoff def execute(filters=None): @@ -154,7 +155,7 @@ def prepare_data(accounts, filters, company_currency, dimension_list): for dimension in dimension_list: row[frappe.scrub(dimension)] = flt(d.get(frappe.scrub(dimension), 0.0), 3) - if abs(row[frappe.scrub(dimension)]) >= 0.005: + if abs(row[frappe.scrub(dimension)]) >= get_zero_cutoff(company_currency): # ignore zero values has_value = True total += flt(d.get(frappe.scrub(dimension), 0.0), 3) diff --git a/erpnext/accounts/report/financial_statements.py b/erpnext/accounts/report/financial_statements.py index 04068dc08a1..bf46c9b07c6 100644 --- a/erpnext/accounts/report/financial_statements.py +++ b/erpnext/accounts/report/financial_statements.py @@ -18,7 +18,7 @@ from erpnext.accounts.doctype.accounting_dimension.accounting_dimension import ( get_dimension_with_children, ) from erpnext.accounts.report.utils import convert_to_presentation_currency, get_currency -from erpnext.accounts.utils import get_fiscal_year +from erpnext.accounts.utils import get_fiscal_year, get_zero_cutoff def get_period_list( @@ -304,7 +304,7 @@ def prepare_data(accounts, balance_must_be, period_list, company_currency, accum row[period.key] = flt(d.get(period.key, 0.0), 3) - if abs(row[period.key]) >= 0.005: + if abs(row[period.key]) >= get_zero_cutoff(company_currency): # ignore zero values has_value = True total += flt(row[period.key]) diff --git a/erpnext/accounts/report/profitability_analysis/profitability_analysis.py b/erpnext/accounts/report/profitability_analysis/profitability_analysis.py index dfb941d9123..5f3215fe7e2 100644 --- a/erpnext/accounts/report/profitability_analysis/profitability_analysis.py +++ b/erpnext/accounts/report/profitability_analysis/profitability_analysis.py @@ -12,6 +12,7 @@ from erpnext.accounts.report.financial_statements import ( filter_out_zero_value_rows, ) from erpnext.accounts.report.trial_balance.trial_balance import validate_filters +from erpnext.accounts.utils import get_zero_cutoff value_fields = ("income", "expense", "gross_profit_loss") @@ -149,7 +150,7 @@ def prepare_data(accounts, filters, total_row, parent_children_map, based_on): for key in value_fields: row[key] = flt(d.get(key, 0.0), 3) - if abs(row[key]) >= 0.005: + if abs(row[key]) >= get_zero_cutoff(company_currency): # ignore zero values has_value = True diff --git a/erpnext/accounts/report/trial_balance/trial_balance.py b/erpnext/accounts/report/trial_balance/trial_balance.py index 5575426dfff..9e1dd1a57c3 100644 --- a/erpnext/accounts/report/trial_balance/trial_balance.py +++ b/erpnext/accounts/report/trial_balance/trial_balance.py @@ -18,6 +18,7 @@ from erpnext.accounts.report.financial_statements import ( set_gl_entries_by_account, ) from erpnext.accounts.report.utils import convert_to_presentation_currency, get_currency +from erpnext.accounts.utils import get_zero_cutoff value_fields = ( "opening_debit", @@ -413,7 +414,7 @@ def prepare_data(accounts, filters, parent_children_map, company_currency): for key in value_fields: row[key] = flt(d.get(key, 0.0), 3) - if abs(row[key]) >= 0.005: + if abs(row[key]) >= get_zero_cutoff(company_currency): # ignore zero values has_value = True diff --git a/erpnext/accounts/test/test_utils.py b/erpnext/accounts/test/test_utils.py index 5e108dee9b5..f89b47b2dfe 100644 --- a/erpnext/accounts/test/test_utils.py +++ b/erpnext/accounts/test/test_utils.py @@ -9,6 +9,7 @@ from erpnext.accounts.party import get_party_shipping_address from erpnext.accounts.utils import ( get_future_stock_vouchers, get_voucherwise_gl_entries, + get_zero_cutoff, sort_stock_vouchers_by_posting_date, ) from erpnext.stock.doctype.item.test_item import make_item @@ -156,6 +157,11 @@ class TestUtils(unittest.TestCase): self.assertSequenceEqual(doc_name[0:2], ("SUP", fiscal_year)) frappe.db.set_default("supp_master_name", "Supplier Name") + def test_get_zero_cutoff(self): + self.assertEqual(get_zero_cutoff(None), 0.005) + self.assertEqual(get_zero_cutoff("EUR"), 0.005) + self.assertEqual(get_zero_cutoff("BHD"), 0.0005) + ADDRESS_RECORDS = [ { diff --git a/erpnext/accounts/utils.py b/erpnext/accounts/utils.py index 15117b2aa43..3c0485798b1 100644 --- a/erpnext/accounts/utils.py +++ b/erpnext/accounts/utils.py @@ -27,6 +27,7 @@ from frappe.utils import ( now, nowdate, ) +from frappe.utils.caching import site_cache from pypika import Order from pypika.functions import Coalesce from pypika.terms import ExistsCriterion @@ -1130,6 +1131,29 @@ def get_currency_precision(): return precision +def get_fraction_units(currency: str) -> int: + """Returns the number of fraction units for a currency.""" + fraction_units = frappe.db.get_value("Currency", currency, "fraction_units") + + if fraction_units is None: + fraction_units = 100 + + return fraction_units + + +@site_cache() +def get_zero_cutoff(currency: str) -> float: + """Returns the zero cutoff for a currency. + + For example, if the Fraction Units for a currency are set to 100, then the zero cutoff is 0.005. + We don't want to display values less than the zero cutoff. + This value was chosen for compatibility with the previous hard-coded value of 0.005. + """ + fraction_units = get_fraction_units(currency) + + return 0.5 / (fraction_units or 1) + + def get_held_invoices(party_type, party): """ Returns a list of names Purchase Invoices for the given party that are on hold