Adds the user-facing layer on top of the Rust license commands shipped
in #46.
- `licenseService.ts` thin wrapper around the new Tauri commands
- `useLicense` hook follows the project's useReducer pattern (idle,
loading, ready, validating, error) and exposes `submitKey`,
`refresh`, and `checkEntitlement` for cross-component use
- `LicenseCard` shows the current edition, the expiry date when set,
accepts a license key with inline validation feedback, and links to
the purchase page via `openUrl` from `@tauri-apps/plugin-opener`
- Card is inserted at the top of `SettingsPage` so the edition is the
first thing users see when looking for license-related actions
- i18n: new `license.*` keys in both `fr.json` and `en.json`
- Bilingual CHANGELOG entries
Introduces the offline license infrastructure for the Base/Premium editions.
- jsonwebtoken (EdDSA) verifies license JWTs against an embedded Ed25519
public key. The exp claim is mandatory (CWE-613) and is enforced via
Validation::set_required_spec_claims.
- Activation tokens (server-issued, machine-bound) prevent license.key
copying between machines. Storage is wired up; the actual issuance flow
ships with Issue #49.
- get_edition() fails closed to "free" when the license is missing,
invalid, expired, or activated for a different machine.
- New commands/entitlements module centralizes feature → tier mapping so
Issue #48 (and any future gate) reads from a single source of truth.
- machine-uid provides the cross-platform machine identifier; OS reinstall
invalidates the activation token by design.
- Tests cover happy path, expiry, wrong-key signature, malformed JWT,
unknown edition, and machine_id matching for activation tokens.
The embedded PUBLIC_KEY_PEM is the RFC 8410 §10.3 test vector, clearly
labelled as a development placeholder; replacing it with the production
public key is a release-time task.
- Correct CHANGELOG to reflect default type is expense, not all types
- Validate select onChange value against allowed CategoryTypeFilter values
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- Default categoryType filter to "expense" so top-N ranking is not
skewed by mixing income and expense amounts
- Remove redundant showFilterPanel condition (hasCategories already
covers the overTime tab)
- Add unit tests for getCategoryOverTime query construction and output
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
The Category Over Time report previously only showed expenses (t.amount < 0).
This removes that filter so all transaction types are shown by default,
and adds a type filter (expense/income/transfer) in the right filter panel.
Ref: simpl-resultat#41
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Includes fixes#34, #37, #39: budget prev year actuals, changelog sync via Vite, inline buildPrevYearTotalMap.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The 3-line helper was exported solely for testing. Inlining it removes the
export-for-test pattern and eliminates 50 lines of tests that were
disproportionate for a trivial filter-and-set loop.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Revert public/ changelog changes (syncChangelogs copies from root)
- Replace manual __dirname with import.meta.dirname
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
syncChangelogs() in vite.config.ts already handles copying changelogs
to public/ on dev/build start. The prebuild npm script was redundant
and introduced a platform dependency (cp command).
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Transaction amounts are already signed in the DB (expenses negative,
income positive). Remove Math.abs() normalization and stop multiplying
by sign at display time to avoid double negation.
Extract buildPrevYearTotalMap as a testable exported function and
rewrite tests to import the real function instead of reimplementing it.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Fix sign bug in previous year actuals column: transaction amounts are
stored with sign in the DB (expenses negative) but budget entries are
always positive. Apply Math.abs() when building the previousYearTotal
map so the display-time sign multiplier works correctly.
Add unit tests for the normalization logic verifying that both expense
(negative in DB) and income (positive in DB) amounts are correctly
handled.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The in-app changelog page reads from public/CHANGELOG*.md which were
stale (last synced at 0.6.3). Add automatic sync via Vite config
(runs on dev/build start) and npm prebuild script so public/ copies
are always up to date without manual intervention.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add vitest and 17 tests covering computeDateRange (all periods
including January rollover) and buildMonthOptions (length, order,
rollover, label formatting). Add test/test:watch npm scripts.
Ref #33
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Replace planned budget data with actual transaction totals for the
previous year column in the budget table. Add getActualTotalsForYear
helper to budgetService.
Ref #34
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Remove non-null assertions on bYear/bMonth in useDashboard fetchData
by making parameters required
- Extract shared computeDateRange and buildMonthOptions into
src/utils/dateRange.ts to eliminate duplication across useDashboard,
useReports, DashboardPage and ReportsPage
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Add budgetYear/budgetMonth state to useDashboard hook with last
completed month as default
- Add month dropdown selector in the dashboard BudgetVsActual title
- Reduce dropdown font size in both Reports and Dashboard pages
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Clean up the sticky category cell className: remove the duplicated
px-3 for top-level parents and break the long ternary into readable
multi-line format.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Remove dead code: navigateBudgetMonth function and its export from
useReports.ts (replaced by setBudgetMonth, no longer imported anywhere)
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Replace semi-transparent backgrounds on sticky columns with opaque
color-mix equivalents so scrolled content is fully hidden
- Add opaque background to section header sticky td
- Extract IIFE month options in ReportsPage into a useMemo
- Add sticky left-0 positioning to all category cells in BudgetVsActualTable
- Replace MonthNavigator arrows with inline title + dropdown month selector
- Default budget month to previous completed month instead of current
- Add i18n keys for new title prefix (FR/EN)
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Show category names permanently in compact form (text-xs) so they
are always discoverable. Percentages appear only on chart hover to
save space, matching the original request while keeping the legend
accessible without interaction.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Extract reorderRows into shared utility (src/utils/reorderRows.ts) to
deduplicate identical function in BudgetTable and BudgetVsActualTable
- Restore alphabetical sorting of children in budgetService.ts
- Fix styling for intermediate parent rows at depth 2+ (was only handling
depth 0-1)
- Reduce pie chart size (height 220->180, radii reduced) and padding to
give more space to the table
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Make reorderRows() recursive to support subtotals toggle at all depth
levels (not just depth 0-1)
- Restore pie chart legend (show on hover only to save space)
- Give more horizontal space to budget table (3/4 grid vs 2/3)
- Replace flat alphabetical sort with tree-order traversal so child
categories appear directly under their parent subtotal row
- Make category hierarchy recursive (supports arbitrary depth)
- Reduce pie chart width from 1/2 to 1/3 of the dashboard
- Show pie chart labels only on hover via tooltip
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Tooltip was blending with the legend labels at the bottom of the chart,
especially when showing all categories at once. Added shadow and z-index
to ensure the tooltip stands out from the background.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Move the pie chart title to DashboardPage as an external h2,
matching the pattern used by BudgetVsActual and ExpensesOverTime sections.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add a read-only column showing the annual budget total from the
previous year for each category. This serves as a baseline reference
when planning the current year's budget.
- Add previousYearTotal field to BudgetYearRow type
- Fetch previous year budget entries in useBudget hook
- Display column between Category and Annual in BudgetTable
- Propagate totals through parent/subtotal/section/grand total rows
- Add i18n keys for FR ("Année préc.") and EN ("Prev. Year")
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- CLAUDE.md: bump version to 0.6.3
- architecture.md: update version, component counts, dashboard description
- guide-utilisateur.md: rewrite dashboard section (budget table, chart, no recent transactions)
- i18n docs: update dashboard help text in both FR and EN
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Default period changed from month to year-to-date
- Remove recent transactions section
- Add expenses over time stacked bar chart (by category/month)
- Add budget vs actual table (current month)
- Reorganize layout: cards, pie + budget table, full-width chart
Closes#15
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Section subtotals: text-sm font-semibold with more padding.
Grand totals: text-sm font-bold with border-t-2 and extra padding.
Applied consistently across BudgetTable, BudgetVsActualTable,
MonthlyTrendsTable, CategoryOverTimeTable, CategoryTable,
and DynamicReportTable.
Closes#14
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Increase category over time limit from 8 to 50 so all categories appear.
Fix category name visibility: use foreground color for bar chart Y-axis
labels and chart legend text instead of muted/inherited colors.
Closes#13
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>