Skip to content

Write the GitHub release from the tag that publishes it - #55

Merged
oblomov-dev merged 1 commit into
mainfrom
claude/repo-analysis-structure-0wpt5q
Aug 18, 2026
Merged

Write the GitHub release from the tag that publishes it#55
oblomov-dev merged 1 commit into
mainfrom
claude/repo-analysis-structure-0wpt5q

Conversation

@oblomov-dev

Copy link
Copy Markdown
Member

Description

This workflow published five versions to npm and made a GitHub release for none of them. It surfaced when the API was asked for the latest one:

  • releases/latest answered 404
  • No Latest badge on the repository
  • The releases page was 37 rolling render-gate-bundle prereleases, with no version among them

For a repository whose job is to be installed by strangers, that is the first page they see. The five releases (v0.1.0v0.2.2) were written by hand today. This is so there is no sixth.

Where it goes, and why there

Into the job that already has contents: write and already runs after a successful publish — so:

  • publish keeps contents: read, which the comment there asks for explicitly
  • no release is written for a publish that did not happen

The job is renamed major-tagafter-publish, because it does two things now and the old name described only one. Not a required status check anywhere (the workflow is tag- and dispatch-triggered), so the rename costs nothing.

Three decisions worth the words

A missing CHANGELOG section warns, it does not fail The packages are on npm by the time this runs. Missing notes are visible on the page and editable in a minute, and the release is still created — pointing at the file. A red run for something cosmetic is how people learn to ignore red release runs. The stale-alias step next to it is different: silent, serves the wrong code, and rightly fails.
make_latest is computed, not hard-coded A patch backported to an older line (v0.1.3 after v0.2.0) is a release but not the latest one. Hard-coding true would point every reader at older code.
A re-run leaves an existing release alone Same doctrine as the publish step: find the work done, move on. Rewriting would destroy notes edited by hand on the page — the likeliest reason to re-run at all.

!cancelled() on the new step, so the order between it and the alias move costs nothing in either direction: a failure here cannot skip the alias move, and a failed alias move cannot skip this.

How to test

The script was run against this repository's real data with a fake github object, since a workflow step cannot be exercised any other way before merge:

Scenario Result
newest tag v0.2.2 make_latest=true, 74 lines of notes — identical to what the hand-written release got
backport v0.1.3 make_latest=false ✅ does not hijack Latest
CHANGELOG section missing warning + pointer body, release still created
non-version tag skipped, nothing written
re-run (HTTP 422) absorbed, logged, release untouched
server error (HTTP 500) propagates — not swallowed
## 0.2.1 vs ## 0.2.10 correctly distinguished

Also verified: release.yml parses as YAML with both jobs; the embedded script is syntactically valid in the async-wrapper form github-script executes it in; npm test still green.

The first real proof is the next release tag — and if the step misbehaves, it cannot damage the publish that precedes it.

Checklist

  • npm test passes
  • Workflow YAML and embedded script validated
  • Logic tested against real repository data, failure paths included
  • publish still contents: read
  • RELEASING.md follows the rename and documents where the notes come from

Generated by Claude Code

This workflow published five versions to npm and made no GitHub release for
any of them. Nobody noticed until somebody asked the API for the latest one:
`releases/latest` answered 404, the repository showed no Latest badge, and the
releases page was 37 rolling `render-gate-bundle` prereleases with no version
among them. For a repository whose whole job is to be installed by strangers,
that is the first page they see.

The five were written by hand today. This is so there is no sixth.

It goes in the job that already has `contents: write` and already runs after a
successful publish - so `publish` keeps `contents: read`, which the comment
there asks for explicitly, and no release is written for a publish that did not
happen. The job is renamed `after-publish`, because it does two things now and
`major-tag` named only one of them.

Three decisions worth the words:

- **A missing CHANGELOG section warns, it does not fail.** The packages are on
  npm by the time this runs. Notes that are missing are visible on the page and
  editable in a minute; the release is still created, pointing at the file. A
  red run for something cosmetic is how people learn to ignore red release
  runs - unlike the stale alias next to it, which is silent and serves the
  wrong code, and rightly fails.
- **`make_latest` is computed, not hard-coded.** A patch backported to an older
  line (v0.1.3 after v0.2.0) is a release but not the latest one, and saying
  otherwise would point every reader at older code.
- **A re-run leaves an existing release alone.** Same doctrine as the publish
  step: find the work done and move on. Rewriting it would destroy notes edited
  by hand on the page, which is the likeliest reason to re-run at all.

`!cancelled()` on the new step so the order between it and the alias move costs
nothing in either direction.

Tested by running the script against this repository's real data with a fake
`github`: the newest tag gets make_latest=true and 74 lines of notes, a v0.1.3
backport gets make_latest=false, a missing section warns and still creates, a
non-version tag does nothing, a 422 is absorbed, a 500 propagates, and the
heading match distinguishes `## 0.2.1` from `## 0.2.10`.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01PLDFPfAK1MGq6qHeC6KKWH
Copilot AI lite review requested due to automatic review settings August 18, 2026 14:03

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot was unable to review this pull request because the user who requested the review has reached their quota limit.

@oblomov-dev
oblomov-dev merged commit 03df3bb into main Aug 18, 2026
5 checks passed
@oblomov-dev
oblomov-dev deleted the claude/repo-analysis-structure-0wpt5q branch August 18, 2026 14:14
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.

3 participants