Skip to content

feat(take-notes): warn on a stale install, and guard doc drift in CI - #12

Merged
davertor merged 1 commit into
mainfrom
davertor/ci-drift-guard
Sep 9, 2026
Merged

davertor merged 1 commit into
mainfrom
davertor/ci-drift-guard

Conversation

@davertor

@davertor davertor commented Sep 9, 2026

Copy link
Copy Markdown
Owner

What and why

Two silent failure modes, one guard each.

scripts/check-drift.py — the invariants that live in prose. CONTRIBUTING.md
claims SKILL.md holds the only copy of the note-writing standard, that the Step 1
catch-all must stay last, and that never-auto-invoke moves in two files together.
Nothing checked any of it: the --selftest asserts cover the scripts, not the
document. Every one of these breaks quietly — a routing row the catch-all above it
swallows, a guide the table names and nobody wrote, a second copy of the writing
standard free to drift from the first. Nothing fails until a note is already wrong.

Six checks, stdlib, ~100 lines, run in CI beside the manifest and version checks.
It is development tooling and deliberately lives in a new root scripts/, not in
skills/take-notes/scripts/, which ships to users.

The sixth is worth calling out now that releases go through commitizen: cz bump
rewrites the version in five files but is told not to touch CHANGELOG.md, so the
version can ship ahead of its entry by design. This fails the build when it does.

A stale install had no symptom. Only the Claude Code marketplace route
auto-updates; the clone and npx skills routes need the user to remember, and the
version appears nowhere they look — a copy three minor versions behind just
quietly lacks whatever the README shows. Building the gallery now says so, in the
footer and on stderr, in both languages.

It reads one ~700-byte file from raw.githubusercontent with a 2.5s timeout, and
every failure — offline, proxy, GitHub down, unexpected body — means the same
thing: say nothing. Versions compare as numbers, so 1.10.0 > 1.9.0 and a copy
ahead of main is never told to downgrade. TAKE_NOTES_NO_UPDATE_CHECK=1 skips
it. It goes in gallery.py rather than render.py because the gallery is rebuilt
on demand, so a slow request delays nothing anyone is waiting on.

Checks

  • for s in render notes gallery export transcript tags retag slides themes; do uv run skills/take-notes/scripts/$s.py --selftest; done passes
  • uv run scripts/check-drift.py passes — also verified against a clean export of origin/main
  • No new third-party dependency — urllib.request and json are stdlib
  • English throughout — code, comments, commit messages

Verified at 3250b82. The update warning was exercised end to end while this
branch still sat on 1.3.0, and printed:

gallery: take-notes 1.4.0 ya está disponible — tienes la 1.3.0. Actualiza: https://github.com/davertor/take-notes

With TAKE_NOTES_NO_UPDATE_CHECK=1 the footer carries only the notes directory,
and at 1.4.0 == 1.4.0 the notice is empty. The version-comparison and
notice-rendering logic is asserted in gallery.py --selftest, which touches no
network; the fetch itself is a thin wrapper whose every failure is already the
same as having nothing to say.

The drift guard was mutation-tested on a scratch copy: breaking each of the six
invariants in turn produces exactly one error each and exit 1.

If you touched…

  • anything user-facing — README.md § Gallery documents the check and the opt-out
  • a note template — untouched
  • SKILL.md — untouched
  • the version — untouched; this is not a release

Noted, not fixed here

CONTRIBUTING.md § "The four things that will bite you" now has six subsections,
and ### 6. A genre is a contract plus a template sits orphaned between § Set up
and § Verify rather than with its siblings. Both predate this branch. Left alone
to keep the diff to one concern.

Two silent failure modes, one guard each.

The scripts' --selftest asserts cover the scripts. The invariants that live in
prose had nothing enforcing them, and every one of them breaks quietly: a
routing row the catch-all above it swallows, a guide the table names and nobody
wrote, a second copy of the writing standard free to drift from the first, a
rule dropped in a rewrite. Nothing fails until a note is already wrong.
scripts/check-drift.py is six stdlib checks run in CI beside the manifest and
version ones, and lives in a new root scripts/ because it is development
tooling — skills/take-notes/scripts/ ships to users. The sixth matters more now
that cz bump rewrites the version in five files but is told not to touch
CHANGELOG.md: the version can ship ahead of its entry by design.

A stale install had no symptom either. Only the marketplace route auto-updates;
the clone and npx skills routes need the user to remember, and the version
appears nowhere they look. Building the gallery now says so, in the footer and
on stderr, in both languages. It reads one small file from raw.githubusercontent
with a 2.5s timeout, and every failure means the same thing — say nothing.
Versions compare as numbers, so a copy ahead of main is never told to downgrade.
TAKE_NOTES_NO_UPDATE_CHECK=1 skips it. It goes in gallery.py rather than
render.py because the gallery is rebuilt on demand, so a slow request delays
nothing anyone is waiting on.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@davertor
davertor force-pushed the davertor/ci-drift-guard branch from 3250b82 to f0edf1a Compare September 9, 2026 15:04
@davertor
davertor merged commit 93987e3 into main Sep 9, 2026
1 check passed
@davertor
davertor deleted the davertor/ci-drift-guard branch September 9, 2026 15:04
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant