Skip to content

Auto funded envelopes - #792

Merged
michaelst merged 3 commits into
mainfrom
auto-funded-envelopes
Sep 5, 2026
Merged

michaelst merged 3 commits into
mainfrom
auto-funded-envelopes

Conversation

@michaelst

Copy link
Copy Markdown
Owner

No description provided.

michaelst and others added 3 commits August 16, 2026 21:19
Budgets fill themselves from a monthly amount instead of the user
splitting every paycheck by hand. A Funding records what one month put
into one budget; balance is now fundings + allocations + adjustment.
The job runs daily rather than monthly, since funding a month is
idempotent, so a missed run heals itself.

Rollover is per envelope. On, an overspend carries and eats into the
next month. Off, the month funds what brings the balance back to the
amount, so the envelope starts whole and leftover does not accumulate.

Income is a fourth budget type, one per source, so a paycheck and a card
reward are never the same figure. Income budgets receive and never spend;
every other budget nets positive allocations against its spending, which
is what makes a reimbursement cancel the spend it repays.

Behaviour changes to expect on deploy:

- Netting is retroactive. Any past month where a positive amount was
  allocated to a spending budget reports less spent than before.
- Spendable no longer takes an overspent envelope off the pool twice.
  Anyone sitting on a negative envelope sees the figure move.
- An envelope in the hole reads OVERSPENT with the shortfall as a
  positive figure, where it used to read LEFT with a minus sign.
- rollover is required on the Budget API response.

funding_amount ships nil everywhere, so no budget funds itself until the
user sets an amount.

Co-Authored-By: Claude Opus 5 <[email protected]>
An envelope had two amounts that were the same number wearing two hats:
what its spending was measured against, and what a month put into it.
That is what put two clocks on one card - a lifetime balance above a
this-month bar, disagreeing.

It keeps one. Having it is what makes the envelope fund itself, so the
balance is always a figure the month can explain. The migration folds
budgeted_amount into funding_amount, so no amount is lost and every
existing envelope starts funding. Goals keep two, because a target and a
monthly contribution are different numbers; tracking and income keep the
figure they are measured against.

The envelope card reads REMAINING, or OVERSPENT with the shortfall as a
positive figure. The form asks two questions and no more: Budget Per
Month, and Remaining.

Funding a month by hand is gone with it - the fund_budget MCP tool and
the update_funding action. A month is funded one way now, by the amount
on the budget. That left Funding.changeset unreachable, so the schema is
fields only.

Behaviour changes to expect on deploy:

- budgeted_amount is null on every envelope, and its value now lives in
  funding_amount. Clients reading the old field see nothing there.
- Envelopes that had an amount but were never funded start funding.
  Their historical balance is left alone, so one that was spent from
  before funding existed still reads OVERSPENT until it is corrected.

Co-Authored-By: Claude Opus 5 <[email protected]>
@michaelst
michaelst merged commit e53cbfa into main Sep 5, 2026
5 of 6 checks passed
@michaelst
michaelst deleted the auto-funded-envelopes branch September 5, 2026 05:37
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.

1 participant