chore: configure release-please for 6.0.0-beta line (closes #802)#804
Conversation
Enable prerelease versioning so release-please bumps within the beta line (6.0.0-beta.1 → 6.0.0-beta.2 → …) rather than jumping to a stable 6.0.0 on every breaking-change commit. The next release-please run produces v6.0.0-beta.1; subsequent feature work for the AdCP 3.1 SDK surface (#741 canonical-formats, #347 UpstreamRecorder, #711 permissive resolver, #758 revoked_publisher_domains inline) ships as additional beta increments until GA. Refs: #802 Release-As: 6.0.0-beta.1
There was a problem hiding this comment.
Held on the conversion question: whether release-please's extra-files type: "json" writer applies PEP 440 normalization to the version string it lands in pyproject.toml. The config is the right shape and the test plan's inspection gate is the right gate — but if there's a concrete one-line config change that removes the risk, better to do it now than to discover it at release-PR time.
Things I checked
release-please-config.json:10-11— JSON well-formed.prereleaseandprerelease-typeare valid release-please keys forrelease-type: "python". Two-line additive change, nothing else touched.- Test plan honesty: the unchecked items in the PR body are post-merge verification steps that cannot be checked before merging the config. Fair — not a test-plan-honesty violation.
Release-As: 6.0.0-beta.1footer ona083f820is single-shot. Subsequent beta increments rely onprerelease+prerelease-type+ conventional-commit signals.- PyPI:
pip install adcp(no--pre) continues resolving to 5.7.0 once a6.0.0b1ships. Pre-release exclusion is the PEP 440 default. Safe. - No public-API surface, no schema, no code paths.
Open question — what would flip this to approve
code-reviewer and dx-expert disagree on whether the extra-files block at release-please-config.json:12-18 actually applies PEP 440 normalization:
code-reviewer: release-please dispatches the version write through the python strategy, so6.0.0-beta.1→6.0.0b1lands inpyproject.toml.project.version.dx-expert: the genericJsonupdater is a string writer — the python strategy's PEP 440 conversion is applied by the dedicatedpyproject.toml/setup.pyupdaters, not by the generic json+jsonpath path. Risk: literalversion = "6.0.0-beta.1"lands in pyproject, which setuptools accepts with a warning but uv / poetry / pip-tools reject.
Resolve before the release PR merges. Two ways to flip this to approve:
- Preferred — proactive config fix. Replace the
extra-filesjson+jsonpath block with the native pyproject updater:release-please ships this updater specifically to handle PEP 440 conversion. Removes the question entirely."extra-files": [{ "type": "pyproject", "path": "pyproject.toml" }]
- Or — keep this config, but verify in the release PR diff that
pyproject.tomlshowsversion = "6.0.0b1"(PEP 440), notversion = "6.0.0-beta.1"(SemVer). The PR's own test plan already promises this check.
Either path is fine. Option 1 is one line; option 2 is the gate the PR body already commits to.
Minor nits (non-blocking)
- Inert pre-major keys.
release-please-config.json:7-8—bump-minor-pre-major: trueandbump-patch-for-minor-pre-major: falseonly fire while the current version is0.x. At 5.7.0 they're dead config. Drop in a follow-up cleanup. - No auto-graduation off the beta line. Once on
6.0.0-beta.N, there is no automatic exit — going GA will require either removingprerelease/prerelease-typefrom this config or anotherRelease-As: 6.0.0footer. Worth a note in CONTRIBUTING or the release runbook so future maintainers know the exit ramp.
LGTM after either the config switches to type: "pyproject" or the release PR is verified to write 6.0.0b1 (not 6.0.0-beta.1) to pyproject.toml.
There was a problem hiding this comment.
Block on a release-PR failure mode that's already in the test plan as a manual gate. The extra-files JSON updater at release-please-config.json:12-18 writes the raw SemVer string into pyproject.toml's $.project.version — for stable versions that's a no-op because SemVer and PEP 440 agree, but for 6.0.0-beta.1 it produces an invalid PEP 440 version and the wheel becomes uninstallable. Fix in this PR, not in the release PR.
Things I checked
- The two added lines (
prerelease: true,prerelease-type: "beta") are valid release-please config for the Python release-type. (release-please-config.json:10-11) pyproject.toml's current5.7.0flows throughextra-filescleanly because stable SemVer is already PEP 440 — no conversion needed. The prerelease branch is the first time the conversion path actually matters in this repo.Release-As: 6.0.0-beta.1footer ona083f820is correctly authored to trigger the initial bump from 5.7.0..release-please-manifest.jsonwill track the SemVer form (6.0.0-beta.1), which is fine — the bug is specifically the pyproject.toml write.
Must fix
release-please-config.json:12-18—extra-fileswrites SemVer literally. Release-please's genericJsonupdater (the one invoked bytype: "json") applies no PEP 440 normalization; only the Python strategy's nativepyproject.tomlupdater does. The release PR will proposeversion = "6.0.0-beta.1"and the PyPI publish step rejects it. Drop theextra-filesentry and letrelease-type: pythonhandlepyproject.tomlnatively, or switch the entry to a Python-aware updater.code-revieweranddx-expertboth flagged Blocker independently with the same fix.
The PR body's test-plan checkbox [ ] Verify the proposed pyproject.toml version is 6.0.0b1 (NOT 6.0.0-beta.1) is the author's own anticipation of this exact failure. Belt-and-suspenders is good, but the underlying config should produce correct output unconditionally — the manual gate is the second line of defense, not the first.
Follow-ups (non-blocking — file as issues, or fold into the same fix-up)
- README install line.
pip install adcpkeeps resolving to 5.7.x by PEP 440 prerelease exclusion — that's the right default, but adopters tracking beta need a one-liner near the install command pointing atpip install --pre adcporpip install adcp==6.0.0b1. - Migration stub. Precedent set by the existing
MIGRATION_*.mdfiles — aMIGRATION_v5_to_v6.mdshell can land alongside this config flip and accrete entries as #741 (canonical-formats) lands. ADCP_VERSIONis decoupled. The SDK going to6.0.0-beta.1does not flip the schema-sync skip in.github/workflows/ci.yml;ADCP_VERSION(3.1.0-beta.3) is the upstream spec version and tracks separately. Worth a sentence in the PR body so this doesn't get re-flagged later.feat!:during the beta line. Withprerelease: true, a breaking-change commit increments to6.0.0-beta.2rather than rolling over. Standard behavior, but worth saying out loud somewhere —bump-minor-pre-major: trueis a no-op past 1.0 and doesn't change this.
Two-line config diff, one concrete uninstallable-wheel path. Fix the updater shape, re-request review.
…lization Per aao-ipr-bot review on #804: the generic JSON `extra-files` updater writes the raw SemVer version string into `pyproject.toml`, bypassing PEP 440 normalization. For stable releases this is inert (SemVer == PEP 440), but for prereleases it produces invalid versions like `6.0.0-beta.1` instead of `6.0.0b1` — and PyPI rejects the wheel. The Python release-type natively handles `pyproject.toml`'s `[project] version` field and applies the SemVer → PEP 440 conversion automatically. Dropping the redundant `extra-files` entry lets the native updater do its job. Refs: #802, #804
|
Addressed the blocker in cd0c54f4 — dropped the |
|
Thanks for the quick fixup. The change in cd0c54f looks correct — dropping the The remaining verification (PEP 440 format in the release PR, manifest in SemVer form, CHANGELOG section) is still in the test-plan checklist — nothing to change there. Ready for human review/merge when CI is green. Generated by Claude Code |
There was a problem hiding this comment.
LGTM. Follow-ups noted below. Dropping the generic JSON extra-files writer in favor of the python release-type's native [project] version updater is the right shape — it's the only path that gets SemVer → PEP 440 normalization (6.0.0-beta.1 → 6.0.0b1) and keeps the wheel installable.
Things I checked
- release-please's python release-type owns
pyproject.toml's[project] versionnatively and applies PEP 440 normalization — theextra-filesremoval atrelease-please-config.json:10-15is exactly the fixcd0c54f4claims. googleapis/release-please-action@v5defaultsconfig-file/manifest-fileto repo-root paths, both of which exist. The action-levelrelease-type: pythonat.github/workflows/release-please.yml:19is harmless redundancy — the per-package config wins.src/adcp/__init__.py:502reads version viaimportlib.metadata.version("adcp"), not a literal — so droppingextra-filesdoes not leave__version__stranded. No source-file patching needed.Release-As: 6.0.0-beta.1footer +prerelease: true+prerelease-type: betacompose correctly: footer forces the first bump, the prerelease settings governbeta.2 → beta.3 → …until GA.- pip resolution:
pip install adcpstays on 5.7.0 post-publish (prereleases not pulled without--preor a pre spec). PYPY_API_TOKENat.github/workflows/release-please.yml:46is the intentional repo-secret name perCLAUDE.md, not a typo.
Follow-ups (non-blocking — file as issues)
- Adopter install path is a footgun across the SemVer/PEP 440 split.
pip install adcp==6.0.0-beta.1will fail with pip's generic "no matching distribution"; the working pin isadcp==6.0.0b1(orpip install --pre adcp). Add one line toRELEASING.mdand an "Installing pre-releases" note toREADME.mdbefore the beta lands — an agent generating an install command from the git tagv6.0.0-beta.1will produce a broken pin otherwise. - Tighten the pre-merge checklist on the release PR. Add: (1) git tag is
v6.0.0-beta.1, (2) the GitHub release is marked "pre-release" (not "latest"), (3)pip install adcpwith no spec still resolves to 5.7.0 after publish. - First-publish risk is one-shot. A malformed version string burns the number permanently on prod PyPI. Worth a TestPyPI dry-run or a one-time manual-approval environment gate on the
Publish to PyPIstep for the6.0.0-beta.1release only — the prerelease config has never run end-to-end against this repo.
Clean response to the prior aao-ipr-bot flag on the extra-files PEP 440 leak — that was the load-bearing catch.
LGTM. Follow-ups noted below.
Mirrors the precedent set by MIGRATION_v1_to_v2 / v3_to_v4 / v4.0_to_v4.1 — a per-major migration doc that accretes entries as breaking surfaces land on the beta line (starting with #741 canonical-formats). Also serves as the Release-As trigger for the initial 6.0.0-beta.1 bump, since the original trailer on #804 was buried mid-message by the squash-merge and release-please's parser only honors footers at the very end of a commit message. Refs: #802 Release-As: 6.0.0-beta.1
Summary
Configures release-please to track a 6.0.0-beta prerelease line. The
Release-As: 6.0.0-beta.1footer on the commit triggers an initial bump from 5.7.0 → 6.0.0-beta.1 when this PR merges to main; theprerelease: true+prerelease-type: "beta"config keeps subsequent feature work on the beta line (6.0.0-beta.2, beta.3, …) until GA.Why now: most of the AdCP 3.1 SDK roadmap shipped in 5.7.0 (#350, #392, #453, #462, #749 Parts 1-3, plus ADCP_VERSION bump to 3.1.0-beta.3). The remaining work — most notably #741 canonical-formats projection — changes the public type surface (
ProductFormatDeclarationdiscriminator), which is breaking enough to warrant a major bump.Closes #802.
Verify before merging the release PR
This is the config-only PR — merging it doesn't cut a release. After merge, release-please opens a follow-up PR proposing v6.0.0-beta.1. Inspect that PR before merging it:
pyproject.tomlversion is6.0.0b1(PEP 440), not the literal SemVer string6.0.0-beta.1. The Python release-type should convert; if it doesn't, the package becomes uninstallable via pip and we need to fix the conversion before merging the release PR..release-please-manifest.jsonis6.0.0-beta.1(SemVer form is fine in the manifest).Follow-up work that ships on this line
Test plan
6.0.0b1(NOT6.0.0-beta.1)adcp==6.0.0b1pip install adcp==6.0.0b1succeedspip install adcpstill resolves to 5.7.0 (prereleases not pulled by default)🤖 Generated with Claude Code