Skip to content

Add monthly view to TUI#133

Merged
mike1858 merged 2 commits intoPiebald-AI:mainfrom
Sewer56:feature/monthly-view-toggle
Apr 5, 2026
Merged

Add monthly view to TUI#133
mike1858 merged 2 commits intoPiebald-AI:mainfrom
Sewer56:feature/monthly-view-toggle

Conversation

@Sewer56
Copy link
Copy Markdown
Contributor

@Sewer56 Sewer56 commented Mar 15, 2026

Changes

Press m in the TUI to toggle between daily and monthly stats. The monthly view rolls up all your daily usage into per-month totals, making it easier to see longer-term trends.

image

Notes

This works, but it's not perfect.
The changes could be a bit cleaner; but that'd require a larger refactor.
I wanted a quick view personally; and felt like throwing away the code would be a waste, so here it is.

Use it, or do anything else with it :p

Refactor needed: Notably src/tui.rs has grown too large (~500 lines of changes in this PR alone). It should be split into smaller modules (e.g., separate files for rendering, state management, input handling).

Summary by CodeRabbit

  • New Features

    • Added daily and monthly aggregate view modes for the TUI statistics display
    • Enhanced date filtering with improved pattern matching for date inputs
    • Added upload progress visualization and tracking
  • Tests

    • Expanded test coverage for aggregation functionality and date filtering

Allow the stats table to switch between daily and monthly periods with a hotkey so broader usage trends are easier to inspect without leaving the dashboard.
@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented Mar 15, 2026

Warning

Rate limit exceeded

@mike1858 has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 4 minutes and 59 seconds before requesting another review.

Your organization is not enrolled in usage-based pricing. Contact your admin to enable usage-based pricing to continue reviews beyond the rate limit, or try again in 4 minutes and 59 seconds.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 9cfb8423-3ee5-4711-a894-320ab6cf7837

📥 Commits

Reviewing files that changed from the base of the PR and between 1db144d and de5d699.

📒 Files selected for processing (1)
  • src/tui/logic.rs
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@Sewer56 Sewer56 marked this pull request as ready for review March 15, 2026 16:17
coderabbitai[bot]
coderabbitai Bot previously requested changes Mar 15, 2026
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🧹 Nitpick comments (1)
src/tui.rs (1)

110-120: Consider caching monthly aggregates per refresh.

get_aggregate_stats() rebuilds the rolled-up BTreeMap every call. In monthly mode this helper is hit by navigation, date jump, and draw paths, so one keypress can re-aggregate the same daily_stats several times.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/tui.rs` around lines 110 - 120, get_aggregate_stats currently recomputes
the monthly rollup every call; to fix, add a cache that stores the result of
aggregate_daily_stats_by_month(&view.daily_stats) and only rebuild it when
daily_stats changes (e.g., on a refresh/update). Concretely: add a
cached_monthly field (Option<...>) to the owner of AnalyzerStatsView or
AnalyzerStatsView itself, set/invalidate that cache whenever daily_stats is
updated/refreshed, update get_aggregate_stats to return
AggregateStatsData::Owned from the cached_monthly when
AggregateViewMode::Monthly (computing and storing it on first use if absent),
and ensure cache invalidation happens on the same code paths that mutate or
reload view.daily_stats so navigation/draw calls reuse the cached monthly
BTreeMap.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@src/tui.rs`:
- Around line 1205-1207: The clamp and metadata must be computed from the
actually rendered subset rather than the full map: change the code so
get_aggregate_stats/aggregate_stats.as_map() is invoked on the same
filtered/reordered collection used to render the table (the rendered_rows /
rendered_aggregate_map), then call clamp_table_selection(table_state,
rendered_aggregate_map.len() + 2); also update the routines that derive best-row
indices, totals labels and model metadata (the code paths that currently read
from the unfiltered order) to read from that same rendered_aggregate_map so
reversed/filtered views and search jumps show correct max markers, selected row
and Total (...m) label.

In `@src/tui/logic.rs`:
- Around line 84-96: The single-number branch currently treats any parsed number
>31 as year and 1..=12 as month but lets 13..=31 fall-through to the substring
match, causing "/20" or "/25" to match year substrings; update the logic in the
parts[0] parse block so that: if number > 31 return day_year == number; else if
(13..=31).contains(&number) return a comparison against the day-of-month field
(use the existing day-of-month variable or parse it from day); else if
(1..=12).contains(&number) return day_month == number; otherwise fall back to
return day.contains(trimmed); ensure parts[0], number, day_year, day_month and
the day substring match are the referenced symbols to locate where to change.

---

Nitpick comments:
In `@src/tui.rs`:
- Around line 110-120: get_aggregate_stats currently recomputes the monthly
rollup every call; to fix, add a cache that stores the result of
aggregate_daily_stats_by_month(&view.daily_stats) and only rebuild it when
daily_stats changes (e.g., on a refresh/update). Concretely: add a
cached_monthly field (Option<...>) to the owner of AnalyzerStatsView or
AnalyzerStatsView itself, set/invalidate that cache whenever daily_stats is
updated/refreshed, update get_aggregate_stats to return
AggregateStatsData::Owned from the cached_monthly when
AggregateViewMode::Monthly (computing and storing it on first use if absent),
and ensure cache invalidation happens on the same code paths that mutate or
reload view.daily_stats so navigation/draw calls reuse the cached monthly
BTreeMap.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 61154f04-2114-48a6-87a9-bc659339419e

📥 Commits

Reviewing files that changed from the base of the PR and between 6610d71 and 1db144d.

📒 Files selected for processing (3)
  • src/tui.rs
  • src/tui/logic.rs
  • src/tui/tests.rs

Comment thread src/tui.rs
Comment thread src/tui/logic.rs
Numbers 13-31 fell through both the >31 (year) and 1..=12 (month) checks,
landing on day.contains(trimmed). This caused e.g. typing '20' to
substring-match against '2025-...' dates instead of matching day-of-month 20.

Added explicit (13..=31) branch that compares against day_number.
@mike1858 mike1858 enabled auto-merge (squash) April 5, 2026 16:29
@mike1858 mike1858 merged commit f506cc6 into Piebald-AI:main Apr 5, 2026
6 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants