feat(release): prefix app tags app/v so they leave SwiftPM's namespace - #79
Merged
Conversation
Delivers backlog 999.2 / audit W-1.
This repo is both an app and a SwiftPM package, and SwiftPM claims every
tag that parses as a version. So v0.1.1+9 was simultaneously the app's
release marker AND package version 0.1.1: an App Store metadata bump
published a package version, and adopters got a bump from a commit that
never mentioned SwiftPM.
Decided on a measurement, which contradicted the roadmap. Its third
option was "publish the package from a separate tag series SwiftPM
resolves". Tagging this repo and resolving against it:
pkg-0.3.0, package/0.4.0, release/0.5.0, milestone/v0.2
-> .upToNextMajor(from: "0.1.0") resolved 0.1.1+9 (all ignored)
v0.2
-> resolved 0.2.0 (claimed at once)
SwiftPM cannot be pointed at a non-default tag scheme, so that option
does not exist. The inverse works and was not in the list at all: move
the APP tags out of its view and leave the package namespace clean.
Neither remaining option was needed — the package did not have to move
repos, and the coupling did not have to be accepted.
Implemented upstream as RELEASE_TAG_PREFIX (apple-shipkit#286, plus #287
fixing plumbing #286 shipped incomplete: the value reached neither
.bootstrap.env readers nor the fastlane subprocess, so ship.rb would
have computed app/v0.1.2+10 and handed it to a process still stripping
"v"). Unset means "v", so no other fork changes.
Verified end to end here: bin/compute-release-tag.rb returns
app/v0.1.1+10 from .bootstrap.env, and RELEASE_TAG_PREFIX=v returns
v0.1.1+10 — env precedence and default-equivalence both proven on the
real path.
v0.1.0+6 and v0.1.1+9 stay published and remain the current package
versions; every reader strips the configured prefix then falls back to a
bare "v", so pre-change tags still parse.
ci/check-release-commit.sh now says which kind of tag a ship is about to
push — its W-1 note fires only when the tag really is SwiftPM-visible.
A package release now requires cutting a bare X.Y.Z tag on purpose.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
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.
Delivers backlog 999.2 / audit W-1.
The coupling
This repo is both an app and a SwiftPM package, and SwiftPM claims every tag that parses as a version. So
v0.1.1+9was simultaneously the app's release marker and package version0.1.1. An App Store metadata bump published a package version, and adopters got a bump from a commit that never mentioned SwiftPM.The measurement contradicted the plan
The roadmap's third option was "publish the package from a separate tag series that SwiftPM resolves — needs checking whether SwiftPM can be pointed at a non-default tag scheme". I checked, by tagging this repo and resolving against it:
.upToNextMajor(from: "0.1.0")resolved topkg-0.3.0,package/0.4.0,release/0.5.0,milestone/v0.20.1.1+9— every prefixed tag ignoredv0.20.2.0— a bare tag claimed immediatelyThat option does not exist. But the inverse works, and it was not in the options list at all: move the app tags out of SwiftPM's view and leave the package namespace clean.
Neither remaining option was needed — the package did not have to move to its own repo, and the coupling did not have to be accepted. The two lifecycles now move independently in one repo, which the backlog note said was the thing that could not be had.
Implemented upstream
RELEASE_TAG_PREFIXin apple-shipkit#286, plus #287 fixing plumbing that #286 shipped incomplete — the value reached neither.bootstrap.envreaders nor the fastlane subprocess, soship.rbwould have computedapp/v0.1.2+10and handed it to a process that still strippedv, leaving every artifact name built from the unstripped tag. Found while adopting it here, not by re-reading the diff.Unset means
v, so no other fork changes behaviour.Verified end to end, on the real path
.bootstrap.env→Config→ENV→Version.tag_prefix→ tag. Env precedence and default-equivalence both proven, not inferred.Compatibility
v0.1.0+6andv0.1.1+9stay published and remain the current package versions. Every reader strips the configured prefix and then falls back to a barev, so pre-change tags still parse —ci/bump-asc-version.rbmay still be handed either.ci/check-release-commit.shnow says which kind of tag a ship is about to push. Its W-1 "this is also a package version" note fires only when the tag really is SwiftPM-visible:Both branches exercised.
A package release now requires cutting a bare
X.Y.Ztag on purpose. That is the point, and it is documented inAGENTS.mdand.bootstrap.env.example.Local:
tag_prefix_test.rb23/23,check-shell.shclean,check-patch-registry.shpasses.