Migrate · 3 of 3
Keep it up to date
The loop
# 1. what has moved on since you installed it (reads only)
npx hoverlab outdated
# 2. what actually changed in one of them
npx hoverlab diff pricing-tiers
# 3. take it — but look first
npx hoverlab update pricing-tiers --dry-run
npx hoverlab update pricing-tiersAll three read hoverlab.lock.json, which npx hoverlab add wrote when you installed. No lockfile, nothing to compare, and the commands say so rather than guess.
outdated: what changed
! 1 of 3 have changed in the catalog:
pricing-tiers (block)
3fa9c01b7d2e -> 8b17d4e02c9a · updated 2026-08-12
See what changed: hoverlab diff pricing-tiers
Nothing has been written. Your copies are untouched.outdated never writes and has no fix flag, deliberately. It compares one fingerprint per artifact, and a fingerprint difference says the catalog’s file changed — not that yours did not. Overwriting on that evidence would be the most destructive thing this CLI could do, so it does not.
A tracked id that is no longer in the catalog is listed separately as not found; it may have been renamed or retired. For CI, add --json:
npx hoverlab outdated --json
# { "tracked": 3, "outdated": [ { "id", "level", "from", "to", "updated" } ], "unknown": [] }outdated exits 0 whether or not anything is stale, so a CI step has to read the JSON to fail on it. For example, with jq (not part of Hoverlab): npx hoverlab outdated --json | jq -e '.outdated | length == 0'diff: what the change is
diff prints the changed lines between your copy and the catalog’s current one, for each file that artifact installed. It ignores line-ending differences, so a file that a Windows checkout turned to CRLF is not reported as changed from top to bottom. It writes nothing. There is no --json for it; use outdated --json for machines.
update: taking it safely
update is not the fix flag outdated refuses to have. It asks a different question, one the lockfile can answer: is your file byte-for-byte what the CLI wrote? If so, replacing it destroys nothing. If not, it leaves the file alone.
| Situation | What update does |
|---|---|
| File matches its recorded hash | Replaces it with the catalog’s copy and re-records the revision and hashes. |
| You edited it — or a formatter or a line-ending conversion did | Refuses that artifact, says has local changes, and points at diff. Other artifacts are unaffected. |
| It was installed before hashes were recorded | Refuses: it cannot tell whether you edited it. |
| The file is gone from disk | Counts as blocked, like an edited one. Only --force writes it back. |
| Any one file of an artifact is blocked | Writes none of that artifact’s files. Half an update compiles, runs and is wrong in a way nobody thinks to look for. |
--force | Overwrites the blocked files too. For when you know your edits are disposable. |
--dry-run | Prints the same report and writes nothing. |
With no ids, update takes everything outdated lists. Name ids to take only those.
! pricing-tiers not updated:
components/pricing-tiers.tsx has local changes
See what would change: hoverlab diff pricing-tiers
Or overwrite anyway: hoverlab update pricing-tiers --forceThe merge is yours. A three-way merge on a component you have restyled is a judgement call about which of two intentions wins, and neither the CLI nor a hash can make it.
Things the lockfile does not know about
Only add records. A template from init, anything from npx shadcn add, and anything copied by hand are invisible to outdated. To see the current source next to yours, without the lockfile:
npx hoverlab show pricing-tiersshow prints the catalog’s code and writes nothing; compare it in your editor. To bring an unedited copy under tracking, npx hoverlab add pricing-tiers --force rewrites it with the catalog’s current copy and records that revision. On a file you have not edited that is an update; on one you have, it is a real overwrite, so commit first.
The revision ledger
Behind outdated is one public endpoint, with no key:
curl 'https://hoverlab5.netlify.app/api/v1/revisions?level=block&ids=pricing-tiers'It returns version, generatedAt, count and an artifacts map of { level, revision, updated? } per id. updated is present where the catalog can state the date precisely. The CLI asks for the whole ledger, not for your ids, so the request does not reveal what you installed. The mechanism, in the order you meet it:
- Every artifact carries a revision. A content fingerprint per effect, block, page and template, derived from the source rather than from a version somebody remembers to bump.
- It is a public endpoint, with no key. /api/v1/revisions returns the whole ledger. Your lockfile never has to tell us which forty things you installed.
- The CLI reads your copy against it.
npx hoverlab outdatedlists what has moved since you installed it, with the date it changed;hoverlab diff <id>shows the lines. - Applying it is your call, always. Nothing reaches into your repo and nothing phones home. The file is yours — this only tells you it is not the newest one.
The revision is derived from the file bodies alone. Retitling a block or adding a tag does not move it, so a stale-copy notice means the source changed, not the marketing.
We have not audited every vendor above for this, so the table has no column for it. What we can say is what we do.
What the twelve-month window covers
The window belongs to the commercial licence, and its wording is the licence’s, quoted rather than paraphrased:
- Perpetual and irrevocable for anything already shipped. A refund or a lapsed subscription never reaches back into work you have delivered.
- Twelve months of catalog updates from the date of purchase. Everything published in that window is yours permanently, whether or not you renew.
- Subscriptions include updates for as long as they are live — there is no separate window.
- When it ends. The licence certificate on your account shows the date beside the issue date.
- Renewing. A renewal buys another twelve months, added to whatever is left, so renewing early costs you nothing. It appears on the certificate as the window runs out.
- The commands are not tied to it.
outdated,diffandupdatedo not ask for a key or check a date; they work the same on every machine.
Full terms are on the licence page, and how the ledger compares with other catalogs, with dates on every row, is on the comparison page.
What leaves your machine
outdatedfetches the whole ledger and compares locally.diffandupdatefetch the artifacts you name, so the server sees those ids.addreports the ids it installed, for the catalog’s popularity ranking, and nothing else about your project.HOVERLAB_NO_TELEMETRY=1switches that off.
None of them writes to your repo except add and update, and update only where it can prove the file is untouched.
Something wrong or missing here? Browse the catalog — every page in it links back to the source it documents.