theam / theam/facility

Monthly budget can be exceeded when several turns run in parallel

Open
#401 0 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Dominant language
TypeScript
Stars
71
Forks
64
Avg merge
15h 38m
Merged PRs (30d)
66

Description

In short: the budget is checked once per turn, before the provider call, against the sum of turns that already finished. Nothing holds a place for turns still running, so several turns that start close together all pass the check with the same balance, and the project ends the month over its limit. Lines are from main at 5e6b6fc.

What I see in the code

README.md:92-94 says a running call may finish and is accounted afterwards. That covers one turn, not N parallel turns each spending the same last dollars.

Scenario

A project has 5 USD left. Three stories get a message at the same time and three workers pick them up. Each sees 5 USD left and starts. Each turn costs 4 USD. The month ends 7 USD over the limit. More workers and longer turns make the gap bigger.

Relation to #399

Same root: the number the check uses is not the real spend. #399 is spend never booked; this is spend booked too late. A reservation taken before the call also covers the dead-worker case, because the cost is held before the engine starts.

Proposal

Like a card payment: authorize first, capture later.

  1. Before the call, insert a reservation with an estimated cost. A simple per-model estimate could be a starting point.
  2. Block if limit - spent - active reservations < estimate. Check and insert in one transaction, or under a per-project advisory lock as catalog.ts:326 does.
    This makes the limit stricter near the end of the month, which is the goal.
  3. When the turn ends, replace the reservation with the real cost.
  4. A reservation never settled (worker died) is captured at the reserved amount, not released.

A good estimate is hard for long agent turns. If that is a blocker, a simpler first step could be to allow only one running turn per project once the remaining budget is below a threshold.

Questions
  • Is the soft limit intended? If yes, it may be worth mentioning in the docs that parallel turns can go over it.
  • If not, would you accept a PR in this direction? I can do it, with the tests AGENTS.md asks for.

Thanks for putting Facility out early. It is a good base to build on.

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start with services/api/src/insights/costs.ts and the dispatcher paths at services/api/src/turns/dispatcher.ts, then read the WorkerTurnGuard and the transaction or locking pattern in agents/catalog.ts. Check AGENTS.md for required tests. Done means concurrent turns cannot all spend the same remaining budget, reservations are settled after completion, and abandoned reservations follow the stated capture behavior.

Written by the indexing model from the issue text.

Assessment

Tech stack
typescript
Domain
api, backend, database, distributed-systems
Issue type
Bug
Difficulty
5/5
Estimated time
Over a week
Activity status
Active
Clarity
Mostly clear
Newbie friendliness
45/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.