Implement Reporting tab (#276)

* First reporting version

* Fixes for all tabs

* Transactions table

* Budget section re-design

* FIX exports

Fix transactions table aggregation

* Add support for google sheets

Remove pdf and xlsx for now

* Multiple fixes

- Trends & Insights now follows top filter
- Transactions Breakdown removed filters, implemented sort by amount.
- The entire section follows top filters.
- Export to CSV adds per month breakdown

* Linter and tests

* Fix amounts

- Correctly handle amounts across the views and controller.
- Pass proper values to do calculation on, and not loose precision

* Update Gemfile.lock

* Add support for api-key on reports

Also fix custom date filter

* Review fixes

* Move budget status calculations out of the view.

* fix ensures that quarterly reports end at the quarter boundary

* Fix bugdet days remaining

Fix raw css style

* Fix test

* Implement google sheets properly with hotwire

* Improve UX on period comparison

* FIX csv export for non API key auth
This commit is contained in:
soky srm
2025-11-05 14:54:45 +01:00
committed by GitHub
parent 9b6ec259bd
commit d9f8d064af
17 changed files with 2398 additions and 52 deletions

View File

@@ -75,6 +75,34 @@ class BudgetCategory < ApplicationRecord
(actual_spending / budgeted_spending) * 100
end
def bar_width_percent
[ percent_of_budget_spent, 100 ].min
end
def over_budget?
available_to_spend.negative?
end
def near_limit?
!over_budget? && percent_of_budget_spent >= 90
end
# Returns hash with suggested daily spending info or nil if not applicable
def suggested_daily_spending
return nil unless available_to_spend > 0
budget_date = budget.start_date
return nil unless budget_date.month == Date.current.month && budget_date.year == Date.current.year
days_remaining = (budget_date.end_of_month - Date.current).to_i + 1
return nil unless days_remaining > 0
{
amount: Money.new((available_to_spend / days_remaining), budget.family.currency),
days_remaining: days_remaining
}
end
def to_donut_segments_json
unused_segment_id = "unused"
overage_segment_id = "overage"