release: publish saldo 0.1.0
This commit is contained in:
@@ -0,0 +1,60 @@
|
||||
from __future__ import annotations
|
||||
|
||||
from decimal import Decimal
|
||||
|
||||
from app.models import MonthlyAllocation, MonthlyEntryValue, MonthlyIncome, to_decimal
|
||||
|
||||
|
||||
class ComparisonService:
|
||||
def month_delta(self, current_month, previous_month) -> dict:
|
||||
if previous_month is None:
|
||||
zero = Decimal("0.00")
|
||||
return {
|
||||
"income_delta": zero,
|
||||
"cost_delta": zero,
|
||||
"remainder_delta": zero,
|
||||
"allocation_delta": zero,
|
||||
}
|
||||
return {
|
||||
"income_delta": self._total_income(current_month) - self._total_income(previous_month),
|
||||
"cost_delta": self._total_costs(current_month) - self._total_costs(previous_month),
|
||||
"remainder_delta": self._remainder(current_month) - self._remainder(previous_month),
|
||||
"allocation_delta": self._total_allocations(current_month)
|
||||
- self._total_allocations(previous_month),
|
||||
}
|
||||
|
||||
def top_entry_changes(self, current_month, previous_month, limit: int = 6) -> list[dict]:
|
||||
if previous_month is None:
|
||||
return []
|
||||
previous_values = {
|
||||
item.entry_id: to_decimal(item.planned_amount) for item in previous_month.entry_values
|
||||
}
|
||||
changes = []
|
||||
for item in current_month.entry_values:
|
||||
previous_amount = previous_values.get(item.entry_id, Decimal("0.00"))
|
||||
current_amount = to_decimal(item.planned_amount)
|
||||
delta = current_amount - previous_amount
|
||||
if delta:
|
||||
changes.append(
|
||||
{
|
||||
"entry_name": item.entry.name,
|
||||
"category_name": item.entry.category.name,
|
||||
"delta": delta,
|
||||
"current_amount": current_amount,
|
||||
"previous_amount": previous_amount,
|
||||
}
|
||||
)
|
||||
changes.sort(key=lambda item: abs(item["delta"]), reverse=True)
|
||||
return changes[:limit]
|
||||
|
||||
def _total_income(self, month) -> Decimal:
|
||||
return sum((to_decimal(item.amount) for item in month.incomes), Decimal("0.00"))
|
||||
|
||||
def _total_costs(self, month) -> Decimal:
|
||||
return sum((to_decimal(item.planned_amount) for item in month.entry_values), Decimal("0.00"))
|
||||
|
||||
def _total_allocations(self, month) -> Decimal:
|
||||
return sum((to_decimal(item.amount) for item in month.allocations), Decimal("0.00"))
|
||||
|
||||
def _remainder(self, month) -> Decimal:
|
||||
return self._total_income(month) - self._total_costs(month)
|
||||
Reference in New Issue
Block a user