A bulk update hit “all articles”: count before you write, and break your tests to prove they work

日本語版

Development log of Torecadash / October 2026

In my iOS app Torecadash, a new job that fixes article status in bulk hit every article, including ones I never meant to target, the first time I ran it. 18 items from other sites were wrongly restored to visible. This is how I fixed the accident, and how I checked that the test I built afterward to close the same hole actually works, from my hand-over notes.

This is a development log of the app.

What the job was for

The app has a “price gate” that checks whether a listing’s price is reasonable (I wrote about it in another article). Among articles hidden by this gate only because of price, I added a job that restores those that were actually correct and had been hidden because of a product mix-up. The condition for restoring is “the correct product’s list price matches the listing price.”

The accident: it hit all articles

At first this job hit all articles without distinguishing the source. As a result, 18 articles from other sites (Amazon, Card Labo, Ministop and others) were restored to visible. They should have stayed hidden.

There were two fixes.

But there was something I could not get back for these 18. The job had overwritten the original list-price field with the listing price. The value stays as the listing price.

The cause was that I had not counted the target range before writing. My notes say so: “count the target range before a bulk write.”

Building tests to close the same hole

To make sure the problems found in that day’s inspection (wrong splitting of 9-pack sets, single cards slipping in, non-card products slipping in) never happen again, I built tests: 66 cases in catalog-guards.test.js, and all six test files together can be run in one procedure (run-all.sh).

I also added warnings to my daily operations notice: when the miss rate of matching falls below the criteria (Chusen Zukan 80%, Pokechu 75%, X roundup 75%), when nothing has run for 30 hours, and when single cards or non-card names appear in the product list. The judgments are pure functions with no side effects, so once things are fixed, the warning disappears by itself on the next run.

Breaking it to check that the tests work

You cannot tell whether a test works just by writing it. A test that always passes may protect nothing. So I took a copy of the production code and removed its rules one at a time to confirm the tests fail.

With this procedure, I tried 6 kinds of modification, and the tests failed for all 6 (all were detected).

I also wrote down an operating rule: if I touch functions/index.js, I always run all the tests before deploying.

What I learned

Count before a bulk write. Break the test to prove it.

This article is written from my hand-over notes (§272) (October 7, 2026). The counts are as written in the notes.

This is the English version of the original Japanese article.

More in English