| name | dev-bump-zudo-deps |
| description | Bump every `@takazudo/*` registry dependency in the current project to its newest version, resolving each by the channel it currently tracks. Use when: (1) User says '/dev-bump-zudo-deps', 'bump zudo deps', 'bump the @takazudo packages', 'update zfb', 'update zudo-doc', or 'update the takazudo toolchain to latest', (2) A new `@takazudo/*` prerelease or release has shipped and this project should adopt it, (3) Routine first-party dependency-update rounds. Resolution rule: a dep currently on the `next` prerelease line (`0.1.0-next.N`) → newest `next` release; a dep on the literal `latest` tag → `dist-tags.latest`; a plain stable semver → newest stable. Skips `workspace:`/`file:`/`link:` specs and leaves operator style (exact / `^` / `~`) and prerelease channel intact. A bundled script does the discovery + semver resolution; this skill drives install + verify + report. |
| user-invocable | true |
| argument-hint | [package-name... | all (default)] [--dry-run] |
dev-bump-zudo-deps — Bump all @takazudo/* deps to latest
Discover every @takazudo/* dependency that resolves to the npm registry across all
package.json files in the project, bump each to the newest version on the channel it already
tracks, install, and verify the project still builds.
The fragile part — finding the deps, classifying each spec's channel, and computing the target
with correct prerelease semver — is done deterministically by scripts/resolve-bumps.mjs, so
it never depends on the model recomputing version math by hand.
Resolution rule (what "bump" means per dep)
The dep's current spec decides the channel, and only deps pinned to a concrete version get
rewritten — specs that float are reported but left alone, because rewriting them would silently
turn a deliberate choice into a hard pin:
| Current spec | Resolved to | Action |
|---|
0.1.0-next.58 (a -next.* prerelease pin) | newest release on the next line | ✏ bump |
^1.2.0-beta.3 (any other prerelease line) | newest release on that line | ✏ bump |
1.2.3 / ^1.2.3 / ~1.2.3 (stable semver) | newest stable (dist-tags.latest) | ✏ bump |
next / latest / beta (a dist-tag string) | reported (what the tag points at now) | tag |
* / x / empty (floating) | — | skip |
workspace: / file: / link: / git / url | — | skip |
Write-back preserves what was there: an exact pin stays exact, ^/~ operators are kept, and a
prerelease-pinned dep stays on its own line. A dep declared via a dist-tag string (next,
latest, …) is intentionally not rewritten — it already floats to that tag on install, so the
script just reports what the tag currently resolves to (with a stale-tag/graduation note) and
leaves the pinning decision to you. Non-registry specs (workspace:*, file:, link:,
portal:, catalog:, npm: aliases, git/url) are left untouched — bumping a workspace:* dep
would break the monorepo.
The one gotcha worth knowing: the next dist-tag can be stale
For prerelease lines, the npm next dist-tag sometimes points at an older version than what's
actually published (or than latest). "Newest next" means the highest published -next.*
version, not whatever the next tag literally says. The script already resolves this by scanning
the full version list and flags two cases in its report:
- stale tag —
next dist-tag < newest published next version (script uses the newest).
- graduation —
latest is higher than the newest next (the line may have moved to stable);
this is a human call, so surface it instead of silently switching channels.
Step 1 — Resolve the plan (dry-run)
From the project root (running without --write is a dry-run):
node "$HOME/.claude/skills/dev-bump-zudo-deps/scripts/resolve-bumps.mjs"
It prints one row per @takazudo/* dep — bump / up-to-date / tag / skip / error — with
current → target and any stale-tag/graduation notes, plus a Scanned N package.json line. Pass
exact package names to limit scope (… resolve-bumps.mjs @takazudo/zfb @takazudo/zfb-runtime);
--json adds a machine-readable plan.
- If every dep is
up-to-date (or only tag/skip rows remain), report "already on latest" and stop.
- An
error row can mean the package is genuinely unpublished or a registry/auth/offline
issue — if every lookup errored the script says so; confirm npm view @takazudo/<pkg> works from
this shell before concluding a package is missing.
tag/skip rows are deliberately not rewritten — surface them so the user can pin or update
those manually if they want.
- The scan does not follow symlinks, so a symlinked nested workspace won't be found; sanity-check
the
Scanned N count against the project.
Read the table before writing and act on any flagged note — a graduation warning means asking
the user whether to follow the line to stable rather than silently staying on the prerelease channel.
Step 2 — Apply the bumps
node "$HOME/.claude/skills/dev-bump-zudo-deps/scripts/resolve-bumps.mjs" --write
--write does a minimal in-place string edit per dep (it preserves each file's formatting). The
same package appearing in several package.json files is moved to the same target everywhere;
the script warns (⚠ … multiple targets) if anything would diverge.
Step 3 — Check peer coupling
First-party families often pin each other. Before installing, confirm a bumped package's peers are
satisfied by the other targets — bump coupled packages together so the install resolves:
npm view <bumped-pkg>@<target> peerDependencies
If a peer requires a version the plan didn't reach (common with exact-pinned prerelease lines
where ^x-next.40 does NOT satisfy next.41), re-run Step 1/2 including that peer so the whole
family lands on a mutually compatible set.
Step 4 — Install
Use the project's package manager (check packageManager in package.json / the lockfile —
pnpm-lock.yaml → pnpm, package-lock.json → npm, yarn.lock → yarn). Prefer a project-provided
safe-install script if one exists (e.g. pnpm install:safe).
pnpm install
Independent nested workspaces install separately. After --write, the script prints the
distinct directories it edited — install in each one that has its own lockfile (a nested workspace
with an independent lockfile is not covered by the root install), and commit every changed
lockfile:
pnpm install
cd doc && pnpm install
Step 5 — Verify
Run the project's checks and build to prove the bump didn't break anything. Use whatever the
project defines:
pnpm typecheck && pnpm build
For a monorepo, build each workspace the bump touched, not just the root. Read the output — a
green typecheck/build is the bar. If a build breaks, the new version likely changed an API or a
peer; report the failure with the offending package rather than forcing the bump through.
Step 6 — Report
Summarize for the user:
- Bumped:
pkg old → new (note next-channel vs stable)
- Up-to-date / skipped: counts (and which were skipped as
workspace:/non-registry)
- Flags: any stale-tag or graduation warnings from Step 1, and the decision taken
- Verify result: typecheck/build status per workspace
- Lockfiles changed: which ones (so they get committed)
Leave committing to the user / /commits unless they asked otherwise.
Step 7 — File upstream reports for anything the bump surfaced
The bump is the moment first-party problems show up — a stale/misleading dist-tag, a removed or
broken export, a regression in the new version, or a consumer-side fix that should have shipped as
a package change. File these on the source repo so they get fixed at the root instead of
worked around forever, via the /dev-upstream-report skill:
Skill tool: skill="dev-upstream-report" args="<concise description + evidence>"
Privacy guardrail — this skill runs in arbitrary repos, some of them private client work. When
writing an upstream report (or any external artifact), describe the problem in terms of the
public package (name + version + a minimal repro), and:
- Name the source repo only when it is one of the first-party accounts —
Takazudo/* or
zudolab/* (e.g. Takazudo/zudo-front-builder, zudolab/zudo-doc). If the upstream is not one
of those, do not assume a repo.
- Never include the consuming project's name, directory paths, internal URLs, or any
client/company identifiers. A private client project must not be named or hinted at in a public
issue. Strip paths down to the package-relevant minimum.