Three ways "the spec said X" was wrong
I keep a spike issue around to catch small rot before it piles up - dead symlinks, stale docs, a missing package.json field. This week I finally cleared the backlog it had built up. Three of the seven items turned out to be the same shape of mistake: something written down (a symlink target, an in-flight fix, a CSS token) stopped matching reality, and nobody noticed until I went looking.
The symlink pointing nowhere. Three files under .cursor/rules/ were tracked symlinks into ~/Projects/cursor-rules/. That directory doesn’t exist. Not “moved” - ~/Projects/ itself isn’t there. Whatever synced those rules in was a one-time action, never a real mechanism, and the symlinks just kept pointing at nothing since. Removing them wasn’t a judgment call once I checked; there was nothing to restore.
The audit fix that was already in flight. The spike flagged 9 build-toolchain vulnerabilities for npm audit fix. Before running it, I checked open PRs - three Dependabot branches already cover the same dependencies, queued behind an earlier CI-gate issue. Running audit fix by hand would have meant fighting my own automation for no reason. Sometimes the fix is “confirm it’s already scheduled” rather than “do it.”
The CSS class that never existed. My own project docs described a global.css file and a component called MainContent. Neither exists in the current codebase - the page composition is Hero + three section components + a widget, nothing named MainContent anywhere. The doc had drifted from a much earlier version of the site and nobody had diffed it against reality since. Rewriting it meant reading the actual component tree instead of trusting what was already written about it.
None of these needed cleverness. Each one needed the same move: don’t trust the written description, check the thing it’s describing. A dead symlink target, an issue tracker, and a component tree - three different sources of truth, same lesson each time.
Small side fix in the same batch worth a one-line mention: a status badge was 9.6px, under the size most accessibility guidance treats as a floor for body-adjacent text - bumped to 12px. And a “launch game” button that removed itself from the DOM on click was dropping keyboard focus to <body> - moved it to the iframe that replaces the button instead. Neither is exciting, but both are the kind of thing that’s invisible unless you’re using a keyboard or a screen reader, which is exactly why they don’t get caught by build or type checks.
Related reading
The bug behind the bug
A broken GitHub widget traced to a paused upstream demo - and, found along the way, a hash-pinned CSP silently invalidated by a one-line accessibility fix.
Rebasing an affiliate PR into a build dependabot quietly broke
A grouped 12-update dependabot bump hid a Tailwind major that broke loudly and an Astro major that broke silently, triggered by one unmerged branch.
The landing page copy that competed in the wrong category
The marketing page pitched new-release tracking - an incumbent's home turf - while the view model's doc comment had the real pitch all along.
You might also find useful
Proton VPN
Commercial VPN with NetShield filtering and a kill switch.
As a Proton Partner, I earn from qualifying purchases of Proton's privacy and security services (Pass, Mail, VPN, Drive).
Learn moreAiralo eSIM
Local data eSIM for travel - no physical SIM swap needed.
This is my Airalo referral link. You get a discount on your first eSIM, and I earn Airalo credit toward mine.
Learn moreNordPass
Password manager from the team behind NordVPN, with a free tier.
As a NordPass affiliate, I earn from qualifying purchases.
Learn more