What an adversarial read of the whole thing found

Fixkamo-internal
Shipped
September 8, 2026 at 7:14 PM UTC
Author
Kamo
Commit
37b4555

Ten reviewers over the change, three skeptics per finding. These are the ones that survived, and most of them were in the wiring rather than in the parts that had been thought about hardest. **The computer's reply arrived as one jump.** A move against the AI publishes two frames — the position after yours, then the position after its reply — while the HTTP response carries the SECOND of them. Applying that response meant the board skipped straight to the end: your own move never animated, never sounded, and the intermediate frame was then discarded as stale by the version guard. A move's response is thrown away now; the frames are ordered and they are the authority. Errors are still the response's job. **A refused move left the piece on the wrong square, permanently.** The board moves optimistically, because a piece that waits for the network looks heavy — but a refusal publishes no frame at all, so nothing ever corrected it. The board now takes a rejection counter and puts every piece back. **Flipping the board swapped who you were.** The seat took its colour from the orientation and its identity from its position on screen, so a flipped board left the bottom seat labelled "You" while carrying the opponent's colour, captures and turn. Colour first now, and everything follows from whose colour it is. **Resizing the window threw away an in-flight promotion.** The three compositions were three different trees, so crossing a threshold moved ChessBoard under a different parent and React unmounted it — with the piece you had picked up and the promotion card you were choosing from. It is one CSS grid now whose template changes; the board keeps its element from 380 pixels to maximized. A tool window in this product may never lose state on a relayout. **A press held before dragging was inert.** Press, think, then drag is exactly what somebody deciding does, and the hold state was terminal: the piece stayed under the pointer and the release did nothing. Holding resolves the press to a selection; it does not withdraw the offer to drag. And: the winning king's square was never passed, so the victory pulse and the CHECKMATE announcement were both dead code and a screen reader was told a mated game was a check; the live check ring painted over positions being reviewed; the result band was the width of its column rather than the board's, and arrived before the mating piece had landed; the move list's healing refetch cancelled itself every time, so a dropped frame corrupted it for the rest of the game; locally appended rows guessed their own ply; picking a second position while reviewing threw away the notice that the opponent had moved; the promotion card dropped focus to the body when it closed; two delayed sound cues could fire after the window was closed; "game begins" played every time somebody reopened a fourteen-move-old board; and the turn was written twice on screen at once, which §37 asks for exactly once. Think time is capped at six hours. This is correspondence chess — the invitation says "take days if you like" — so the gap between moves is often somebody's evening, and "took 72h 0m" reads as a stopwatch left running rather than as how long anybody considered the position.

All changes

Like what you see shipping?

Every one of these updates lands in your workspace automatically. Start free and watch it grow week after week.

Start Free ForeverView Pricing