[rubygems/rubygems] Add auto_install support to require "bundler/setup"

We have some places that already use `bundle config auto_install true`,
ie:

7a144f3374/bundler/lib/bundler/cli.rb (L11)

This applies the same logic (copy and pasted) to happen when you
`require "bundler/setup"`.

https://github.com/rubygems/rubygems/commit/bb3c922341
This commit is contained in:
Josh Nichols 2023-03-28 15:45:41 -04:00 committed by git
parent b6489e9f62
commit 6f4f360fc4
4 changed files with 40 additions and 21 deletions

View File

@ -40,6 +40,7 @@ module Bundler
SUDO_MUTEX = Thread::Mutex.new
autoload :Checksum, File.expand_path("bundler/checksum", __dir__)
autoload :CLI, File.expand_path("bundler/cli", __dir__)
autoload :CIDetector, File.expand_path("bundler/ci_detector", __dir__)
autoload :Definition, File.expand_path("bundler/definition", __dir__)
autoload :Dependency, File.expand_path("bundler/dependency", __dir__)
@ -165,6 +166,25 @@ module Bundler
end
end
# Automatically install dependencies if Bundler.settings[:auto_install] exists.
# This is set through config cmd `bundle config set --global auto_install 1`.
#
# Note that this method `nil`s out the global Definition object, so it
# should be called first, before you instantiate anything like an
# `Installer` that'll keep a reference to the old one instead.
def auto_install
return unless settings[:auto_install]
begin
definition.specs
rescue GemNotFound, GitError
ui.info "Automatically installing missing gems."
reset!
CLI::Install.new({}).run
reset!
end
end
# Setups Bundler environment (see Bundler.setup) if it is not already set,
# and loads all gems from groups specified. Unlike ::setup, can be called
# multiple times with different groups (if they were allowed by setup).

View File

@ -5,6 +5,7 @@ require_relative "vendored_thor"
module Bundler
class CLI < Thor
require_relative "cli/common"
require_relative "cli/install"
package_name "Bundler"
@ -69,7 +70,7 @@ module Bundler
Bundler.settings.set_command_option_if_given :retry, options[:retry]
current_cmd = args.last[:current_command].name
auto_install if AUTO_INSTALL_CMDS.include?(current_cmd)
Bundler.auto_install if AUTO_INSTALL_CMDS.include?(current_cmd)
rescue UnknownArgumentError => e
raise InvalidOption, e.message
ensure
@ -737,26 +738,6 @@ module Bundler
private
# Automatically invoke `bundle install` and resume if
# Bundler.settings[:auto_install] exists. This is set through config cmd
# `bundle config set --global auto_install 1`.
#
# Note that this method `nil`s out the global Definition object, so it
# should be called first, before you instantiate anything like an
# `Installer` that'll keep a reference to the old one instead.
def auto_install
return unless Bundler.settings[:auto_install]
begin
Bundler.definition.specs
rescue GemNotFound, GitError
Bundler.ui.info "Automatically installing missing gems."
Bundler.reset!
invoke :install, []
Bundler.reset!
end
end
def current_command
_, _, config = @_initializer
config[:current_command]

View File

@ -5,6 +5,9 @@ require_relative "shared_helpers"
if Bundler::SharedHelpers.in_bundle?
require_relative "../bundler"
# try to auto_install first before we get to the `Bundler.ui.silence`, so user knows what is happening
Bundler.auto_install
if STDOUT.tty? || ENV["BUNDLER_FORCE_TTY"]
begin
Bundler.ui.silence { Bundler.setup }

View File

@ -1599,4 +1599,19 @@ end
sys_exec "#{Gem.ruby} #{script}", raise_on_error: false
expect(out).to include("requiring foo used the monkeypatch")
end
it "performs an automatic bundle install" do
gemfile <<-G
source "#{file_uri_for(gem_repo1)}"
gem "rack", :group => :test
G
bundle "config set auto_install 1"
ruby <<-RUBY
require 'bundler/setup'
RUBY
expect(err).to be_empty
expect(out).to include("Installing rack 1.0.0")
end
end