v2.6.0
Highlights
Achievement notification celebrations
Clicking an achievement_earned notification in the bell dropdown now fires the cannon for that specific achievement, scrolls and pulses its card on the achievements list, and lets the user step through the rest of their unread achievement notifications via a Continue Viewing button.
- The XP bar walks a single cursor across the full chain — starting at
(currentXP - sum of all unviewed achievement points)and landing on the user's true current XP/level by the final modal — so progression reads as one coherent journey instead of repeating the same animation on each modal. - Level boundary crossings trigger the level-flash animation as the cursor passes them.
- Level-up notifications are marked read when the chain naturally exhausts (the user has visually seen the level they reached); Dismiss All leaves them unread.
Trade query / analytics refactor
- New
TradeQueriesmodule centralizes the WHERE clause used by both the trade list and analytics aggregations, keeping displayed trades and statistics consistent. - Analytics cache unified:
AnalyticsCache.invalidate(userId)now clears both DB-backed and in-memory caches in one call. - Characterization tests added for
findByUserandgetAnalyticsto lock in current behavior.
Health data normalization
Health controller now normalizes data types to snake_case consistently across the API surface.
Other
- Frontend Vitest coverage added (auth store, date utils, P&L utils, notification center composable, global account filter composable, symbol autocomplete).
- Package management migrated to pnpm with a workspace.
- Removed dead
symbol_enrichmentandmae_mfe_estimationjob queue handlers.