package.json has sat at 0.1.0 since the first commit, through three releases,
because nothing read it. That is fine right up until something does — an image
label, a health endpoint, a bug report quoting a version — at which point the
tree claims to be a version that shipped long ago.
A new `bump` job takes the tag that was just published, works out the next
patch from it, and commits that to main. After 1.2.0 the tree says 1.2.1: not
a version that exists, which is the point. A build from main is then legible
as "after 1.2.0" rather than as 1.2.0 itself.
It sits in publish.yml rather than a workflow of its own so that it can say
`needs: build`. A version that failed to publish has not been released, and
moving past it would say that it had. Prereleases are skipped for the same
reason -- 1.2.3-rc1 is a candidate for a version that has not shipped, so
there is nothing yet to move past.
The bump goes through `npm version` rather than editing the file. The version
is in the lockfile too, in two places, and a tree where those disagree is worse
than one that is merely out of date.
Three smaller things. The patch arithmetic forces base ten, because a patch
number written 08 is otherwise read as octal and kills the job. The commit
carries `[skip ci]`, or pushing it starts another build of the image that was
just published. And the committer is a name that is not a person at a reserved
address that can never become one, so nothing here names the instance it runs
on.
Pushing to main needs a token that may write to the repository. The Actions
task token can where the instance allows it; where it does not, setting a
VERSION_BUMP_TOKEN secret overrides it. A push that is refused fails the job
with both of those as the suggestion rather than a bare 403.
package.json goes to 1.2.1 here, which is where the job would have left it had
it existed when 1.2.0 went out.
Co-Authored-By: Claude Opus 5 <[email protected]>
Claude-Session: https://claude.ai/code/session_017nMQ2eDKnqALYhAibpTKTu