Interest Calculator for ERPNext v16 — Simple & Compound interest on GL balances
  • Python 96.2%
  • CSS 1.9%
  • JavaScript 1.9%
Find a file
Jarvis cc25afe458 polish: resolve 3 cosmetic audit items
- interest_rule.py: add from frappe import _, wrap error strings
- interest_ledger.py: import Decimal helpers from engine (D, R2, to_float, constants)
  instead of duplicating 30 lines
- interest_overdue_analysis.py: same — import from engine, remove duplicate helpers

Eliminates code duplication. All Decimal logic is single-source in interest_calculation.py.
2026-06-07 05:51:13 +05:30
interest_calculator polish: resolve 3 cosmetic audit items 2026-06-07 05:51:13 +05:30
README.md docs: rewrite README — full architecture, features, JE structure, formulas 2026-06-07 05:45:53 +05:30
requirements.txt Initial scaffold: Interest Calculator for ERPNext v16 2026-06-06 22:08:21 +05:30
setup.py Initial scaffold: Interest Calculator for ERPNext v16 2026-06-06 22:08:21 +05:30

Interest Calculator

ERPNext v16 app for financial interest computation with full GL posting, tax compliance, and settlement tracking.


Features

Core Engine

  • Simple & Compound Interest — configurable per rule
  • Calculation Frequencies — Daily, Monthly, Quarterly, Half-Yearly, Yearly
  • GL Filters — Account, Party Type, Party, Cost Centre, Project
  • Balance Types — Any Balance, Debit Only (Overdue), Credit Only (Overdue)
  • Base Amount — Closing Balance, Debit Total, or Credit Total
  • Pure Decimal arithmeticROUND_HALF_UP throughout, no float drift
  • Leap-year aware — uses calendar.monthrange for month-end dates

GL Posting

  • Auto-create Journal Entry on Submit — posts interest to GL
  • Receivable & Payable — correct debit/credit for both directions
  • Party integration — auto-applies party_type/party from rule to Receivable/Payable JE lines

Tax Compliance

  • TDS (Tax Deducted at Source) — configurable per rule: section (194A/I/C/H/J), rate, threshold, account
  • GST (Goods & Services Tax) — configurable per rule: treatment, rate, HSN/SAC code, account
  • India Compliance compatible — passes GST accounts and GSTIN for validation when the India Compliance app is installed

Settlement Tracking

  • Interest Settlement child table — record payment allocations with reference + TDS
  • Computed fieldstotal_settled, pending_interest, settlement_status (Accrued / Partially / Fully)
  • Works for both receivable and payable

Automation

  • Batch Calculate — create Interest Calculations for multiple rules at once
  • Scheduled CalculationsInterest Schedule doctype with daily cron job (Monthly/Quarterly/Yearly)
  • Auto-submit option — schedules can auto-submit created calculations

DocTypes

DocType Type Purpose
Interest Rule Master Defines rate, method, frequency, GL filters, TDS, GST, and posting accounts
Interest Calculation Transaction (Submittable) Stores a calculation run with entries, JE reference, settlement data
Interest Calculation Entry Child Table One row per period with GL data + interest amount
Interest Settlement Child Table Payment allocations against an interest calculation
Interest Schedule Master Recurring calculation config for automation

Reports

Report Type Description
Interest Ledger Script Report (file-based) GL-style view: 3 modes — Saved Calc / On-the-fly / Aggregate. Full Decimal.
Interest Overdue Analysis Script Report (file-based) Aging report by party with 0-30/31-60/61-90/90+ day buckets

Print Formats

Format Purpose
Interest Certificate Professional PDF with period breakdown, TDS, settlement history, signatory line

Architecture

Interest Calculation Workflow

Draft → [Calculate Interest] → Calculated → [Submit] → Submitted
                                                    ↓
                                           Auto-creates Journal Entry
                                           (with TDS + GST if configured)

JE Structure (Receivable, ₹10,000 interest, 10% TDS, 18% GST)

Debit:  Party Account         ₹10,800  (gross + GST - TDS)
Credit: GST Payable           ₹1,800
Credit: TDS Payable           ₹1,000
Credit: Interest Income       ₹10,000

JE Structure (Payable, same amounts)

Debit:  Interest Expense      ₹10,000
Debit:  GST Input             ₹1,800
Credit: TDS Payable           ₹1,000
Credit: Party Account         ₹10,800

Decimal Pipeline

GL Entry (float) → D() → Decimal arithmetic → quantize(ROUND_HALF_UP) → to_float() → Frappe field

All financial math uses Python's decimal.Decimal. float only touches data at the Frappe field boundary.


Installation

bench get-app https://git.ashu.io/ashuio/interest_calculator.git
bench --site <site-name> install-app interest_calculator
bench --site <site-name> migrate
bench build

Optional: India Compliance

For GST validation and GSTR reporting:

bench get-app https://github.com/resilient-tech/india-compliance --branch version-16
bench --site <site-name> install-app india_compliance

The Interest Calculator passes GST accounts and party GSTIN to Journal Entries. India Compliance hooks validate these on JE submit. No hard dependency.


Usage

Quick Start

  1. Create an Interest Rule — set rate, type, frequency, GL account, posting accounts
  2. Create an Interest Calculation — link the rule, set dates, click Calculate Interest
  3. Review entries — verify the period breakdown
  4. Submit — auto-creates Journal Entry with TDS/GST
  5. View — Interest Ledger report or Interest Certificate PDF

Batch Calculation

# Via bench console or API
frappe.call(
    "interest_calculator.interest_calculator.doctype.interest_calculation.interest_calculation.batch_calculate",
    interest_rules=json.dumps(["Rule A", "Rule B"]),
    from_date="2026-01-01",
    to_date="2026-06-30"
)

Scheduled Calculations

  1. Create an Interest Schedule — link a rule, set frequency + day of month
  2. Enable it — the daily cron picks it up automatically
  3. Set auto_submit if you want auto-finalization

Formulas

Simple Interest:

Interest = Principal × Rate × (Days / 365)

Compound Interest:

A = P × (1 + r/n)^(n×t)
    via exp(n×t × ln(1+r/n))  — pure Decimal, no float
Interest = A - P

Where n = compounding periods per year, t = time in years.

The 365-day year convention follows RBI guidelines for Indian banking — leap years are not adjusted.


Technical Notes

  • Frappe v16 tested — file-based reports (is_standard: Yes), before_submit validation guards
  • Button workaround — client script (interest_calculation.js) bypasses Frappe v16 run_doc_method list-format bug
  • Scheduler — daily cron in hooks.py runs run_scheduled_calculations() for enabled schedules
  • NamingIC-{####} autoname with series counter in tabSeries
  • Cache discipline — clear __pycache__ + bench clear-cache + bench restart after deploying Python updates
  • Stale code — Docker containers can accumulate root-owned file copies at shallow paths. Deploy only to the deep module path (where __pycache__ lives). Use docker exec -u root to nuke stale copies.

License

MIT © 2026 Ashutosh Varma