Private
Public Access
1
0

Implement Phase 3: financial features frontend (budgets, scheduled transactions, loans)

Add API service files and replace stub views with full implementations:
- Budgets: month navigator, budget items table with progress bars, create/edit/delete
- Scheduled Transactions: data table with skip/post-now actions, add/edit dialog
- Loans: loan list, detail view with amortization schedule, payoff scenario calculator

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
Catherine Renelle
2026-02-08 12:14:43 -05:00
parent 2ace39c544
commit 23d73736c9
6 changed files with 1062 additions and 16 deletions
+19
View File
@@ -0,0 +1,19 @@
import api from './api'
import type { Budget, BudgetItem } from '@/types'
export const budgetsApi = {
getByMonth: (year: number, month: number) =>
api.get<Budget>(`/budgets/${year}/${month}`),
create: (data: { year: number; month: number; notes?: string; items: { categoryId: string; budgetedAmount: number }[] }) =>
api.post<Budget>('/budgets', data),
update: (id: string, data: { notes?: string; items: { categoryId: string; budgetedAmount: number }[] }) =>
api.put<Budget>(`/budgets/${id}`, data),
delete: (id: string) =>
api.delete(`/budgets/${id}`),
getActuals: (id: string) =>
api.get<BudgetItem[]>(`/budgets/${id}/actual`),
}
+16
View File
@@ -0,0 +1,16 @@
import api from './api'
import type { LoanDetail, PayoffScenario } from '@/types'
export const loansApi = {
getLoanDetail: (accountId: string) =>
api.get<LoanDetail>(`/loans/${accountId}/amortization`),
createLoanDetail: (accountId: string, data: any) =>
api.post<LoanDetail>(`/loans/${accountId}`, data),
updateLoanDetail: (accountId: string, data: any) =>
api.put<LoanDetail>(`/loans/${accountId}`, data),
calculatePayoff: (accountId: string, data: { extraMonthlyPayment?: number; lumpSumPayment?: number; lumpSumDate?: string }) =>
api.post<PayoffScenario>(`/loans/${accountId}/payoff-scenario`, data),
}
+25
View File
@@ -0,0 +1,25 @@
import api from './api'
import type { ScheduledTransaction } from '@/types'
export const scheduledApi = {
getAll: () =>
api.get<ScheduledTransaction[]>('/scheduled-transactions'),
getById: (id: string) =>
api.get<ScheduledTransaction>(`/scheduled-transactions/${id}`),
create: (data: any) =>
api.post<ScheduledTransaction>('/scheduled-transactions', data),
update: (id: string, data: any) =>
api.put<ScheduledTransaction>(`/scheduled-transactions/${id}`, data),
delete: (id: string) =>
api.delete(`/scheduled-transactions/${id}`),
skip: (id: string) =>
api.post<ScheduledTransaction>(`/scheduled-transactions/${id}/skip`),
postNow: (id: string) =>
api.post(`/scheduled-transactions/${id}/post-now`),
}