Lab · Personal finance
Cupel (FinanceOS)
A self-hosted personal finance app that syncs bank transactions and puts net worth and goal progress first.
- Status
- Live · private
- Who uses it
- Andrew. It is built to support more than one account, with sign-in and billing, but today it is his own tool.
- Built with
- Node.js + Express · SQLite (one file per user) · Plaid · Stripe · Claude API · Capacitor · Render
The card payment planner, in its fixed order
ExampleExample paycheck $1,200
- 1Safety buffer$500 of $500 · full
- 2Minimums, each card$180 of $180 · full
- 3Extra payments$520 · what’s left
Shows its working: 1,200 − 500 buffer − 180 minimums = 520 extra
Duplicate-charge catch Example
Net worth over time Example
The problem
Most finance apps lead with spending categories. Cupel leads with the long-term picture, net worth and goals, and treats cashflow, tax deductions and debt as the levers that move it. The point is numbers trustworthy enough to act on.
How it works
Bank sync
Accounts connect through Plaid Link, so the app never sees a bank password. Transactions sync incrementally when Plaid signals new data.
Cashflow that separates sure from likely
“Guaranteed” income is kept apart from estimated income, so must-pay decisions only count money that is certain.
Card payment planner
Works in a fixed order: safety buffer, then minimums, then extra payments, and shows its working.
Goals with a verdict
Each goal shows the monthly amount needed against what is actually spare, and flags goals competing for the same dollar.
Net worth over time
A daily snapshot, with adding or removing an account recorded so it never reads as a gain or a loss.
Duplicate charges
Catches double charges across pending and posted transactions, refunds and merchant-name variants.
Plus
Budgets, subscription and price-increase detection, a retirement planner, and push alerts kept to things that are urgent and actionable.
Where AI fits
- Tax-deduction pre-sort: each transaction is tiered likely / possible / no for review, never filed.
- “Ask” answers questions about your own data; “Assistant” turns a plain-English scenario into proposed plan changes.
- All Claude calls go through one wrapper with retries, a daily spend cap and usage logging.
Guardrails
Locked by default
Every route needs a login, and the app refuses to start without a password configured.
Encrypted bank tokens
Bank access tokens are encrypted at rest (AES-256-GCM) with a separate key per user.
AI never does the maths
Ask’s tools are read-only, the database computes every figure, and Assistant changes need an explicit click.
Not tax advice
Deduction tiers are a pre-sort for a human to review. Nothing is filed automatically.
Engineering notes
One database file per user
Instead of a user column in every table. With hundreds of hand-written queries, a file boundary can’t be forgotten, and export or delete becomes a file operation.
“The model picks the query, the database computes, the model explains”
So every number in an AI answer comes from the database, not the model.
Native sign-in
The phone shells can’t keep a web cookie, so the same signed session travels as a bearer token to allow-listed app origins only.
App Store rules designed in
No purchase links inside the native app, and the experimental trading feature is removed from client builds; the build fails if any trace survives.
What’s next
iOS and Android builds exist but are not submitted. Next is the paperwork for the stores: a legal entity, developer accounts, public privacy and terms pages.