feat: add month breakdown and session backups
Allow recurring costs and confirmations to remain unassigned when created from a purchase without a post. Add browser backup retention and restore controls, with coverage and documentation updates.
This commit is contained in:
1 parent
019517e6e9
commit
7cccd7a41a
32 files changed
+640
-41
No files matched your search
@@ -0,0 +1,29 @@
|
||||
import type { MonthViewModel } from "../domain/views.ts";
|
||||
|
||||
export type MonthPieMode = "spending" | "allocation";
|
||||
export interface MonthPieSlice {
|
||||
id: string;
|
||||
label: string;
|
||||
amount: number;
|
||||
}
|
||||
|
||||
/** Chart data comes from the same folded figures as the month table. */
|
||||
export function monthPieData(view: MonthViewModel, mode: MonthPieMode) {
|
||||
const items: MonthPieSlice[] = view.rows.map(({ post, figures }) => ({
|
||||
id: post.id,
|
||||
label: post.name,
|
||||
amount: mode === "spending" ? figures.charges : figures.allocation,
|
||||
}));
|
||||
if (mode === "spending" && view.looseCharges !== 0) {
|
||||
items.push({ id: "unassigned", label: "Unassigned", amount: view.looseCharges });
|
||||
}
|
||||
const byAmount = (a: MonthPieSlice, b: MonthPieSlice) => b.amount - a.amount || a.label.localeCompare(b.label);
|
||||
const positive = items.filter((item) => item.amount > 0).sort(byAmount);
|
||||
const adjustments = items.filter((item) => item.amount < 0).sort((a, b) => a.amount - b.amount);
|
||||
return {
|
||||
positive,
|
||||
adjustments,
|
||||
positiveTotal: positive.reduce((sum, item) => sum + item.amount, 0),
|
||||
netTotal: mode === "spending" ? view.totalCharges : view.totalAllocation,
|
||||
};
|
||||
}
|
||||
Reference in new issue
Block a user