Imports name this capability’s declared dependencies, which fune builds next to it in your project; each one links to its page.
from typing import List, Optional, Sequence
from .dates_days_between import days_between ← from dates.days-between ^1.0.0 · built alongside by fune
from .finance_aged_debt_types import AgedDebt, AgedDebtBucket, OpenInvoice
from .money_add import add_money ← from money.add ^1.0.0 · built alongside by fune
from .money_amount import Money, money ← from money.amount ^1.0.0 · built alongside by fune
def aged_debt(invoices: Sequence[OpenInvoice], as_at: str, bucket_days: Sequence[int], currency: str) -> AgedDebt:
"""Bucket open invoices by how many days past their due date they are.
Age runs from the due date, not the invoice date: an invoice due today is
current. Every bucket is returned, empty or not, so a report's columns are
fixed.
"""
if len(bucket_days) == 0:
raise ValueError("bucketDays needs at least one boundary")
previous = 0
for bound in bucket_days:
if isinstance(bound, bool) or not isinstance(bound, int) or bound <= previous:
raise ValueError(
"bucketDays must be whole days, ascending, from 1: received %s after %s" % (bound, previous)
)
previous = bound
zero = money(0, currency)
labels: List[str] = ["current"]
froms: List[Optional[int]] = [None]
tos: List[Optional[int]] = [0]
start = 1
for bound in bucket_days:
labels.append("%d-%d" % (start, bound))
froms.append(start)
tos.append(bound)
start = bound + 1
labels.append("%d+" % (start - 1,))
froms.append(start)
tos.append(None)
totals: List[Money] = [zero for _ in labels]
refs: List[List[str]] = [[] for _ in labels]
total = zero
for invoice in invoices:
overdue = days_between(invoice.due_date, as_at)
index = 0
if overdue > 0:
index = len(bucket_days) + 1
for i, bound in enumerate(bucket_days):
if overdue <= bound:
index = i + 1
break
totals[index] = add_money(totals[index], invoice.outstanding)
refs[index].append(invoice.reference)
total = add_money(total, invoice.outstanding)
buckets = [
AgedDebtBucket(label=labels[i], from_days=froms[i], to_days=tos[i], total=totals[i], references=refs[i])
for i in range(len(labels))
]
return AgedDebt(as_at=as_at, buckets=buckets, total=total)