feat(gating): routes + Sidebar (budget, rapports avancés, bilan) #305

Closed
maximus wants to merge 1 commit from issue-299-routes-sidebar into issue-298-require-feature

1 commit

Author SHA1 Message Date
le king fu
553da0ce8c feat(gating): gate routes and Sidebar for budget, advanced reports, balance
Apply the tier gating to routes and navigation on top of the #298 UI
guard:

- App.tsx: pathless RequireFeature layout-routes grouping /balance,
  /balance/accounts, /balance/snapshot under "balance"; /reports/
  highlights|compare|category|cartes under "reports-advanced"; /budget
  under "budget"; /adjustments under "adjustments". The /reports hub and
  /reports/trends stay Free and ungated.
- NavItem gains an optional `feature?: FeatureKey`; set in NAV_ITEMS on
  budget, adjustments and balance only — NOT on reports (Free hub).
- Sidebar: local NavLock child component (hook at component top level)
  renders a lock badge only when the license is ready AND the feature is
  not allowed — no locked flash at boot; items stay clickable and lead
  to the upsell via the gated route. Tooltip/aria reuse nav.locked.
- ReportsPage hub: single useEntitlement("reports-advanced") call
  drives a `locked` badge on the 4 advanced tiles via a new additive
  HubReportNavCard `locked?` prop; the Trends tile is never locked.
- Pure contract test on NAV_ITEMS (gated trio present, reports/Free
  items ungated, exactly 3 of 9 gated).

No new i18n strings (nav.locked shipped with #298), no DB migration.
Changelog centralized in #302.

Resolves #299

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-20 22:12:51 -04:00