Skip to content

ci: build the Docker image after PyPI publish finishes, not alongside it - #64

Merged
cnygaard merged 1 commit into
mainfrom
fix/docker-after-publish
Aug 17, 2026
Merged

ci: build the Docker image after PyPI publish finishes, not alongside it#64
cnygaard merged 1 commit into
mainfrom
fix/docker-after-publish

Conversation

@cnygaard

Copy link
Copy Markdown
Owner

docker.yml triggered on push: tags — and so does publish.yml. A tag fires both at the same instant, and the image installs glq==<version> from PyPI, so the build raced the upload and lost:

ERROR: Could not find a version that satisfies the requirement glq==0.8.7
       (from versions: ..., 0.8.5, 0.8.6)

three minutes into a build that started in the same second as the wheel matrix.

This has been broken for two releases

tag Docker build image
v0.8.5 success (19m50s) published
v0.8.6 failure (4m01s) none
v0.8.7 failure (3m03s) none

It went unnoticed because nothing looks at this workflow after tagging, and the release itself succeeds — PyPI gets its wheels, the GitHub release gets created, only the container is silently missing.

The file's own comment claimed tags-only was the fix:

Tags-only (NOT every main push) … a main-push build would always fail with "No matching distribution found". Restricting to tag pushes keeps this workflow reliably green

True for main pushes, irrelevant for the tag. The comment is corrected along with the trigger, since leaving the wrong rationale in place is what would send the next person back to the same design.

Change

  • workflow_run on "Publish to PyPI" completing, gated on conclusion == 'success' and a v* head_branch. A failed or partial publish must not produce an image claiming that version.
  • Checkout head_branchworkflow_run otherwise defaults to the default branch, which would build the Dockerfile and install.sh from main rather than from the tag.
  • Wait for the simple index before building. That is what pip resolves against, it is CDN-served, and it lags even after publish reports success — measured on 0.8.6, a container started 2m16s after publish installed 0.8.5 and produced a green log proving the previous release's behaviour. 10-minute cap; the failure message points at the upload rather than at this build.

Not fixed here

0.8.6 and 0.8.7 still have no image on ghcr. Both can be built with workflow_dispatch now that the versions are on PyPI — worth doing, since the README points at ghcr.io/cnygaard/glq-env:latest in five places.

The image installs `glq==<version>` from PyPI, so it cannot be built until that version
exists. docker.yml triggered on the tag push — and so does publish.yml, in the same
instant, so the build raced the upload and lost:

    ERROR: Could not find a version that satisfies the requirement glq==0.8.7
           (from versions: ..., 0.8.5, 0.8.6)

three minutes into a build that started in the same second as the wheel matrix. **v0.8.6
and v0.8.7 both failed this way and neither release produced an image**; it went unnoticed
for two releases because the failure is in a workflow nobody watches after tagging.

The file's own comment argued that tags-only kept it green ("a main-push build would always
fail ... restricting to tag pushes keeps this workflow reliably green"). That reasoning
holds for main pushes and does nothing for the tag itself, which fires both workflows at
once. Comment corrected along with the trigger, since the wrong rationale is what would
send the next person back to the same design.

Now: `workflow_run` on Publish-to-PyPI completing, gated on conclusion == success and a
`v*` head_branch, checking out that tag rather than the default branch.

Then it waits for the **simple index** — what pip actually resolves against, CDN-served and
lagging even after publish reports success. Measured on 0.8.6: a container started 2m16s
after publish installed 0.8.5 and produced a green log proving the previous release's
behaviour. Ten-minute cap, and the failure message points at the upload rather than at this
build.

Not fixed here: 0.8.6 and 0.8.7 have no image on ghcr. Both can be built with
workflow_dispatch now that the versions are on PyPI.
@cnygaard
cnygaard enabled auto-merge (squash) August 17, 2026 22:09
@cnygaard
cnygaard merged commit 1a2d56a into main Aug 17, 2026
3 checks passed
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