How it holds up

22 books and 71 pictures since August 2026. 13 of them are fully illustrated, and those are the only ones the cost figures below use. Small numbers, and they are real ones — this is a thing one family uses, not a demo.

What a book costs

Provider-reported usage recorded on each row as it happens, never estimated: the text generation plus every picture. Only fully illustrated books count — a book with half its pictures is a measurement of half a book. Waste is included. A picture that was drawn, billed and then failed to store is money the book cost, and leaving it out would flatter the figure while the section below describes that exact spend.

Median
$0.14
Cheapest
$0.10
Dearest
$0.19
Books measured
13

How long a picture takes

Gaps between consecutive finished pictures, kept when they fall between 5 and 150 seconds — the route aborts its own provider call at 120, so anything longer cannot be one drawing. Nothing records which run a job belonged to, so a slow image and a person pausing between two clicks are indistinguishable here. Read it as a distribution, not a stopwatch.

Median
30s
Fastest
20s
Slowest
91s
Gaps in range
40

8 checks, and the bug each one exists because of

Every one of these was written after something got through. They run in two places, doing different jobs: a local hook gives fast feedback and can be skipped deliberately, and CI runs them on every pull request, where they gate the merge and cannot be bypassed. That second layer exists because the first one was bypassed on nearly every commit while it was assumed to be running. This list comes from the same manifest CI asserts against the scripts themselves, so it cannot quietly describe checks that no longer exist.

Which versions made what

Model ids are pinned dated snapshots rather than floating aliases, and the prompt version is stored with each book, so any output can be traced back to what produced it. Prompt versions are listed oldest first with what each one changed — every bump was a correction to something that had gone wrong, which is the part a version number on its own does not tell you.

VersionKindBooks
gpt-image-2-2026-04-21image19
2026-08-01.1The ceiling on an image prompt moved from 500 to 1500 characters. The old limit made valid output impossible — the character description the model is required to repeat verbatim was longer than the whole budget — so it changed what output could be accepted at all.prompt2
2026-08-02.1Requests started carrying a response schema, so the model is constrained by the API rather than only by the prompt asking nicely. Two production failures came from trusting the prompt alone, and drift is non-deterministic, so local runs passing had proved nothing.prompt4
2026-08-02.2The model began reporting which language it wrote in, so a memory written in Spanish produces a Spanish story. Deliberately kept outside the part of the response the parent can edit, so it cannot be rewritten by the client.prompt3
2026-08-02.3The model started writing the cover's own art prompt. Before this the cover was drawn from page one's prompt, so every book's cover and first page were the same picture — nothing threw, and no test caught it.prompt13
gemini-3.5-flashtext22

What went wrong

Grouped by who paid and what is safe to do next, which is more useful than any error string — each category is a decision the system had to make. No message text is printed: an unanticipated provider message must not be able to reach a public page, so anything matching no known shape is counted and nothing more. The full text is in the server logs. Resolution is not tracked: when a person resolves a locked job by hand the row changes and no transition is recorded, so these are the current state and not a history.

Known waste: $0.04 across 2 jobs — billed by the provider, never delivered to a reader, and counted in the cost figures above rather than quietly dropped. “Known” is doing real work in that sentence: an outcome that ended without a clear answer has no recorded cost, so it could never be part of this total. There are none right now.

What happenedStateCount
Drawn and billed, but not stored
The image was produced, and paid for, and then storing it failed. Retrying would pay for it a second time, so the slot stays locked for a person.
failed2
Back to the story