Repository navigation
🐛 FIX: Build both distributions in CI and publish those exact files - #1221
Merged
Merged
Conversation
Add a `build` job to `tests.yml` that builds myst-parser, then rewrites the project with `docutils_setup.py` and builds myst-docutils, each with `python -m build` into its own directory. It runs `twine check --strict`, checks each directory holds one wheel and one sdist of the expected project, and on a tag checks the built version matches the tag. Each directory is uploaded as its own artifact. The job is part of the `check` aggregator, so a broken release build fails a pull request rather than a tag push.
…flit Both publish jobs ran `pip install flit~=3.4` then `flit build`. That now resolves flit 3.12 with flit_core 4.2, and `flit build` fails with `TypeError: SdistBuilder.build() got an unexpected keyword argument 'gen_setup_py'`, so a tag push could not publish either distribution. `publish` and `publish-docutils` now download the `dist-parser` and `dist-docutils` artifacts from the `build` job and upload them with trusted publishing, so what is published is what CI built and checked. Neither job checks out the repository or installs anything. `publish-docutils` still runs only after `publish` succeeds.
…riod The publish jobs download the artifacts the build job uploaded. A 7-day retention made a publish fail if it ran more than 7 days after the tag: an approval on the `pypi` environment that came late, or a re-run of a failed publish job. Dropping `retention-days` uses the repository default instead.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What and why
The release build is broken for both distributions, so the next tag push cannot publish anything.
Both publish jobs in
tests.ymlrunpip install flit~=3.4and thenflit build.That specifier now resolves flit 3.12.0, which requires
flit_core>=3.12with no cap, so it pulls in flit_core 4.2.0, andflit buildcrashes:This PR changes
.github/workflows/tests.yml(the file name is unchanged, because both PyPI trusted publishers name it):buildjob runs on every push and pull request.It builds myst-parser with
python -m build --outdir dist-parser.It then rewrites the project with the existing
.github/workflows/docutils_setup.py, unchanged, and builds myst-docutils withpython -m build --outdir dist-docutils.python -m builduses the[build-system]pin inpyproject.toml(flit_core >=3.4,<4), so the release build cannot drift away from it again.twine check --stricton all four files.dist-parseranddist-docutils.They are kept for the repository's default retention period, not a short one,
so a publish job that runs late (after a slow environment approval, or as a re-run) still finds them.
persist-credentials: false.buildis added to thecheckaggregator, so a broken release build fails a PR instead of a tag push.publishandpublish-docutilsno longer check out or build anything.Each one downloads its own artifact and uploads it with
pypa/gh-action-pypi-publishfrom its ownpackages-dir, using trusted publishing (environmentpypi,id-token: write, both unchanged).So what is published is exactly what CI built and checked.
publish-docutilsstill runs only afterpublishsucceeds.How it was tested
The red run reproduces the bug on
master(723cffc):For the green runs, the new job's steps were run locally with Python 3.13, build 1.6.1, twine 7.0.0 and tomlkit 0.15.2, at both
v5.1.0and this branch:python -m build --outdir dist-parser, thendocutils_setup.py, thenpython -m build --outdir dist-docutils: rc=0 at both refs.twine check --stricton all four files: PASSED.TAG=v5.1.0: rc=0;TAG=v5.2.0: rc=1, withtag v5.2.0 != built version(s) ['5.1.0']for each directory;docutils_setup.pystep skipped: rc=1, withdist-docutils: expected myst_docutils, got ['myst_parser'].These builds were compared with the files on PyPI for 5.1.0, built from the
v5.1.0tag with the new job:METADATAPKG-INFOOn this branch the only file-list change from that comparison is the new
myst_parser/slugs.pymodule, in both wheels and both sdists.The contents of other modules differ too, because
masterhas moved on since 5.1.0.Linting:
actionlint .github/workflows/tests.ymlreports no new findings. The one finding left is a SC2102 info at line 93, which is already onmaster, in the unchangedcheck-myst-docutilsinstall step.pre-commit run --all-files: all hooks pass.Notes for the reviewer
The sdists get smaller. The flit CLI built sdists in VCS mode, so they included every git-tracked file not excluded.
python -m buildgoes through the flit_core backend, which ships only the package pluspyproject.toml,README.md,LICENSEandPKG-INFO.These files drop out of both sdists:
.github/.gitignore.pre-commit-config.yaml.readthedocs.ymlAGENTS.mdCHANGELOG.mdcodecov.ymlexample-include.mdtox.initests/anddocs/were already excluded, by[tool.flit.sdist] excludeinpyproject.toml. None of these files is needed to build or install, and the wheels are unchanged.If
CHANGELOG.mdortox.inishould stay in the sdist, a[tool.flit.sdist] includelist inpyproject.tomladds them back. I left that out because it is a packaging-policy choice.The same goes for shipping
tests/in the sdist, which would also mean dropping it from the existingexcludelist.What myst-docutils declares is unchanged.
docutils_setup.pyis untouched, so myst-docutils still declares no runtime docutils requirement: docutils and sphinx stay in its[sphinx]extra, as in 5.1.0. Whether to change that is a separate decision.The tag path cannot be fully tested before a tag. The download and upload steps follow the PyPA trusted-publishing guide's pattern. Trusted publishers are registered for both projects, against workflow
tests.ymland environmentpypi.Kept out of scope:
<5(⬆️ Update flit-core requirement from <4,>=3.4 to >=3.4,<5 #1185);permissions: contents: read;