Skip to main content
FomiVIP
Tech Sharing

We Added One Rollback Line to Our Gray Release Script

Our gray release script ran two years without incident — until August, when a styling bug appeared on older Android after ramping to 50%. The script could only advance, never retreat; manual Nginx edits cost 12 extra minutes. We added a rollback command that runs the same checks as advance.

August 21, 2026Gray ReleaseRollbackLessons Learned

Our gray release script was written separately from the Jenkins pipeline we set up in 2020. It ramps traffic by the last digit of employee IDs and had exactly one action — advance: 10%, 30%, 50%, 100%, always forward. It ran two years without incident, so no one ever thought about going backward.

August 21

Half an hour after ramping to 50%, support forwarded two screenshots: buttons squashed together on older Android phones. The cause was a flex pattern in the new version that older WebView versions didn't support — our test devices were all too new to catch it.

Simple fix: roll back. Except the script had no rollback.

The Manual 12 Minutes

The person on duty dug through docs to find the Nginx config location, edited the weights, reloaded, then re-checked the logs to confirm traffic was back on the old version. Twelve minutes in all — not long, but during those 12 minutes nobody could be sure everything had fully reverted, because the script normally refreshes the gray release flags in Redis as a side effect, and manually editing weights doesn't. Sure enough, a few scattered users were still on the new version, and we had to clear the flags separately.

The problem wasn't speed — it was that rolling back and advancing weren't the same operation, and things fell through the gap between them.

The Line We Added

We added a rollback command that also takes a ratio: drop straight to 0, or back to 10% and keep a small cohort under observation. The key is that it runs the same code path as advance: adjust Nginx weights, refresh the Redis gray release flags, write a release log line, and post a message to the group chat. All four, every time.

While we were at it, we made "current gray release ratio" a queryable command instead of something you guess from config files. Before, your best option was finding whoever last posted a screenshot in the group.

Two More Guards Added Alongside

  • After advancing to 100%, keep the old version running for 7 days. This used to live in documentation only; now the script enforces it.
  • Run the 5 curl health checks before every ramp step; if any fail, stay at the current ratio instead of pushing on. Previously they only ran at the 100% step.

Afterward

We rewrote the flex pattern and re-ran the ramp — 10%, 30%, 50% — this time with an older Android device added to the test fleet.

The script now has both advance and rollback, side by side on the first line of the README. When someone asked why we'd write code for an action we'd "probably never use," I showed them the chat log from those 12 minutes on August 21.

Consulting · Free initial chat

Need advice for your scenario?

Tell us your business context and current systems, and we'll give an actionable approach.

Contact us

Mon–Fri 9:00–18:00 · We respond on business days within one business day.

WeChat (Business Only)
WeChat (Business Only)二维码

Scan and add our WeChat for consulting

Or fill out the requirements form