From b49625a7dc19517289764df0b2e1dc5671dd490e Mon Sep 17 00:00:00 2001 From: Mike McQuaid Date: Thu, 23 Jan 2025 14:42:03 +0000 Subject: [PATCH] Add `brew install --skip-link` We already have `--skip-post-install` and this adds similar behaviour for e.g. `brew bundle` (and other users) to be able to install a formula but skip the `brew link` stage afterwards. --- Library/Homebrew/cmd/install.rb | 5 +++++ Library/Homebrew/formula_installer.rb | 18 +++++++++++++++++- Library/Homebrew/install.rb | 7 +++++-- .../rbi/dsl/homebrew/cmd/install_cmd.rbi | 3 +++ completions/bash/brew | 2 ++ completions/fish/brew.fish | 2 ++ completions/zsh/_brew | 6 ++++-- docs/Manpage.md | 4 ++++ manpages/brew.1 | 3 +++ 9 files changed, 45 insertions(+), 5 deletions(-) diff --git a/Library/Homebrew/cmd/install.rb b/Library/Homebrew/cmd/install.rb index defbe8f820d5d..c4aeb49d0d138 100644 --- a/Library/Homebrew/cmd/install.rb +++ b/Library/Homebrew/cmd/install.rb @@ -101,6 +101,9 @@ class InstallCmd < AbstractCommand [:switch, "--skip-post-install", { description: "Install but skip any post-install steps.", }], + [:switch, "--skip-link", { + description: "Install but skip linking the keg into the prefix.", + }], [:flag, "--bottle-arch=", { depends_on: "--build-bottle", description: "Optimise bottles for the specified architecture rather than the oldest " \ @@ -289,6 +292,7 @@ def run only_dependencies: args.only_dependencies?, force: args.force?, quiet: args.quiet?, + skip_link: args.skip_link?, overwrite: args.overwrite?, ) end @@ -319,6 +323,7 @@ def run verbose: args.verbose?, dry_run: args.dry_run?, skip_post_install: args.skip_post_install?, + skip_link: args.skip_link?, ) Upgrade.check_installed_dependents( diff --git a/Library/Homebrew/formula_installer.rb b/Library/Homebrew/formula_installer.rb index 25218a1f60e95..430fd47db7210 100644 --- a/Library/Homebrew/formula_installer.rb +++ b/Library/Homebrew/formula_installer.rb @@ -60,6 +60,7 @@ class FormulaInstaller show_header: T::Boolean, build_bottle: T::Boolean, skip_post_install: T::Boolean, + skip_link: T::Boolean, force_bottle: T::Boolean, bottle_arch: T.nilable(String), ignore_deps: T::Boolean, @@ -88,6 +89,7 @@ def initialize( show_header: false, build_bottle: false, skip_post_install: false, + skip_link: false, force_bottle: false, bottle_arch: nil, ignore_deps: false, @@ -120,6 +122,7 @@ def initialize( @build_from_source_formulae = build_from_source_formulae @build_bottle = build_bottle @skip_post_install = skip_post_install + @skip_link = skip_link @bottle_arch = bottle_arch @formula.force_bottle ||= force_bottle @force_bottle = T.let(@formula.force_bottle, T::Boolean) @@ -195,6 +198,11 @@ def skip_post_install? @skip_post_install.present? end + sig { returns(T::Boolean) } + def skip_link? + @skip_link.present? + end + sig { params(output_warning: T::Boolean).returns(T::Boolean) } def pour_bottle?(output_warning: false) return false if !formula.bottle_tag? && !formula.local_bottle_path @@ -866,7 +874,15 @@ def finish ohai "Finishing up" if verbose? keg = Keg.new(formula.prefix) - link(keg) + if skip_link? + unless quiet? + ohai "Skipping 'link' on request" + puts "You can run it manually using:" + puts " brew link #{formula.full_name}" + end + else + link(keg) + end install_service diff --git a/Library/Homebrew/install.rb b/Library/Homebrew/install.rb index aea4eba02e88d..80c3c540699cc 100644 --- a/Library/Homebrew/install.rb +++ b/Library/Homebrew/install.rb @@ -70,6 +70,7 @@ def install_formula?( only_dependencies: false, force: false, quiet: false, + skip_link: false, overwrite: false ) # head-only without --HEAD is an error @@ -201,7 +202,7 @@ def install_formula?( To upgrade to #{formula.pkg_version}, run: #{unpin_cmd_if_needed}brew upgrade #{formula.full_name} EOS - elsif only_dependencies + elsif only_dependencies || skip_link return true else onoe <<~EOS @@ -250,7 +251,8 @@ def install_formulae( quiet: false, verbose: false, dry_run: false, - skip_post_install: false + skip_post_install: false, + skip_link: false ) formula_installers = formulae_to_install.filter_map do |formula| Migrator.migrate_if_needed(formula, force:, dry_run:) @@ -279,6 +281,7 @@ def install_formulae( quiet:, verbose:, skip_post_install:, + skip_link:, ) begin diff --git a/Library/Homebrew/sorbet/rbi/dsl/homebrew/cmd/install_cmd.rbi b/Library/Homebrew/sorbet/rbi/dsl/homebrew/cmd/install_cmd.rbi index e83974293fef1..2bd0d91e0250b 100644 --- a/Library/Homebrew/sorbet/rbi/dsl/homebrew/cmd/install_cmd.rbi +++ b/Library/Homebrew/sorbet/rbi/dsl/homebrew/cmd/install_cmd.rbi @@ -152,6 +152,9 @@ class Homebrew::Cmd::InstallCmd::Args < Homebrew::CLI::Args sig { returns(T::Boolean) } def skip_cask_deps?; end + sig { returns(T::Boolean) } + def skip_link?; end + sig { returns(T::Boolean) } def skip_post_install?; end diff --git a/completions/bash/brew b/completions/bash/brew index 24772fdaad45a..4db025a7a1ab9 100644 --- a/completions/bash/brew +++ b/completions/bash/brew @@ -1342,6 +1342,7 @@ _brew_instal() { --screen-saverdir --servicedir --skip-cask-deps + --skip-link --skip-post-install --verbose --vst-plugindir @@ -1405,6 +1406,7 @@ _brew_install() { --screen-saverdir --servicedir --skip-cask-deps + --skip-link --skip-post-install --verbose --vst-plugindir diff --git a/completions/fish/brew.fish b/completions/fish/brew.fish index e48d454848b71..22334a5a5208c 100644 --- a/completions/fish/brew.fish +++ b/completions/fish/brew.fish @@ -912,6 +912,7 @@ __fish_brew_complete_arg 'instal' -l require-sha -d 'Require all casks to have a __fish_brew_complete_arg 'instal' -l screen-saverdir -d 'Target location for Screen Savers (default: `~/Library/Screen Savers`)' __fish_brew_complete_arg 'instal' -l servicedir -d 'Target location for Services (default: `~/Library/Services`)' __fish_brew_complete_arg 'instal' -l skip-cask-deps -d 'Skip installing cask dependencies' +__fish_brew_complete_arg 'instal' -l skip-link -d 'Install but skip linking the keg into the prefix' __fish_brew_complete_arg 'instal' -l skip-post-install -d 'Install but skip any post-install steps' __fish_brew_complete_arg 'instal' -l verbose -d 'Print the verification and post-install steps' __fish_brew_complete_arg 'instal' -l vst-plugindir -d 'Target location for VST Plugins (default: `~/Library/Audio/Plug-Ins/VST`)' @@ -966,6 +967,7 @@ __fish_brew_complete_arg 'install' -l require-sha -d 'Require all casks to have __fish_brew_complete_arg 'install' -l screen-saverdir -d 'Target location for Screen Savers (default: `~/Library/Screen Savers`)' __fish_brew_complete_arg 'install' -l servicedir -d 'Target location for Services (default: `~/Library/Services`)' __fish_brew_complete_arg 'install' -l skip-cask-deps -d 'Skip installing cask dependencies' +__fish_brew_complete_arg 'install' -l skip-link -d 'Install but skip linking the keg into the prefix' __fish_brew_complete_arg 'install' -l skip-post-install -d 'Install but skip any post-install steps' __fish_brew_complete_arg 'install' -l verbose -d 'Print the verification and post-install steps' __fish_brew_complete_arg 'install' -l vst-plugindir -d 'Target location for VST Plugins (default: `~/Library/Audio/Plug-Ins/VST`)' diff --git a/completions/zsh/_brew b/completions/zsh/_brew index 2de28d5f85ecc..aefc9e48fdee2 100644 --- a/completions/zsh/_brew +++ b/completions/zsh/_brew @@ -1145,6 +1145,7 @@ _brew_instal() { '(--formula)--screen-saverdir[Target location for Screen Savers (default: `~/Library/Screen Savers`)]' \ '(--formula)--servicedir[Target location for Services (default: `~/Library/Services`)]' \ '(--formula)--skip-cask-deps[Skip installing cask dependencies]' \ + '(--cask)--skip-link[Install but skip linking the keg into the prefix]' \ '(--cask)--skip-post-install[Install but skip any post-install steps]' \ '--verbose[Print the verification and post-install steps]' \ '(--formula)--vst-plugindir[Target location for VST Plugins (default: `~/Library/Audio/Plug-Ins/VST`)]' \ @@ -1154,7 +1155,7 @@ _brew_instal() { '(--casks --binaries --require-sha --quarantine --adopt --skip-cask-deps --zap --appdir --keyboard-layoutdir --colorpickerdir --prefpanedir --qlplugindir --mdimporterdir --dictionarydir --fontdir --servicedir --input-methoddir --internet-plugindir --audio-unit-plugindir --vst-plugindir --vst3-plugindir --screen-saverdir --language)--formula[Treat all named arguments as formulae]' \ '*::formula:__brew_formulae' \ - cask \ - '(--formulae --env --ignore-dependencies --only-dependencies --cc --build-from-source --force-bottle --include-test --HEAD --fetch-HEAD --keep-tmp --debug-symbols --build-bottle --skip-post-install --bottle-arch --interactive --git --overwrite)--cask[Treat all named arguments as casks]' \ + '(--formulae --env --ignore-dependencies --only-dependencies --cc --build-from-source --force-bottle --include-test --HEAD --fetch-HEAD --keep-tmp --debug-symbols --build-bottle --skip-post-install --skip-link --bottle-arch --interactive --git --overwrite)--cask[Treat all named arguments as casks]' \ '*::cask:__brew_casks' } @@ -1203,6 +1204,7 @@ _brew_install() { '(--formula)--screen-saverdir[Target location for Screen Savers (default: `~/Library/Screen Savers`)]' \ '(--formula)--servicedir[Target location for Services (default: `~/Library/Services`)]' \ '(--formula)--skip-cask-deps[Skip installing cask dependencies]' \ + '(--cask)--skip-link[Install but skip linking the keg into the prefix]' \ '(--cask)--skip-post-install[Install but skip any post-install steps]' \ '--verbose[Print the verification and post-install steps]' \ '(--formula)--vst-plugindir[Target location for VST Plugins (default: `~/Library/Audio/Plug-Ins/VST`)]' \ @@ -1212,7 +1214,7 @@ _brew_install() { '(--casks --binaries --require-sha --quarantine --adopt --skip-cask-deps --zap --appdir --keyboard-layoutdir --colorpickerdir --prefpanedir --qlplugindir --mdimporterdir --dictionarydir --fontdir --servicedir --input-methoddir --internet-plugindir --audio-unit-plugindir --vst-plugindir --vst3-plugindir --screen-saverdir --language)--formula[Treat all named arguments as formulae]' \ '*::formula:__brew_formulae' \ - cask \ - '(--formulae --env --ignore-dependencies --only-dependencies --cc --build-from-source --force-bottle --include-test --HEAD --fetch-HEAD --keep-tmp --debug-symbols --build-bottle --skip-post-install --bottle-arch --interactive --git --overwrite)--cask[Treat all named arguments as casks]' \ + '(--formulae --env --ignore-dependencies --only-dependencies --cc --build-from-source --force-bottle --include-test --HEAD --fetch-HEAD --keep-tmp --debug-symbols --build-bottle --skip-post-install --skip-link --bottle-arch --interactive --git --overwrite)--cask[Treat all named arguments as casks]' \ '*::cask:__brew_casks' } diff --git a/docs/Manpage.md b/docs/Manpage.md index fe8caa45a5887..e330e3b1113f2 100644 --- a/docs/Manpage.md +++ b/docs/Manpage.md @@ -644,6 +644,10 @@ upgrade *`formula`* if it is already installed but outdated. : Install but skip any post-install steps. +`--skip-link` + +: Install but skip linking the keg into the prefix. + `--bottle-arch` : Optimise bottles for the specified architecture rather than the oldest diff --git a/manpages/brew.1 b/manpages/brew.1 index 818ff540060f5..e98221f238fbb 100644 --- a/manpages/brew.1 +++ b/manpages/brew.1 @@ -403,6 +403,9 @@ Prepare the formula for eventual bottling during installation, skipping any post \fB\-\-skip\-post\-install\fP Install but skip any post\-install steps\. .TP +\fB\-\-skip\-link\fP +Install but skip linking the keg into the prefix\. +.TP \fB\-\-bottle\-arch\fP Optimise bottles for the specified architecture rather than the oldest architecture supported by the version of macOS the bottles are built on\. .TP