AiBook · Jeremy Schoemaker · 2026 · ch-49.html

It Works While You Sleep

(Spine Ch. 49.)

“Early to bed and early to rise, makes a man healthy, wealthy and wise.” Benjamin Franklin, Poor Richard’s Almanack (1735)

Eleven agents, two workflows, one MinIO bucket, one database. By morning the evidence said eight tests were failing on clean main, three merges had blown up, and a toolbar badge still needed building. Three alarms, all ugly, all sitting there waiting with the coffee. I read them in order and started fixing the first one. The tell was small enough that I walked past it twice: the assertion values were not the same from one run to the next. Real regressions do not do that.

At 2am on 13 August 2026 a review agent on airank ran a SELECT against production and found that an offload job I had already approved would have overwritten 337,353 rows of archive pointers. I was asleep. I did not approve, review, or know about that catch until coffee. The machinery that found it was not the smart part of the stack. It was a query.

Bottom line: Unattended overnight work is not a model capability. It is a verification capability. The agent is allowed to run while you sleep exactly as far as something cheap and deterministic can tell you in the morning whether it worked, and not one inch further. If the only artifact waiting for you at 7am is a report of what the agent would do, you did not run an overnight job. You ran a very expensive brainstorm and paid for eight hours of GPU time to have it read nicely.

The thing that has to run all night is the check, not the model.


When it bites


The pattern

Among the longest-running Claude Code sessions, the 99.9th-percentile time the agent works before stopping nearly doubled in three months, from under 25 minutes to over 45 minutes (Anthropic, February 2026). Same paper: new users run full auto-approve in roughly 20% of sessions, experienced users in over 40%.

Forty-five minutes is not a night. The gap between “45 minutes at p99.9” and “burned down ten jobs by morning” is filled by structure, not a better model. Ralph Loop, which shipped in Anthropic’s official Claude Code plugin marketplace as ralph-wiggum, is the crude version: an autonomous loop that runs for hours unattended, marketed for “night batch jobs that need to be finished in the morning” (Paddo.dev, December 2025; Obvious Works, March 2026). Finished in the morning. That’s what she said.

The loop is the easy half. The hard half is the sentence Zernie put better than I have managed to: an agent can run nearly unattended wherever you can check its output cheaply, deterministically, and a thousand times a night, and wherever you cannot, you are the bottleneck and a smarter model changes nothing about that (Zernie, July 2026).

So the pattern is four parts, and skipping any one of them turns your night into a report:

1. The goal has a shape, not a mood. Chapter 8’s ladder: PRD, milestones, phases, tasks, tests, prompts, build. By the time an overnight job starts, “every task passes its test” has to mean a specific command with a specific exit code. Anything I cannot phrase as a command is a daytime job.

2. The check is deterministic and it runs without me. In commander-in-chief, the Godot project I have been building since July 2023, the simulation core in src/sim/ uses fixed 16.16 integer math and a SimRng xoshiro128** generator. A linter (tools/lint_sim.gd) fails the build if anyone sneaks in a float, an engine RNG call, a Time.* call, or scene-tree access. test_determinism.gd checks FNV-1a golden checksums across runs, producing bit-identical state on x86_64 and Apple Silicon. The formal name is deterministic simulation testing (DBOS, July 2025; Zernie, July 2026).

3. Something external holds the state. Long-running agents have to solve persistence, recovery, and verification with a state layer that lives outside the model’s context window (Addy Osmani, Elevate, April 2026).

4. Remediation is bounded, investigation is not. Autonomous investigation is reliable; autonomous remediation stays bounded and supervised (DevSecOps.ae, August 2026). My night jobs get free rein to read production, run tests, count artifacts, and write code. They do not get an unbounded DROP, an unreviewed schema migration, or a deploy to a customer-facing box without a gate.


One worked example

airank, the night of 13 August 2026. Two overnight runs.

The first was a council marathon: four implementations carried to completion before morning. Database optimization, toolbar readiness, webserver tuning, centralized logging. All four landed. Most were saved from their own authors by background machinery that had nothing to do with intelligence.

Save one is the 337,353 rows from the top of this chapter: a query, not a code review.

Save two: the nginx microcache config failed curl tests twice, once on a hyphenated cookie name, once because it stripped Set-Cookie unconditionally, which nginx -t never flags and which breaks every login on the site. Fixed, it took the site from 16.6 RPS at a p50 of 1.13 seconds to 1,873 RPS at a p50 of 10.3ms, a 113x speedup that would have shipped attached to a total login outage.

Same night, second run. Eleven unattended jobs across two workflows, an overnight survey and a todo-cycle. Three times the evidence claimed something was broken. Three times the evidence was lying.

Eight tests “failing on clean main.” Eleven agents were running parallel suites against one shared MinIO bucket and one shared database, and the fixtures were colliding. I set that up myself, and it is Snakes on a Plane (2006): you know how it ends from the title, and I booked the flight anyway. Re-run solo on a quiet fleet, 17 of 17 pass.

“Three merge failures.” zsh’s noclobber flag refused to overwrite a log file, so the merge commands never executed. merge=1 was a shell error wearing a git conflict’s clothes. The kill was counting: git log --oneline showed one merge where four should be. Re-run with >|, four clean merges.

Eleven jobs landed, three false alarms killed. Both nights I contributed nothing but the goal file and my continued unconsciousness.

Both nights went in the win column, which is the part I do not trust. Every overnight failure I have a record of got caught by a query, a curl, a test, or the morning log sweep, and I cannot show you the one that got past all four. That is not proof it never happened. A file drawer full of caught failures is exactly what a system with an uncaught one looks like, because the miss does not file a report. Read these two nights as the shape of the thing, not as a batting average.


The quiet failure

The loud failure is the overnight run that crashes at 1am and leaves you a stack trace. Annoying, cheap, obvious.

The quiet failure:

The agent finishes, declares success, and the proof is a paragraph it wrote about itself.

“Implemented centralized logging. All changes verified.” No exit code, no row count, no curl output, no git log --oneline you can read in nine seconds. This is the Ch. 20 seam again: when done is not a measurement, the most articulate artifact in the room wins by default.

Second: your verification shares infrastructure with your work. Eleven agents writing to one bucket cost me a morning of fake test failures. A non-deterministic check is a coin flip with a log file.

Third: nothing watches the watcher. The scheduler died at logrotate time and no alarm fired, because the alarm was downstream of the scheduler. That is a smoke detector mounted inside the fire, and a dead cron produces silence that looks like a quiet night.

During the migration two days later, the scheduler’s cron line got commented out with a marker meaning temporarily, and temporarily ran from 13 to 15 August 2026. Thirteen scheduled tasks stopped. Every dashboard stayed green the whole time, because a scheduler is not a service, it is a pulse, and nothing was measuring the pulse.

The fix shipped on 15 August and it is eleven lines at the bottom of routes/console.php: the schedule’s own last entry pings an Uptime Kuma push monitor every minute, and the monitor, airank-scheduler-alive, has a 180-second window, so three missed beats page a phone. It reads the URL through config() and not env(), because env() returns null under config:cache and I would have built a dead man’s switch that was itself dead. Eleven lines buy back the two days I did not know I had lost.


Do / don’t

Do

Don’t


Where this sits in the book

Ch. 8 built the ladder that makes a /goal block executable. Ch. 14 is the Ralph loop, and this chapter is that loop with the lights off and no one to ask. Ch. 15 is why the plan is not the work, the same argument moved eight hours later. Ch. 36 is the verification layer this chapter leans on entirely: no cheap deterministic check, no unattended night. Ch. 60 is where this scales past one machine and one person’s sleep schedule.


Sources and receipts

Thesis is Jeremy’s: argument, not citation.

Verified:

What I could not verify: