Skip to content

Cumulative duration billing + cost strip at top of Invoke tab - #45

Merged
aakri0 merged 1 commit into
mainfrom
feat/cumulative-duration-and-cost-strip
May 1, 2026
Merged

Cumulative duration billing + cost strip at top of Invoke tab#45
aakri0 merged 1 commit into
mainfrom
feat/cumulative-duration-and-cost-strip

Conversation

@aakri0

@aakri0 aakri0 commented May 1, 2026

Copy link
Copy Markdown
Owner

Two improvements packaged together — both touch the cost story.

1. Pricing accuracy: cumulative duration

Bug. The worker rewrote `duration_seconds` on every terminal write, so a job that retried 3× at 5s each finished with `duration_seconds=5`, not 20. Pricing's `compute` and `memory` charges multiplied that one-attempt time, silently undercharging retried jobs by a factor of `attempts`. The per-request fee was correct (`attempts × per_request`), but compute/memory drifted.

Fix. The worker now reads the prior `duration_seconds` at the top of `handle_job`, adds this attempt's wall-clock, and writes the sum on every terminal and retry path. The field is a running total. Pricing keeps reading `duration_seconds` as before — it's now correct.

Verified end-to-end: a 4-attempt failed job (`raise Exception("boom")`, `max_retries=3`) reports:

  • `duration_seconds = 0.358` (sum of all four attempts)
  • `compute = 4.296e-06` = 0.358s × 0.5 vCPU × $0.000024 ✓
  • `request = 1.6e-06` = 4 × $0.0000004 ✓
  • total `$0.000006120` (~4× what the old code would have charged)

A new pricing test (`test_actual_cost_compute_uses_cumulative_duration`) pins the contract.

2. Cost moved to a horizontal strip at the top of Invoke

Why. Cost is what the user is reasoning about while configuring a job — should it be the first thing they see, not a square card competing with the result panel for attention. The previous big card was overweight for what's three numbers.

Layout. Slim full-width strip at the very top of the Invoke tab:

```
[ Estimated max ] [ Actual (· details ↓) ] [ Last 30 days · N jobs ]
[ $0.000507 ] [ $0.000003 ] [ $0.012345 · 73 ]
```

Click the Actual cell to expand a thin breakdown row underneath:

```
[ compute $0.000002 memory $0.000000 request $0.000000 network $0.000000 ]
```

Hidden until the user has data to look at. Strip stays compact when not in use.

Test plan

  • `pytest -q` — 171 passed (one new pricing test).
  • Live single submit: estimate appears immediately, actual + breakdown after the run.
  • Live 4-attempt failed job: cumulative duration in the response, compute charge against the full sum.
  • Burst 50 (with the `Load sample` compute snippet): `Last 30 days · 50 jobs` updates after the burst.
  • Click Actual cell: breakdown expands/collapses; hidden again when a new submit clears state.

Bumps: `app.js?v=16`, `styles.css?v=13`.

Pricing accuracy
================
Previously the worker rewrote duration_seconds on each terminal write,
so a job that retried 3× at 5s each ended up with duration_seconds=5,
not 20. Pricing's compute and memory charges multiplied that single-
attempt time and silently undercharged retried jobs.

The worker now reads the prior duration_seconds at the top of
handle_job, adds this attempt's wall-clock, and writes the sum on
every terminal *and* retry path. Pricing uses duration_seconds as a
running total; the per_request fee already correctly multiplied by
attempts, so combined the cost reflects all the compute that
actually happened.

Verified end-to-end: a 4-attempt failed job now reports
duration_seconds=0.358 and a compute charge against the full 0.358s
(not 0.09s).

UI repositioning
================
Cost moved from a separate card to a horizontal strip at the very
top of the Invoke tab. Three side-by-side cells:
  Estimated max  /  Actual (· details ↓)  /  Last 30 days · N jobs

Click the Actual cell to expand a breakdown row showing
compute / memory / request / network. Hidden until there's something
to expand.

Reasoning: cost is what the user is reasoning about *while*
configuring a job; it should be the first thing they see, not a
square card competing with the result panel for attention. The
strip uses less vertical space than the old card and gives the
Latest result panel back its breathing room.

Asset cache-busts: app.js?v=16, styles.css?v=13.
@aakri0
aakri0 merged commit d3950d1 into main May 1, 2026
3 checks passed
@aakri0
aakri0 deleted the feat/cumulative-duration-and-cost-strip branch May 1, 2026 22:29
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