Standardize Xcode bundle naming with a configurable separator#156
Merged
Conversation
Adds a user-selectable separator ('_' or '-') controlling managed Xcode
bundle names, and drops the build-number suffix from the default format
(issue #155). Build number is now appended only on collision.
- New AppPreferences.XcodeBundleSeparator preference (default '_').
- XcodeService: thread separator through name generation, install, and
selection flows. Default name is Xcode<sep><version>.app; collision
falls back to Xcode<sep><version><sep><build>.app, then numeric suffix.
- New IXcodeService.GetNormalizationPlanAsync + NormalizeBundleNamesAsync
so the UI can offer to rename existing bundles when the setting
changes, retargeting /Applications/Xcode.app if needed via admin shell.
- Settings.razor: new separator dropdown with confirm-and-normalize
migration flow.
- CLI parity in XcodeCommand, plus a new 'apple xcode normalize-names'
subcommand with --separator and --dry-run.
- Parameterized tests for both separators, collision handling, and
normalization planning (symlink retarget, collisions, no-op cases).
Refs #155
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.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.
Sherpa's managed Xcode bundles currently use a custom
Xcode_<version>_<build>.appformat, which doesn't match GitHub's runner-images (Xcode_<version>.app) or the xcodes CLI (Xcode-<version>.app). This PR standardizes on the common shape and lets users pick which separator they prefer. Refs #155.What changed
Xcode<sep><version>.app(e.g.Xcode_26.3.app). The build number is appended only when needed to disambiguate two installs of the same marketing version, and a numeric suffix is the final fallback.XcodeBundleSeparatorpreference (_default,-alternative) surfaced as a dropdown in Settings under the Xcode section./Applications, shows a confirm dialog listing the exact renames, then runs an admin-elevated shell script tomveach bundle and retarget/Applications/Xcode.appviaxcode-selectif its symlink target was one of the renamed bundles.XcodeCommandthreads the same separator through its helpers, and a newmaui-sherpa apple xcode normalize-namessubcommand exposes the planner with--separatorand--dry-runflags for scripted use.XcodeServiceTestsnow has parameterized coverage for both separators, the plain-name / build-suffix / numeric-suffix collision ladder, and four normalization-plan scenarios (no-op, cross-format rename, symlink retarget, and collision-via-build-number when two installs land in the same slot).Notes for reviewers
XcodeService(CreateSelectionPlan,InstallXcodeAsync,SelectXcodeAsync) all take the separator as a parameter now;SelectXcodeAsyncreads the current user pref viaGetBundleSeparatorAsync()so callers don't need to know about it.ComputeNormalizationPlanis kept as a pure static so it's easy to unit test; the asyncGetNormalizationPlanAsync/NormalizeBundleNamesAsyncare thin wrappers over the filesystem and the existingRunElevatedShellScriptAsynchelper.LooksLikeManagedBundleName) intentionally skips plainXcode.app(Mac App Store) andXcodes.appso those are never renamed. Only bundles starting withXcode_orXcode-are considered.build.ymlalready assumes theXcode_<version>.appshape in a few places, so the underscore default is consistent with CI expectations.Closes #155.