diff options
72 files changed, 470 insertions, 412 deletions
diff --git a/.rspec_parallel b/.rspec_parallel new file mode 100644 index 0000000000..6989221a44 --- /dev/null +++ b/.rspec_parallel @@ -0,0 +1,4 @@ +--format progress +--format ParallelTests::RSpec::RuntimeLogger --out tmp/parallel_runtime_rspec.log +--require spec_helper +--require support/parallel.rb diff --git a/.travis.yml b/.travis.yml index 3d2a321215..52591a022c 100644 --- a/.travis.yml +++ b/.travis.yml @@ -39,8 +39,8 @@ env: - RGV=master BUNDLER_SPEC_SUB_VERSION=3.0.0 - RGV=master # Test the latest rubygems release with all of our supported rubies - - RGV=v3.0.4 BUNDLER_SPEC_SUB_VERSION=3.0.0 - - RGV=v3.0.4 + - RGV=v3.0.6 BUNDLER_SPEC_SUB_VERSION=3.0.0 + - RGV=v3.0.6 jobs: include: @@ -52,7 +52,7 @@ jobs: env: RGV=master stage: test - rvm: 2.3.8 - env: RGV=v3.0.4 + env: RGV=v3.0.6 stage: test # Ruby 2.5, Rubygems 2.7 - rvm: 2.5.5 @@ -51,7 +51,7 @@ namespace :spec do sh "sudo apt-get install graphviz -y" # Install the gems with a consistent version of RubyGems - sh "gem update --system 3.0.4" + sh "gem update --system 3.0.6" # Install the other gem deps, etc Rake::Task["spec:deps"].invoke @@ -89,9 +89,13 @@ namespace :spec do namespace :rubygems do # When editing this list, also edit .travis.yml! branches = %w[master] - releases = %w[v2.5.2 v2.6.14 v2.7.10 v3.0.4] + releases = %w[v2.5.2 v2.6.14 v2.7.10 v3.0.6] (branches + releases).each do |rg| desc "Run specs with RubyGems #{rg}" + task "parallel_#{rg}" do + sh("bin/parallel_rspec spec/") + end + task rg do sh("bin/rspec --format progress") end @@ -112,7 +116,7 @@ namespace :spec do desc "Run specs under a RubyGems checkout (set RGV=path)" task "co" do - sh("bin/rspec --format progress") + sh("bin/parallel_rspec spec/") end namespace "co" do @@ -312,7 +316,9 @@ else # This will be automated once https://github.com/segiddins/automatiek/pull/3 # is included in `automatiek` and we start using the new API for vendoring # subdependencies. - + # Besides that, we currently cherry-pick changes to use `require_relative` + # internally instead of regular `require`. They are pending review at + # https://github.com/drbrain/net-http-persistent/pull/106 desc "Vendor a specific version of net-http-persistent" Automatiek::RakeTask.new("net-http-persistent") do |lib| lib.download = { :github => "https://github.com/drbrain/net-http-persistent" } diff --git a/bin/parallel_rspec b/bin/parallel_rspec new file mode 100755 index 0000000000..26402aee7c --- /dev/null +++ b/bin/parallel_rspec @@ -0,0 +1,12 @@ +#!/usr/bin/env ruby +# frozen_string_literal: true + +load File.expand_path("../with_rubygems", __FILE__) if ENV["RGV"] + +require_relative "../spec/support/rubygems_ext" + +begin + Spec::Rubygems.gem_load("parallel_tests", "parallel_rspec") +rescue Gem::LoadError => e + warn "We couln't activate parallel_tests (#{e.requirement}). Run `gem install parallel_tests:'#{e.requirement}'`" +end diff --git a/exe/bundle b/exe/bundle index aaf773745d..b3b1b691d8 100755 --- a/exe/bundle +++ b/exe/bundle @@ -7,7 +7,14 @@ Signal.trap("INT") do exit 1 end -require "bundler" +base_path = File.expand_path("../lib", __dir__) + +if File.exist?(base_path) + require_relative "../lib/bundler" +else + require "bundler" +end + # Check if an older version of bundler is installed $LOAD_PATH.each do |path| next unless path =~ %r{/bundler-0\.(\d+)} && $1.to_i < 9 @@ -18,9 +25,18 @@ $LOAD_PATH.each do |path| abort(err) end -require "bundler/friendly_errors" +if File.exist?(base_path) + require_relative "../lib/bundler/friendly_errors" +else + require "bundler/friendly_errors" +end + Bundler.with_friendly_errors do - require "bundler/cli" + if File.exist?(base_path) + require_relative "../lib/bundler/cli" + else + require "bundler/cli" + end # Allow any command to use --help flag to show help for that command help_flags = %w[--help -h] diff --git a/lib/bundler.rb b/lib/bundler.rb index 1887457c77..a21dc7726d 100644 --- a/lib/bundler.rb +++ b/lib/bundler.rb @@ -260,7 +260,7 @@ module Bundler message = <<EOF It is a security vulnerability to allow your home directory to be world-writable, and bundler can not continue. You should probably consider fixing this issue by running `chmod o-w ~` on *nix. -Please refer to http://ruby-doc.org/stdlib-2.1.2/libdoc/fileutils/rdoc/FileUtils.html#method-c-remove_entry_secure for details. +Please refer to https://ruby-doc.org/stdlib-2.1.2/libdoc/fileutils/rdoc/FileUtils.html#method-c-remove_entry_secure for details. EOF File.world_writable?(path) ? Bundler.ui.warn(message) : raise raise PathError, "Please fix the world-writable issue with your #{path} directory" diff --git a/lib/bundler/capistrano.rb b/lib/bundler/capistrano.rb index 573df95043..1f3712d48e 100644 --- a/lib/bundler/capistrano.rb +++ b/lib/bundler/capistrano.rb @@ -2,7 +2,7 @@ require_relative "shared_helpers" Bundler::SharedHelpers.major_deprecation 2, - "The Bundler task for Capistrano. Please use http://github.com/capistrano/bundler" + "The Bundler task for Capistrano. Please use https://github.com/capistrano/bundler" # Capistrano task for Bundler. # @@ -12,7 +12,7 @@ require_relative "deployment" require "capistrano/version" if defined?(Capistrano::Version) && Gem::Version.new(Capistrano::Version).release >= Gem::Version.new("3.0") - raise "For Capistrano 3.x integration, please use http://github.com/capistrano/bundler" + raise "For Capistrano 3.x integration, please use https://github.com/capistrano/bundler" end Capistrano::Configuration.instance(:must_exist).load do diff --git a/lib/bundler/cli/doctor.rb b/lib/bundler/cli/doctor.rb index 1b3913a300..fcf139ed1e 100644 --- a/lib/bundler/cli/doctor.rb +++ b/lib/bundler/cli/doctor.rb @@ -100,7 +100,7 @@ module Bundler files_not_readable_or_writable = [] files_not_rw_and_owned_by_different_user = [] files_not_owned_by_current_user_but_still_rw = [] - Find.find(Bundler.home.to_s).each do |f| + Find.find(Bundler.bundle_path.to_s).each do |f| if !File.writable?(f) || !File.readable?(f) if File.stat(f).uid != Process.uid files_not_rw_and_owned_by_different_user << f diff --git a/lib/bundler/cli/exec.rb b/lib/bundler/cli/exec.rb index 5dcf4a01ef..0b0e991ea5 100644 --- a/lib/bundler/cli/exec.rb +++ b/lib/bundler/cli/exec.rb @@ -13,7 +13,7 @@ module Bundler @cmd = args.shift @args = args - if Bundler.current_ruby.ruby_2? && !Bundler.current_ruby.jruby? + if !Bundler.current_ruby.jruby? @args << { :close_others => !options.keep_file_descriptors? } elsif options.keep_file_descriptors? Bundler.ui.warn "Ruby version #{RUBY_VERSION} defaults to keeping non-standard file descriptors on Kernel#exec." diff --git a/lib/bundler/cli/gem.rb b/lib/bundler/cli/gem.rb index 5ae9ca4af8..d3e5831759 100644 --- a/lib/bundler/cli/gem.rb +++ b/lib/bundler/cli/gem.rb @@ -190,7 +190,7 @@ module Bundler Bundler.ui.error "You have specified a gem name which does not conform to the \n" \ "naming guidelines for C extensions. For more information, \n" \ "see the 'Extension Naming' section at the following URL:\n" \ - "http://guides.rubygems.org/gems-with-extensions/\n" + "https://guides.rubygems.org/gems-with-extensions/\n" exit 1 end diff --git a/lib/bundler/cli/open.rb b/lib/bundler/cli/open.rb index 552fe6f128..df32e2f38b 100644 --- a/lib/bundler/cli/open.rb +++ b/lib/bundler/cli/open.rb @@ -14,12 +14,16 @@ module Bundler editor = [ENV["BUNDLER_EDITOR"], ENV["VISUAL"], ENV["EDITOR"]].find {|e| !e.nil? && !e.empty? } return Bundler.ui.info("To open a bundled gem, set $EDITOR or $BUNDLER_EDITOR") unless editor return unless spec = Bundler::CLI::Common.select_spec(name, :regex_match) - path = spec.full_gem_path - Dir.chdir(path) do - command = Shellwords.split(editor) + [path] - Bundler.with_original_env do - system(*command) - end || Bundler.ui.info("Could not run '#{command.join(" ")}'") + if spec.default_gem? + Bundler.ui.info "Unable to open #{name} because it's a default gem, so the directory it would normally be installed to does not exist." + else + path = spec.full_gem_path + Dir.chdir(path) do + command = Shellwords.split(editor) + [path] + Bundler.with_original_env do + system(*command) + end || Bundler.ui.info("Could not run '#{command.join(" ")}'") + end end end end diff --git a/lib/bundler/cli/outdated.rb b/lib/bundler/cli/outdated.rb index 5c8cd26d88..0b710e9782 100644 --- a/lib/bundler/cli/outdated.rb +++ b/lib/bundler/cli/outdated.rb @@ -169,8 +169,6 @@ module Bundler end def retrieve_active_spec(definition, current_spec) - return unless current_spec.match_platform(Bundler.local_platform) - if strict active_spec = definition.find_resolved_spec(current_spec) else diff --git a/lib/bundler/definition.rb b/lib/bundler/definition.rb index de3950a744..01ee86a358 100644 --- a/lib/bundler/definition.rb +++ b/lib/bundler/definition.rb @@ -113,7 +113,7 @@ module Bundler end @unlocking ||= @unlock[:ruby] ||= (!@locked_ruby_version ^ !@ruby_version) - add_platforms unless Bundler.frozen_bundle? + add_current_platform unless Bundler.frozen_bundle? converge_path_sources_to_gemspec_sources @path_changes = converge_paths @@ -518,6 +518,10 @@ module Bundler raise InvalidOption, "Unable to remove the platform `#{platform}` since the only platforms are #{@platforms.join ", "}" end + def add_current_platform + current_platforms.each {|platform| add_platform(platform) } + end + def find_resolved_spec(current_spec) specs.find_by_name_and_platform(current_spec.name, current_spec.platform) end @@ -539,12 +543,6 @@ module Bundler private - def add_platforms - (@dependencies.flat_map(&:expanded_platforms) + current_platforms).uniq.each do |platform| - add_platform(platform) - end - end - def current_platforms current_platform = Bundler.local_platform [].tap do |platforms| @@ -892,7 +890,17 @@ module Bundler dependencies.each do |dep| dep = Dependency.new(dep, ">= 0") unless dep.respond_to?(:name) next if !remote && !dep.current_platform? - dep.gem_platforms(sorted_platforms).each do |p| + platforms = dep.gem_platforms(sorted_platforms) + if platforms.empty? && !Bundler.settings[:disable_platform_warnings] + mapped_platforms = dep.expanded_platforms + Bundler.ui.warn \ + "The dependency #{dep} will be unused by any of the platforms Bundler is installing for. " \ + "Bundler is installing for #{@platforms.join ", "} but the dependency " \ + "is only for #{mapped_platforms.join ", "}. " \ + "To add those platforms to the bundle, " \ + "run `bundle lock --add-platform #{mapped_platforms.join " "}`." + end + platforms.each do |p| deps << DepProxy.new(dep, p) if remote || p == generic_local_platform end end diff --git a/lib/bundler/dsl.rb b/lib/bundler/dsl.rb index 534c9b5537..cc23f9b389 100644 --- a/lib/bundler/dsl.rb +++ b/lib/bundler/dsl.rb @@ -128,7 +128,7 @@ module Bundler else Bundler.ui.warn "Your Gemfile lists the gem #{current.name} (#{current.requirement}) more than once.\n" \ "You should probably keep only one of them.\n" \ - "Remove any duplicate entries and specify the gem only once (per group).\n" \ + "Remove any duplicate entries and specify the gem only once.\n" \ "While it's not a problem now, it could cause errors if you change the version of one of them later." end diff --git a/lib/bundler/friendly_errors.rb b/lib/bundler/friendly_errors.rb index 45faf02020..e9f06d90be 100644 --- a/lib/bundler/friendly_errors.rb +++ b/lib/bundler/friendly_errors.rb @@ -28,7 +28,7 @@ module Bundler Bundler.ui.warn <<-WARN, :wrap => true You must recompile Ruby with OpenSSL support or change the sources in your \ Gemfile from 'https' to 'http'. Instructions for compiling with OpenSSL \ - using RVM are available at http://rvm.io/packages/openssl. + using RVM are available at https://rvm.io/packages/openssl. WARN Bundler.ui.trace error when Interrupt diff --git a/lib/bundler/gem_helper.rb b/lib/bundler/gem_helper.rb index 68f5e636ff..d00c1894a8 100644 --- a/lib/bundler/gem_helper.rb +++ b/lib/bundler/gem_helper.rb @@ -75,8 +75,8 @@ module Bundler def build_gem file_name = nil - gem = ENV["BUNDLE_GEM"] ? ENV["BUNDLE_GEM"] : "gem" - sh(%W[#{gem} build -V #{spec_path}]) do + gem = ENV["GEM_COMMAND"] ? ENV["GEM_COMMAND"] : "gem" + sh("#{gem} build -V #{spec_path}".shellsplit) do file_name = File.basename(built_gem_path) SharedHelpers.filesystem_access(File.join(base, "pkg")) {|p| FileUtils.mkdir_p(p) } FileUtils.mv(built_gem_path, "pkg") @@ -87,10 +87,10 @@ module Bundler def install_gem(built_gem_path = nil, local = false) built_gem_path ||= build_gem - gem = ENV["BUNDLE_GEM"] ? ENV["BUNDLE_GEM"] : "gem" - cmd = %W[#{gem} install #{built_gem_path}] - cmd << "--local" if local - out, status = sh_with_status(cmd) + gem = ENV["GEM_COMMAND"] ? ENV["GEM_COMMAND"] : "gem" + cmd = "#{gem} install #{built_gem_path}" + cmd += " --local" if local + out, status = sh_with_status(cmd.shellsplit) unless status.success? && out[/Successfully installed/] raise "Couldn't install gem, run `gem install #{built_gem_path}' for more detailed output" end diff --git a/lib/bundler/inline.rb b/lib/bundler/inline.rb index c7c58de52b..dbf737c7ee 100644 --- a/lib/bundler/inline.rb +++ b/lib/bundler/inline.rb @@ -58,7 +58,7 @@ def gemfile(install = false, options = {}, &gemfile) Bundler.ui = ui if install if install || missing_specs.call - Bundler.settings.temporary(:inline => true) do + Bundler.settings.temporary(:inline => true, :disable_platform_warnings => true) do installer = Bundler::Installer.install(Bundler.root, definition, :system => true) installer.post_install_messages.each do |name, message| Bundler.ui.info "Post-install message from #{name}:\n#{message}" diff --git a/lib/bundler/plugin.rb b/lib/bundler/plugin.rb index ffb3ee9883..f4dd435df4 100644 --- a/lib/bundler/plugin.rb +++ b/lib/bundler/plugin.rb @@ -4,11 +4,11 @@ require_relative "plugin/api" module Bundler module Plugin - autoload :DSL, "bundler/plugin/dsl" - autoload :Events, "bundler/plugin/events" - autoload :Index, "bundler/plugin/index" - autoload :Installer, "bundler/plugin/installer" - autoload :SourceList, "bundler/plugin/source_list" + autoload :DSL, File.expand_path("plugin/dsl", __dir__) + autoload :Events, File.expand_path("plugin/events", __dir__) + autoload :Index, File.expand_path("plugin/index", __dir__) + autoload :Installer, File.expand_path("plugin/installer", __dir__) + autoload :SourceList, File.expand_path("plugin/source_list", __dir__) class MalformattedPlugin < PluginError; end class UndefinedCommandError < PluginError; end diff --git a/lib/bundler/settings.rb b/lib/bundler/settings.rb index 166e494f0e..2074070e3e 100644 --- a/lib/bundler/settings.rb +++ b/lib/bundler/settings.rb @@ -24,6 +24,7 @@ module Bundler disable_exec_load disable_local_branch_check disable_multisource + disable_platform_warnings disable_shared_gems disable_version_check force_ruby_platform diff --git a/lib/bundler/shared_helpers.rb b/lib/bundler/shared_helpers.rb index af1836009f..e6e2b79344 100644 --- a/lib/bundler/shared_helpers.rb +++ b/lib/bundler/shared_helpers.rb @@ -268,7 +268,7 @@ module Bundler until !File.directory?(current) || current == previous if ENV["BUNDLE_SPEC_RUN"] # avoid stepping above the tmp directory when testing - gemspec = if ENV["BUNDLE_RUBY"] && ENV["BUNDLE_GEM"] + gemspec = if ENV["GEM_COMMAND"] # for Ruby Core "lib/bundler/bundler.gemspec" else @@ -304,7 +304,7 @@ module Bundler exe_file = File.expand_path("../../../exe/bundle", __FILE__) # for Ruby core repository testing - exe_file = File.expand_path("../../../bin/bundle", __FILE__) unless File.exist?(exe_file) + exe_file = File.expand_path("../../../libexec/bundle", __FILE__) unless File.exist?(exe_file) # bundler is a default gem, exe path is separate exe_file = Bundler.rubygems.bin_path("bundler", "bundle", VERSION) unless File.exist?(exe_file) diff --git a/lib/bundler/similarity_detector.rb b/lib/bundler/similarity_detector.rb index f698f46a4c..bd9971f884 100644 --- a/lib/bundler/similarity_detector.rb +++ b/lib/bundler/similarity_detector.rb @@ -28,7 +28,7 @@ module Bundler protected - # http://www.informit.com/articles/article.aspx?p=683059&seqNum=36 + # https://www.informit.com/articles/article.aspx?p=683059&seqNum=36 def levenshtein_distance(this, that, ins = 2, del = 2, sub = 1) # ins, del, sub are weighted costs return nil if this.nil? diff --git a/lib/bundler/source/git/git_proxy.rb b/lib/bundler/source/git/git_proxy.rb index c383c5ecbb..1f6dc5d8f9 100644 --- a/lib/bundler/source/git/git_proxy.rb +++ b/lib/bundler/source/git/git_proxy.rb @@ -19,7 +19,7 @@ module Bundler def initialize(command) msg = String.new msg << "Bundler is trying to run a `git #{command}` at runtime. You probably need to run `bundle install`. However, " - msg << "this error message could probably be more useful. Please submit a ticket at http://github.com/bundler/bundler/issues " + msg << "this error message could probably be more useful. Please submit a ticket at https://github.com/bundler/bundler/issues " msg << "with steps to reproduce as well as the following\n\nCALLER: #{caller.join("\n")}" super msg end diff --git a/lib/bundler/spec_set.rb b/lib/bundler/spec_set.rb index 2c5d9e6580..463113ef8e 100644 --- a/lib/bundler/spec_set.rb +++ b/lib/bundler/spec_set.rb @@ -162,11 +162,7 @@ module Bundler end def extract_circular_gems(error) - if Bundler.current_ruby.mri? && Bundler.current_ruby.on_19? - error.message.scan(/(\w+) \([^)]/).flatten - else - error.message.scan(/@name="(.*?)"/).flatten - end + error.message.scan(/@name="(.*?)"/).flatten end def lookup diff --git a/lib/bundler/templates/newgem/CODE_OF_CONDUCT.md.tt b/lib/bundler/templates/newgem/CODE_OF_CONDUCT.md.tt index a3833d29d7..7dfd14aab9 100644 --- a/lib/bundler/templates/newgem/CODE_OF_CONDUCT.md.tt +++ b/lib/bundler/templates/newgem/CODE_OF_CONDUCT.md.tt @@ -68,7 +68,7 @@ members of the project's leadership. ## Attribution This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4, -available at [http://contributor-covenant.org/version/1/4][version] +available at [https://contributor-covenant.org/version/1/4][version] -[homepage]: http://contributor-covenant.org -[version]: http://contributor-covenant.org/version/1/4/ +[homepage]: https://contributor-covenant.org +[version]: https://contributor-covenant.org/version/1/4/ diff --git a/lib/bundler/vendor/net-http-persistent/lib/net/http/persistent.rb b/lib/bundler/vendor/net-http-persistent/lib/net/http/persistent.rb index f3382465a7..327cb0f8c2 100644 --- a/lib/bundler/vendor/net-http-persistent/lib/net/http/persistent.rb +++ b/lib/bundler/vendor/net-http-persistent/lib/net/http/persistent.rb @@ -1,7 +1,7 @@ require 'net/http' require 'uri' require 'cgi' # for escaping -require 'bundler/vendor/connection_pool/lib/connection_pool' +require_relative '../../../../connection_pool/lib/connection_pool' begin require 'net/http/pipeline' @@ -1197,6 +1197,6 @@ application: end -require 'bundler/vendor/net-http-persistent/lib/net/http/persistent/connection' -require 'bundler/vendor/net-http-persistent/lib/net/http/persistent/pool' +require_relative 'persistent/connection' +require_relative 'persistent/pool' diff --git a/lib/bundler/vendor/net-http-persistent/lib/net/http/persistent/pool.rb b/lib/bundler/vendor/net-http-persistent/lib/net/http/persistent/pool.rb index fb1816de83..9dfa6ffdb1 100644 --- a/lib/bundler/vendor/net-http-persistent/lib/net/http/persistent/pool.rb +++ b/lib/bundler/vendor/net-http-persistent/lib/net/http/persistent/pool.rb @@ -49,5 +49,5 @@ class Bundler::Persistent::Net::HTTP::Persistent::Pool < Bundler::ConnectionPool end end -require 'bundler/vendor/net-http-persistent/lib/net/http/persistent/timed_stack_multi' +require_relative 'timed_stack_multi' diff --git a/lib/bundler/vendored_fileutils.rb b/lib/bundler/vendored_fileutils.rb index 4b71759224..1be1138ce2 100644 --- a/lib/bundler/vendored_fileutils.rb +++ b/lib/bundler/vendored_fileutils.rb @@ -1,9 +1,4 @@ # frozen_string_literal: true module Bundler; end -if RUBY_VERSION >= "2.4" - require_relative "vendor/fileutils/lib/fileutils" -else - # the version we vendor is 2.4+ - require "fileutils" -end +require_relative "vendor/fileutils/lib/fileutils" diff --git a/man/bundle-config.1 b/man/bundle-config.1 index c415763cbc..eda7379359 100644 --- a/man/bundle-config.1 +++ b/man/bundle-config.1 @@ -187,6 +187,9 @@ The following is a list of all configuration keys and their purpose\. You can le \fBdisable_multisource\fR (\fBBUNDLE_DISABLE_MULTISOURCE\fR): When set, Gemfiles containing multiple sources will produce errors instead of warnings\. Use \fBbundle config unset disable_multisource\fR to unset\. . .IP "\(bu" 4 +\fBdisable_platform_warnings\fR (\fBBUNDLE_DISABLE_PLATFORM_WARNINGS\fR): Disable warnings during bundle install when a dependency is unused on the current platform\. +. +.IP "\(bu" 4 \fBdisable_shared_gems\fR (\fBBUNDLE_DISABLE_SHARED_GEMS\fR): Stop Bundler from accessing gems installed to RubyGems\' normal location\. . .IP "\(bu" 4 diff --git a/man/bundle-config.1.txt b/man/bundle-config.1.txt index 66a953b949..e4570be7a9 100644 --- a/man/bundle-config.1.txt +++ b/man/bundle-config.1.txt @@ -213,6 +213,10 @@ LIST OF AVAILABLE KEYS files containing multiple sources will produce errors instead of warnings. Use bundle config unset disable_multisource to unset. + o disable_platform_warnings (BUNDLE_DISABLE_PLATFORM_WARNINGS): Dis- + able warnings during bundle install when a dependency is unused on + the current platform. + o disable_shared_gems (BUNDLE_DISABLE_SHARED_GEMS): Stop Bundler from accessing gems installed to RubyGems' normal location. diff --git a/man/bundle-config.ronn b/man/bundle-config.ronn index 069f3b95fd..75b389e7e3 100644 --- a/man/bundle-config.ronn +++ b/man/bundle-config.ronn @@ -179,6 +179,8 @@ learn more about their operation in [bundle install(1)](bundle-install.1.html). When set, Gemfiles containing multiple sources will produce errors instead of warnings. Use `bundle config unset disable_multisource` to unset. +* `disable_platform_warnings` (`BUNDLE_DISABLE_PLATFORM_WARNINGS`): + Disable warnings during bundle install when a dependency is unused on the current platform. * `disable_shared_gems` (`BUNDLE_DISABLE_SHARED_GEMS`): Stop Bundler from accessing gems installed to RubyGems' normal location. * `disable_version_check` (`BUNDLE_DISABLE_VERSION_CHECK`): diff --git a/spec/bundler/build_metadata_spec.rb b/spec/bundler/build_metadata_spec.rb index a28e25511a..afa2d1716f 100644 --- a/spec/bundler/build_metadata_spec.rb +++ b/spec/bundler/build_metadata_spec.rb @@ -4,9 +4,14 @@ require "bundler" require "bundler/build_metadata" RSpec.describe Bundler::BuildMetadata do + before do + allow(Time).to receive(:now).and_return(Time.at(0)) + Bundler::BuildMetadata.instance_variable_set(:@built_at, nil) + end + describe "#built_at" do it "returns %Y-%m-%d formatted time" do - expect(Bundler::BuildMetadata.built_at).to eq Time.now.strftime("%Y-%m-%d") + expect(Bundler::BuildMetadata.built_at).to eq "1970-01-01" end end @@ -36,7 +41,7 @@ RSpec.describe Bundler::BuildMetadata do subject { Bundler::BuildMetadata.to_h } it "returns a hash includes Built At, Git SHA and Released Version" do - expect(subject["Built At"]).to eq Time.now.strftime("%Y-%m-%d") + expect(subject["Built At"]).to eq "1970-01-01" expect(subject["Git SHA"]).to be_instance_of(String) expect(subject["Released Version"]).to be_falsey end diff --git a/spec/bundler/bundler_spec.rb b/spec/bundler/bundler_spec.rb index 8a4ce729ed..74cf7ae05d 100644 --- a/spec/bundler/bundler_spec.rb +++ b/spec/bundler/bundler_spec.rb @@ -176,12 +176,12 @@ RSpec.describe Bundler do let(:bundler_ui) { Bundler.ui } it "should raise a friendly error" do allow(File).to receive(:exist?).and_return(true) - allow(bundler_fileutils).to receive(:remove_entry_secure).and_raise(ArgumentError) + allow(::Bundler::FileUtils).to receive(:remove_entry_secure).and_raise(ArgumentError) allow(File).to receive(:world_writable?).and_return(true) message = <<EOF It is a security vulnerability to allow your home directory to be world-writable, and bundler can not continue. You should probably consider fixing this issue by running `chmod o-w ~` on *nix. -Please refer to http://ruby-doc.org/stdlib-2.1.2/libdoc/fileutils/rdoc/FileUtils.html#method-c-remove_entry_secure for details. +Please refer to https://ruby-doc.org/stdlib-2.1.2/libdoc/fileutils/rdoc/FileUtils.html#method-c-remove_entry_secure for details. EOF expect(bundler_ui).to receive(:warn).with(message) expect { Bundler.send(:rm_rf, bundled_app) }.to raise_error(Bundler::PathError) diff --git a/spec/bundler/cli_spec.rb b/spec/bundler/cli_spec.rb index 79b0cdb737..02e5155733 100644 --- a/spec/bundler/cli_spec.rb +++ b/spec/bundler/cli_spec.rb @@ -15,7 +15,7 @@ RSpec.describe "bundle executable" do it "looks for a binary and executes it if it's named bundler-<task>" do File.open(tmp("bundler-testtasks"), "w", 0o755) do |f| - ruby = ENV["BUNDLE_RUBY"] || "/usr/bin/env ruby" + ruby = ENV["RUBY"] || "/usr/bin/env ruby" f.puts "#!#{ruby}\nputs 'Hello, world'\n" end diff --git a/spec/bundler/dsl_spec.rb b/spec/bundler/dsl_spec.rb index 2102086794..40739a431b 100644 --- a/spec/bundler/dsl_spec.rb +++ b/spec/bundler/dsl_spec.rb @@ -275,7 +275,7 @@ RSpec.describe Bundler::Dsl do end end - describe "Runtime errors", :unless => Bundler.current_ruby.on_18? do + describe "Runtime errors" do it "will raise a Bundler::GemfileError" do gemfile "raise RuntimeError, 'foo'" expect { Bundler::Dsl.evaluate(bundled_app("Gemfile"), nil, true) }. diff --git a/spec/bundler/env_spec.rb b/spec/bundler/env_spec.rb index 4b9efd85d6..f0ab5d5f35 100644 --- a/spec/bundler/env_spec.rb +++ b/spec/bundler/env_spec.rb @@ -190,11 +190,11 @@ RSpec.describe Bundler::Env do end end - describe ".version_of", :ruby_repo do + describe ".version_of" do let(:parsed_version) { described_class.send(:version_of, "ruby") } it "strips version of new line characters" do - expect(parsed_version).to_not include("\n") + expect(parsed_version).to_not end_with("\n") end end end diff --git a/spec/bundler/gem_helper_spec.rb b/spec/bundler/gem_helper_spec.rb index a21fd4c835..c01d65d5dd 100644 --- a/spec/bundler/gem_helper_spec.rb +++ b/spec/bundler/gem_helper_spec.rb @@ -50,7 +50,7 @@ RSpec.describe Bundler::GemHelper do end end - context "gem management", :ruby_repo do + context "gem management" do def mock_confirm_message(message) expect(Bundler.ui).to receive(:confirm).with(message) end diff --git a/spec/bundler/mirror_spec.rb b/spec/bundler/mirror_spec.rb index fb476b8465..76b697c4d2 100644 --- a/spec/bundler/mirror_spec.rb +++ b/spec/bundler/mirror_spec.rb @@ -304,7 +304,7 @@ RSpec.describe Bundler::Settings::TCPSocketProbe do server.close unless server.closed? end - it "probes the server correctly", :ruby_repo do + it "probes the server correctly" do with_server_and_mirror do |server, mirror| expect(server.closed?).to be_falsey expect(probe.replies?(mirror)).to be_truthy diff --git a/spec/bundler/settings_spec.rb b/spec/bundler/settings_spec.rb index 339428eb48..7e1dadded7 100644 --- a/spec/bundler/settings_spec.rb +++ b/spec/bundler/settings_spec.rb @@ -120,7 +120,7 @@ that would suck --ehhh=oh geez it looks like i might have broken bundler somehow context "when it's not possible to write to the file" do it "raises an PermissionError with explanation" do - expect(bundler_fileutils).to receive(:mkdir_p).with(settings.send(:local_config_file).dirname). + expect(::Bundler::FileUtils).to receive(:mkdir_p).with(settings.send(:local_config_file).dirname). and_raise(Errno::EACCES) expect { settings.set_local :frozen, "1" }. to raise_error(Bundler::PermissionError, /config/) @@ -161,7 +161,7 @@ that would suck --ehhh=oh geez it looks like i might have broken bundler somehow describe "#set_global" do context "when it's not possible to write to the file" do it "raises an PermissionError with explanation" do - expect(bundler_fileutils).to receive(:mkdir_p).with(settings.send(:global_config_file).dirname). + expect(::Bundler::FileUtils).to receive(:mkdir_p).with(settings.send(:global_config_file).dirname). and_raise(Errno::EACCES) expect { settings.set_global(:frozen, "1") }. to raise_error(Bundler::PermissionError, %r{\.bundle/config}) diff --git a/spec/bundler/shared_helpers_spec.rb b/spec/bundler/shared_helpers_spec.rb index 910854fe46..0340cb7bae 100644 --- a/spec/bundler/shared_helpers_spec.rb +++ b/spec/bundler/shared_helpers_spec.rb @@ -223,14 +223,6 @@ RSpec.describe Bundler::SharedHelpers do ENV["BUNDLE_GEMFILE"] = "Gemfile" end - let(:setup_path) do - if ruby_core? - File.expand_path("../../../lib/bundler/setup", __dir__) - else - File.expand_path("../../lib/bundler/setup", __dir__) - end - end - shared_examples_for "ENV['PATH'] gets set correctly" do before { Dir.mkdir ".bundle" } @@ -244,7 +236,7 @@ RSpec.describe Bundler::SharedHelpers do shared_examples_for "ENV['RUBYOPT'] gets set correctly" do it "ensures -rbundler/setup is at the beginning of ENV['RUBYOPT']" do subject.set_bundle_environment - expect(ENV["RUBYOPT"].split(" ")).to start_with("-r#{setup_path}") + expect(ENV["RUBYOPT"].split(" ")).to start_with("-r#{lib}/bundler/setup") end end @@ -402,9 +394,8 @@ RSpec.describe Bundler::SharedHelpers do it "sets BUNDLE_BIN_PATH to the bundle executable file" do subject.set_bundle_environment - bundle_exe = ruby_core? ? "../../../../bin/bundle" : "../../../exe/bundle" bin_path = ENV["BUNDLE_BIN_PATH"] - expect(bin_path).to eq(File.expand_path(bundle_exe, __FILE__)) + expect(bin_path).to eq(bindir.join("bundle").to_s) expect(File.exist?(bin_path)).to be true end end diff --git a/spec/bundler/source_spec.rb b/spec/bundler/source_spec.rb index 46d86937da..5b11503d23 100644 --- a/spec/bundler/source_spec.rb +++ b/spec/bundler/source_spec.rb @@ -57,7 +57,10 @@ RSpec.describe Bundler::Source do let(:locked_gem) { double(:locked_gem, :name => "nokogiri", :version => "< 1.5") } context "with color", :no_color_tty do - before { Bundler.ui = Bundler::UI::Shell.new } + before do + allow($stdout).to receive(:tty?).and_return(true) + Bundler.ui = Bundler::UI::Shell.new + end it "should return a string with the spec name and version and locked spec version" do expect(subject.version_message(spec)).to eq("nokogiri >= 1.6\e[32m (was < 1.5)\e[0m") @@ -78,7 +81,10 @@ RSpec.describe Bundler::Source do let(:locked_gem) { double(:locked_gem, :name => "nokogiri", :version => "1.7.0") } context "with color", :no_color_tty do - before { Bundler.ui = Bundler::UI::Shell.new } + before do + allow($stdout).to receive(:tty?).and_return(true) + Bundler.ui = Bundler::UI::Shell.new + end it "should return a string with the locked spec version in yellow" do expect(subject.version_message(spec)).to eq("nokogiri 1.6.1\e[33m (was 1.7.0)\e[0m") @@ -99,7 +105,10 @@ RSpec.describe Bundler::Source do let(:locked_gem) { double(:locked_gem, :name => "nokogiri", :version => "1.7.0") } context "with color", :no_color_tty do - before { Bundler.ui = Bundler::UI::Shell.new } + before do + allow($stdout).to receive(:tty?).and_return(true) + Bundler.ui = Bundler::UI::Shell.new + end it "should return a string with the locked spec version in green" do expect(subject.version_message(spec)).to eq("nokogiri 1.7.1\e[32m (was 1.7.0)\e[0m") diff --git a/spec/commands/clean_spec.rb b/spec/commands/clean_spec.rb index 2243a72b3d..3ef7e809e8 100644 --- a/spec/commands/clean_spec.rb +++ b/spec/commands/clean_spec.rb @@ -361,8 +361,7 @@ RSpec.describe "bundle clean" do gem "rack" G - gem = ruby_core? ? ENV["BUNDLE_GEM"] : "gem" - sys_exec! "#{gem} list" + gem_command! :list expect(out).to include("rack (1.0.0)").and include("thin (1.0)") end @@ -484,8 +483,7 @@ RSpec.describe "bundle clean" do end bundle! :update, :all => true - gem = ruby_core? ? ENV["BUNDLE_GEM"] : "gem" - sys_exec! "#{gem} list" + gem_command! :list expect(out).to include("foo (1.0.1, 1.0)") end @@ -509,8 +507,7 @@ RSpec.describe "bundle clean" do bundle "clean --force" expect(out).to include("Removing foo (1.0)") - gem = ruby_core? ? ENV["BUNDLE_GEM"] : "gem" - sys_exec "#{gem} list" + gem_command! :list expect(out).not_to include("foo (1.0)") expect(out).to include("rack (1.0.0)") end @@ -544,8 +541,7 @@ RSpec.describe "bundle clean" do expect(err).to include(system_gem_path.to_s) expect(err).to include("grant write permissions") - gem = ruby_core? ? ENV["BUNDLE_GEM"] : "gem" - sys_exec "#{gem} list" + gem_command! :list expect(out).to include("foo (1.0)") expect(out).to include("rack (1.0.0)") end @@ -605,7 +601,7 @@ RSpec.describe "bundle clean" do expect(out).to eq("1.0") end - it "doesn't blow up on path gems without a .gempsec" do + it "doesn't blow up on path gems without a .gemspec" do relative_path = "vendor/private_gems/bar-1.0" absolute_path = bundled_app(relative_path) FileUtils.mkdir_p("#{absolute_path}/lib/bar") diff --git a/spec/commands/config_spec.rb b/spec/commands/config_spec.rb index c0ef3bb70c..ef580463e5 100644 --- a/spec/commands/config_spec.rb +++ b/spec/commands/config_spec.rb @@ -389,7 +389,7 @@ E end describe "subcommands" do - it "list", :ruby_repo do + it "list" do bundle! "config list" expect(out).to eq "Settings are listed in order of priority. The top value will be used.\nspec_run\nSet via BUNDLE_SPEC_RUN: \"true\"" diff --git a/spec/commands/doctor_spec.rb b/spec/commands/doctor_spec.rb index 4198678baa..d829f00092 100644 --- a/spec/commands/doctor_spec.rb +++ b/spec/commands/doctor_spec.rb @@ -22,11 +22,17 @@ RSpec.describe "bundle doctor" do end end + it "succeeds on a sane installation" do + bundle :doctor + + expect(exitstatus).to eq(0) + end + context "when all files in home are readable/writable" do before(:each) do stat = double("stat") unwritable_file = double("file") - allow(Find).to receive(:find).with(Bundler.home.to_s) { [unwritable_file] } + allow(Find).to receive(:find).with(Bundler.bundle_path.to_s) { [unwritable_file] } allow(File).to receive(:stat).with(unwritable_file) { stat } allow(stat).to receive(:uid) { Process.uid } allow(File).to receive(:writable?).with(unwritable_file) { true } @@ -66,7 +72,7 @@ RSpec.describe "bundle doctor" do before(:each) do @stat = double("stat") @unwritable_file = double("file") - allow(Find).to receive(:find).with(Bundler.home.to_s) { [@unwritable_file] } + allow(Find).to receive(:find).with(Bundler.bundle_path.to_s) { [@unwritable_file] } allow(File).to receive(:stat).with(@unwritable_file) { @stat } end diff --git a/spec/commands/exec_spec.rb b/spec/commands/exec_spec.rb index bb13b1b086..a36b303060 100644 --- a/spec/commands/exec_spec.rb +++ b/spec/commands/exec_spec.rb @@ -33,7 +33,7 @@ RSpec.describe "bundle exec" do expect(out).to eq("1.0.0") end - it "works when running from a random directory", :ruby_repo do + it "works when running from a random directory" do install_gemfile <<-G gem "rack" G @@ -56,14 +56,14 @@ RSpec.describe "bundle exec" do end it "respects custom process title when loading through ruby", :github_action_linux do - script_that_changes_its_own_title_and_checks_if_picked_up_by_ps_unix_utility = <<~RUBY - Process.setproctitle("1-2-3-4-5-6-7-8-9-10-11-12-13-14-15-16") - puts `ps -eo args | grep [1]-2-3-4-5-6-7-8-9-10-11-12-13-14-15-16` + script_that_changes_its_own_title_and_checks_if_picked_up_by_ps_unix_utility = <<~'RUBY' + Process.setproctitle("1-2-3-4-5-6-7-8-9-10-11-12-13-14-15") + puts `ps -ocommand= -p#{$$}` RUBY create_file "Gemfile" create_file "a.rb", script_that_changes_its_own_title_and_checks_if_picked_up_by_ps_unix_utility bundle "exec ruby a.rb" - expect(out).to eq("1-2-3-4-5-6-7-8-9-10-11-12-13-14-15-16") + expect(out).to eq("1-2-3-4-5-6-7-8-9-10-11-12-13-14-15") end it "accepts --verbose" do @@ -192,7 +192,7 @@ RSpec.describe "bundle exec" do it "uses version specified" do bundle! "exec irb --version" - expect(out).to include(specified_irb_version) + expect(out).to eq(specified_irb_version) expect(err).to be_empty end end @@ -222,7 +222,7 @@ RSpec.describe "bundle exec" do end it "uses resolved version" do - expect(out).to include(indirect_irb_version) + expect(out).to eq(indirect_irb_version) expect(err).to be_empty end end @@ -279,12 +279,7 @@ RSpec.describe "bundle exec" do G rubyopt = ENV["RUBYOPT"] - setup_path = if ruby_core? - File.expand_path("../../../lib/bundler/setup", __dir__) - else - File.expand_path("../../lib/bundler/setup", __dir__) - end - rubyopt = "-r#{setup_path} #{rubyopt}" + rubyopt = "-r#{lib}/bundler/setup #{rubyopt}" bundle "exec 'echo $RUBYOPT'" expect(out).to have_rubyopts(rubyopt) @@ -299,7 +294,7 @@ RSpec.describe "bundle exec" do G rubylib = ENV["RUBYLIB"] - rubylib = rubylib.to_s.split(File::PATH_SEPARATOR).unshift bundler_path.to_s + rubylib = rubylib.to_s.split(File::PATH_SEPARATOR).unshift lib.to_s rubylib = rubylib.uniq.join(File::PATH_SEPARATOR) bundle "exec 'echo $RUBYLIB'" @@ -341,7 +336,7 @@ RSpec.describe "bundle exec" do expect(err).to include("bundler: exec needs a command to run") end - it "raises a helpful error when exec'ing to something outside of the bundle", :ruby_repo do + it "raises a helpful error when exec'ing to something outside of the bundle" do bundle! "config set clean false" # want to keep the rackup binstub install_gemfile! <<-G source "#{file_uri_for(gem_repo1)}" @@ -693,7 +688,7 @@ RSpec.describe "bundle exec" do it_behaves_like "it runs" end - context "when the file uses the current ruby shebang", :ruby_repo do + context "when the file uses the current ruby shebang" do let(:shebang) { "#!#{Gem.ruby}" } it_behaves_like "it runs" end @@ -842,14 +837,12 @@ __FILE__: #{path.to_s.inspect} context "nested bundle exec" do context "when bundle in a local path" do before do - system_gems :bundler - gemfile <<-G source "#{file_uri_for(gem_repo1)}" gem "rack" G - bundle "config path vendor/bundler" - bundle! :install, :system_bundler => true + bundle "config set path vendor/bundler" + bundle! :install end it "correctly shells out", :ruby_repo do @@ -859,7 +852,7 @@ __FILE__: #{path.to_s.inspect} puts `bundle exec echo foo` RB file.chmod(0o777) - bundle! "exec #{file}", :system_bundler => true + bundle! "exec #{file}" expect(out).to eq("foo") end end diff --git a/spec/commands/info_spec.rb b/spec/commands/info_spec.rb index aa6b237d50..4572823498 100644 --- a/spec/commands/info_spec.rb +++ b/spec/commands/info_spec.rb @@ -116,7 +116,7 @@ RSpec.describe "bundle info" do end end - context "with a valid regexp for gem name", :ruby_repo do + context "with a valid regexp for gem name" do it "presents alternatives" do install_gemfile <<-G source "#{file_uri_for(gem_repo1)}" diff --git a/spec/commands/install_spec.rb b/spec/commands/install_spec.rb index e279d71827..8e161a4aae 100644 --- a/spec/commands/install_spec.rb +++ b/spec/commands/install_spec.rb @@ -330,7 +330,7 @@ RSpec.describe "bundle install with gem sources" do G expect(err).to include("Your Gemfile lists the gem rack (>= 0) more than once.") - expect(err).to include("Remove any duplicate entries and specify the gem only once (per group).") + expect(err).to include("Remove any duplicate entries and specify the gem only once.") expect(err).to include("While it's not a problem now, it could cause errors if you change the version of one of them later.") end @@ -342,7 +342,7 @@ RSpec.describe "bundle install with gem sources" do G expect(err).to include("Your Gemfile lists the gem rack (= 1.0) more than once.") - expect(err).to include("Remove any duplicate entries and specify the gem only once (per group).") + expect(err).to include("Remove any duplicate entries and specify the gem only once.") expect(err).to include("While it's not a problem now, it could cause errors if you change the version of one of them later.") end end diff --git a/spec/commands/newgem_spec.rb b/spec/commands/newgem_spec.rb index f4cd29edbc..32c1868cd2 100644 --- a/spec/commands/newgem_spec.rb +++ b/spec/commands/newgem_spec.rb @@ -210,16 +210,14 @@ RSpec.describe "bundle gem" do end end - it "generates a valid gemspec", :ruby_repo do + it "generates a valid gemspec" do in_app_root bundle! "gem newgem --bin" prepare_gemspec(bundled_app("newgem", "newgem.gemspec")) Dir.chdir(bundled_app("newgem")) do - gems = ["rake-12.3.2", :bundler] - # for Ruby core repository, Ruby 2.6+ has bundler as standard library. - gems.delete(:bundler) if ruby_core? + gems = ["rake-12.3.2"] system_gems gems, :path => :bundle_path bundle! "exec rake build" end @@ -311,8 +309,7 @@ RSpec.describe "bundle gem" do end it "sets a minimum ruby version" do - gemspec_path = ruby_core? ? "../../../lib/bundler" : "../.." - bundler_gemspec = Bundler::GemHelper.new(File.expand_path(gemspec_path, __dir__)).gemspec + bundler_gemspec = Bundler::GemHelper.new(gemspec_dir).gemspec expect(bundler_gemspec.required_ruby_version).to eq(generated_gemspec.required_ruby_version) end diff --git a/spec/commands/open_spec.rb b/spec/commands/open_spec.rb index 6eb6262a2b..8fae4af5b4 100644 --- a/spec/commands/open_spec.rb +++ b/spec/commands/open_spec.rb @@ -1,92 +1,117 @@ # frozen_string_literal: true RSpec.describe "bundle open" do - before :each do - install_gemfile <<-G - source "#{file_uri_for(gem_repo1)}" - gem "rails" - G - end + context "when opening a regular gem" do + before do + install_gemfile <<-G + source "#{file_uri_for(gem_repo1)}" + gem "rails" + G + end - it "opens the gem with BUNDLER_EDITOR as highest priority" do - bundle "open rails", :env => { "EDITOR" => "echo editor", "VISUAL" => "echo visual", "BUNDLER_EDITOR" => "echo bundler_editor" } - expect(out).to include("bundler_editor #{default_bundle_path("gems", "rails-2.3.2")}") - end + it "opens the gem with BUNDLER_EDITOR as highest priority" do + bundle "open rails", :env => { "EDITOR" => "echo editor", "VISUAL" => "echo visual", "BUNDLER_EDITOR" => "echo bundler_editor" } + expect(out).to include("bundler_editor #{default_bundle_path("gems", "rails-2.3.2")}") + end - it "opens the gem with VISUAL as 2nd highest priority" do - bundle "open rails", :env => { "EDITOR" => "echo editor", "VISUAL" => "echo visual", "BUNDLER_EDITOR" => "" } - expect(out).to include("visual #{default_bundle_path("gems", "rails-2.3.2")}") - end + it "opens the gem with VISUAL as 2nd highest priority" do + bundle "open rails", :env => { "EDITOR" => "echo editor", "VISUAL" => "echo visual", "BUNDLER_EDITOR" => "" } + expect(out).to include("visual #{default_bundle_path("gems", "rails-2.3.2")}") + end - it "opens the gem with EDITOR as 3rd highest priority" do - bundle "open rails", :env => { "EDITOR" => "echo editor", "VISUAL" => "", "BUNDLER_EDITOR" => "" } - expect(out).to include("editor #{default_bundle_path("gems", "rails-2.3.2")}") - end + it "opens the gem with EDITOR as 3rd highest priority" do + bundle "open rails", :env => { "EDITOR" => "echo editor", "VISUAL" => "", "BUNDLER_EDITOR" => "" } + expect(out).to include("editor #{default_bundle_path("gems", "rails-2.3.2")}") + end - it "complains if no EDITOR is set" do - bundle "open rails", :env => { "EDITOR" => "", "VISUAL" => "", "BUNDLER_EDITOR" => "" } - expect(out).to eq("To open a bundled gem, set $EDITOR or $BUNDLER_EDITOR") - end + it "complains if no EDITOR is set" do + bundle "open rails", :env => { "EDITOR" => "", "VISUAL" => "", "BUNDLER_EDITOR" => "" } + expect(out).to eq("To open a bundled gem, set $EDITOR or $BUNDLER_EDITOR") + end - it "complains if gem not in bundle" do - bundle "open missing", :env => { "EDITOR" => "echo editor", "VISUAL" => "", "BUNDLER_EDITOR" => "" } - expect(err).to match(/could not find gem 'missing'/i) - end + it "complains if gem not in bundle" do + bundle "open missing", :env => { "EDITOR" => "echo editor", "VISUAL" => "", "BUNDLER_EDITOR" => "" } + expect(err).to match(/could not find gem 'missing'/i) + end - it "does not blow up if the gem to open does not have a Gemfile" do - git = build_git "foo" - ref = git.ref_for("master", 11) + it "does not blow up if the gem to open does not have a Gemfile" do + git = build_git "foo" + ref = git.ref_for("master", 11) - install_gemfile <<-G - source "#{file_uri_for(gem_repo1)}" - gem 'foo', :git => "#{lib_path("foo-1.0")}" - G + install_gemfile <<-G + source "#{file_uri_for(gem_repo1)}" + gem 'foo', :git => "#{lib_path("foo-1.0")}" + G - bundle "open foo", :env => { "EDITOR" => "echo editor", "VISUAL" => "", "BUNDLER_EDITOR" => "" } - expect(out).to match("editor #{default_bundle_path.join("bundler/gems/foo-1.0-#{ref}")}") - end + bundle "open foo", :env => { "EDITOR" => "echo editor", "VISUAL" => "", "BUNDLER_EDITOR" => "" } + expect(out).to match("editor #{default_bundle_path.join("bundler/gems/foo-1.0-#{ref}")}") + end - it "suggests alternatives for similar-sounding gems" do - bundle "open Rails", :env => { "EDITOR" => "echo editor", "VISUAL" => "", "BUNDLER_EDITOR" => "" } - expect(err).to match(/did you mean rails\?/i) - end + it "suggests alternatives for similar-sounding gems" do + bundle "open Rails", :env => { "EDITOR" => "echo editor", "VISUAL" => "", "BUNDLER_EDITOR" => "" } + expect(err).to match(/did you mean rails\?/i) + end - it "opens the gem with short words" do - bundle "open rec", :env => { "EDITOR" => "echo editor", "VISUAL" => "echo visual", "BUNDLER_EDITOR" => "echo bundler_editor" } + it "opens the gem with short words" do + bundle "open rec", :env => { "EDITOR" => "echo editor", "VISUAL" => "echo visual", "BUNDLER_EDITOR" => "echo bundler_editor" } - expect(out).to include("bundler_editor #{default_bundle_path("gems", "activerecord-2.3.2")}") - end + expect(out).to include("bundler_editor #{default_bundle_path("gems", "activerecord-2.3.2")}") + end + + it "select the gem from many match gems" do + env = { "EDITOR" => "echo editor", "VISUAL" => "echo visual", "BUNDLER_EDITOR" => "echo bundler_editor" } + bundle "open active", :env => env do |input, _, _| + input.puts "2" + end - it "select the gem from many match gems" do - env = { "EDITOR" => "echo editor", "VISUAL" => "echo visual", "BUNDLER_EDITOR" => "echo bundler_editor" } - bundle "open active", :env => env do |input, _, _| - input.puts "2" + expect(out).to match(/bundler_editor #{default_bundle_path('gems', 'activerecord-2.3.2')}\z/) end - expect(out).to match(/bundler_editor #{default_bundle_path('gems', 'activerecord-2.3.2')}\z/) - end + it "allows selecting exit from many match gems" do + env = { "EDITOR" => "echo editor", "VISUAL" => "echo visual", "BUNDLER_EDITOR" => "echo bundler_editor" } + bundle! "open active", :env => env do |input, _, _| + input.puts "0" + end + end + + it "performs an automatic bundle install" do + gemfile <<-G + source "#{file_uri_for(gem_repo1)}" + gem "rails" + gem "foo" + G - it "allows selecting exit from many match gems" do - env = { "EDITOR" => "echo editor", "VISUAL" => "echo visual", "BUNDLER_EDITOR" => "echo bundler_editor" } - bundle! "open active", :env => env do |input, _, _| - input.puts "0" + bundle "config set auto_install 1" + bundle "open rails", :env => { "EDITOR" => "echo editor", "VISUAL" => "", "BUNDLER_EDITOR" => "" } + expect(out).to include("Installing foo 1.0") + end + + it "opens the editor with a clean env" do + bundle "open", :env => { "EDITOR" => "sh -c 'env'", "VISUAL" => "", "BUNDLER_EDITOR" => "" } + expect(out).not_to include("BUNDLE_GEMFILE=") end end - it "performs an automatic bundle install" do - gemfile <<-G - source "#{file_uri_for(gem_repo1)}" - gem "rails" - gem "foo" - G + context "when opening a default gem" do + let(:default_gems) do + ruby!(<<-RUBY).split("\n") + if Gem::Specification.is_a?(Enumerable) + puts Gem::Specification.select(&:default_gem?).map(&:name) + end + RUBY + end - bundle "config set auto_install 1" - bundle "open rails", :env => { "EDITOR" => "echo editor", "VISUAL" => "", "BUNDLER_EDITOR" => "" } - expect(out).to include("Installing foo 1.0") - end + before do + skip "No default gems available on this test run" if default_gems.empty? - it "opens the editor with a clean env" do - bundle "open", :env => { "EDITOR" => "sh -c 'env'", "VISUAL" => "", "BUNDLER_EDITOR" => "" } - expect(out).not_to include("BUNDLE_GEMFILE=") + install_gemfile <<-G + gem "json" + G + end + + it "throws proper error when trying to open default gem" do + bundle "open json", :env => { "EDITOR" => "echo editor", "VISUAL" => "echo visual", "BUNDLER_EDITOR" => "echo bundler_editor" } + expect(out).to include("Unable to open json because it's a default gem, so the directory it would normally be installed to does not exist.") + end end end diff --git a/spec/commands/pristine_spec.rb b/spec/commands/pristine_spec.rb index 252bef6d0d..aa5c2213d1 100644 --- a/spec/commands/pristine_spec.rb +++ b/spec/commands/pristine_spec.rb @@ -42,8 +42,7 @@ RSpec.describe "bundle pristine", :ruby_repo do expect(changes_txt).to_not be_file end - it "does not delete the bundler gem", :rubygems => ">= 2.6.2" do - ENV["BUNDLER_SPEC_KEEP_DEFAULT_BUNDLER_GEM"] = "true" + it "does not delete the bundler gem" do system_gems :bundler bundle! "install" bundle! "pristine", :system_bundler => true diff --git a/spec/commands/show_spec.rb b/spec/commands/show_spec.rb index ce45a961f0..61b8f73e7f 100644 --- a/spec/commands/show_spec.rb +++ b/spec/commands/show_spec.rb @@ -166,7 +166,7 @@ RSpec.describe "bundle show", :bundler => "< 3" do end context "with a valid regexp for gem name" do - it "presents alternatives", :ruby_repo do + it "presents alternatives" do install_gemfile <<-G source "#{file_uri_for(gem_repo1)}" gem "rack" diff --git a/spec/install/gemfile/git_spec.rb b/spec/install/gemfile/git_spec.rb index afcac8b153..7eb05a995c 100644 --- a/spec/install/gemfile/git_spec.rb +++ b/spec/install/gemfile/git_spec.rb @@ -1110,7 +1110,7 @@ RSpec.describe "bundle install with git sources" do end context "with an extension" do - it "installs the extension", :ruby_repo do + it "installs the extension" do build_git "foo" do |s| s.add_dependency "rake" s.extensions << "Rakefile" @@ -1139,7 +1139,7 @@ RSpec.describe "bundle install with git sources" do run! <<-R puts $:.grep(/ext/) R - expect(out).to eq(Pathname.glob(default_bundle_path("bundler/gems/extensions/**/foo-1.0-*")).first.to_s) + expect(out).to include(Pathname.glob(default_bundle_path("bundler/gems/extensions/**/foo-1.0-*")).first.to_s) end it "does not use old extension after ref changes", :ruby_repo do @@ -1204,7 +1204,7 @@ In Gemfile: expect(out).not_to include("gem install foo") end - it "does not reinstall the extension", :ruby_repo do + it "does not reinstall the extension" do build_git "foo" do |s| s.add_dependency "rake" s.extensions << "Rakefile" @@ -1245,7 +1245,7 @@ In Gemfile: expect(out).to eq(installed_time) end - it "does not reinstall the extension when changing another gem", :ruby_repo do + it "does not reinstall the extension when changing another gem" do build_git "foo" do |s| s.add_dependency "rake" s.extensions << "Rakefile" @@ -1288,7 +1288,7 @@ In Gemfile: expect(out).to eq(installed_time) end - it "does reinstall the extension when changing refs", :ruby_repo do + it "does reinstall the extension when changing refs" do build_git "foo" do |s| s.add_dependency "rake" s.extensions << "Rakefile" diff --git a/spec/install/gemfile/groups_spec.rb b/spec/install/gemfile/groups_spec.rb index b38e8b43d5..93798ef62e 100644 --- a/spec/install/gemfile/groups_spec.rb +++ b/spec/install/gemfile/groups_spec.rb @@ -333,7 +333,7 @@ RSpec.describe "bundle install with groups" do G ruby <<-R - require "bundler" + require "#{lib}/bundler" Bundler.setup :default Bundler.require :default puts RACK diff --git a/spec/install/gemfile/platform_spec.rb b/spec/install/gemfile/platform_spec.rb index d065e10600..c096531398 100644 --- a/spec/install/gemfile/platform_spec.rb +++ b/spec/install/gemfile/platform_spec.rb @@ -372,7 +372,7 @@ RSpec.describe "bundle install with platform conditionals" do expect(out).not_to match(/Could not find gem 'some_gem/) end - it "resolves all platforms by default and without warning messages" do + it "prints a helpful warning when a dependency is unused on any platform" do simulate_platform "ruby" simulate_ruby_engine "ruby" @@ -384,27 +384,28 @@ RSpec.describe "bundle install with platform conditionals" do bundle! "install" - expect(err).to be_empty + expect(err).to include <<-O.strip +The dependency #{Gem::Dependency.new("rack", ">= 0")} will be unused by any of the platforms Bundler is installing for. Bundler is installing for ruby but the dependency is only for x86-mingw32, x86-mswin32, x64-mingw32, java. To add those platforms to the bundle, run `bundle lock --add-platform x86-mingw32 x86-mswin32 x64-mingw32 java`. + O + end - lockfile_should_be <<-L - GEM - remote: #{file_uri_for(gem_repo1)}/ - specs: - rack (1.0.0) + context "when disable_platform_warnings is true" do + before { bundle! "config set disable_platform_warnings true" } - PLATFORMS - java - ruby - x64-mingw32 - x86-mingw32 - x86-mswin32 + it "does not print the warning when a dependency is unused on any platform" do + simulate_platform "ruby" + simulate_ruby_engine "ruby" - DEPENDENCIES - rack + gemfile <<-G + source "#{file_uri_for(gem_repo1)}" - BUNDLED WITH - #{Bundler::VERSION} - L + gem "rack", :platform => [:mingw, :mswin, :x64_mingw, :jruby] + G + + bundle! "install" + + expect(out).not_to match(/The dependency (.*) will be unused/) + end end end diff --git a/spec/install/gems/resolving_spec.rb b/spec/install/gems/resolving_spec.rb index f245b7fc29..26ff40f7aa 100644 --- a/spec/install/gems/resolving_spec.rb +++ b/spec/install/gems/resolving_spec.rb @@ -1,7 +1,7 @@ # frozen_string_literal: true RSpec.describe "bundle install with install-time dependencies" do - it "installs gems with implicit rake dependencies", :ruby_repo do + it "installs gems with implicit rake dependencies" do install_gemfile <<-G source "#{file_uri_for(gem_repo1)}" gem "with_implicit_rake_dep" @@ -48,7 +48,7 @@ RSpec.describe "bundle install with install-time dependencies" do expect(the_bundle).to include_gems "net_b 1.0" end - it "installs plugins depended on by other plugins", :ruby_repo do + it "installs plugins depended on by other plugins" do install_gemfile <<-G source "#{file_uri_for(gem_repo1)}" gem "net_a" @@ -57,7 +57,7 @@ RSpec.describe "bundle install with install-time dependencies" do expect(the_bundle).to include_gems "net_a 1.0", "net_b 1.0" end - it "installs multiple levels of dependencies", :ruby_repo do + it "installs multiple levels of dependencies" do install_gemfile <<-G source "#{file_uri_for(gem_repo1)}" gem "net_c" diff --git a/spec/plugins/source/example_spec.rb b/spec/plugins/source/example_spec.rb index 7bc8fb0f29..1ef7c2134d 100644 --- a/spec/plugins/source/example_spec.rb +++ b/spec/plugins/source/example_spec.rb @@ -6,7 +6,6 @@ RSpec.describe "real source plugins" do build_repo2 do build_plugin "bundler-source-mpath" do |s| s.write "plugins.rb", <<-RUBY - require "bundler/vendored_fileutils" require "bundler-source-mpath" class MPath < Bundler::Plugin::API diff --git a/spec/quality_es_spec.rb b/spec/quality_es_spec.rb index 46eed8f18a..4238ac7452 100644 --- a/spec/quality_es_spec.rb +++ b/spec/quality_es_spec.rb @@ -1,10 +1,5 @@ # frozen_string_literal: true -if defined?(Encoding) && Encoding.default_external.name != "UTF-8" - # An approximation of ruby -E UTF-8, since it works on 1.8.7 - Encoding.default_external = Encoding.find("UTF-8") -end - RSpec.describe "La biblioteca si misma" do def check_for_expendable_words(filename) failing_line_message = [] @@ -55,11 +50,11 @@ RSpec.describe "La biblioteca si misma" do expect(error_messages.compact).to be_well_formed end - it "mantiene la calidad de lenguaje de oraciones usadas en el código fuente", :ruby_repo do + it "mantiene la calidad de lenguaje de oraciones usadas en el código fuente" do error_messages = [] exempt = /vendor/ Dir.chdir(root) do - `git ls-files -z -- lib`.split("\x0").each do |filename| + lib_tracked_files.split("\x0").each do |filename| next if filename =~ exempt error_messages << check_for_expendable_words(filename) error_messages << check_for_specific_pronouns(filename) diff --git a/spec/quality_spec.rb b/spec/quality_spec.rb index 7cd04fdc75..09e59d88ae 100644 --- a/spec/quality_spec.rb +++ b/spec/quality_spec.rb @@ -108,8 +108,7 @@ RSpec.describe "The library itself" do exempt = /\.gitmodules|fixtures|vendor|LICENSE|vcr_cassettes|rbreadline\.diff|\.txt$/ error_messages = [] Dir.chdir(root) do - files = ruby_core? ? `git ls-files -z -- lib/bundler lib/bundler.rb spec/bundler` : `git ls-files -z` - files.split("\x0").each do |filename| + tracked_files.split("\x0").each do |filename| next if filename =~ exempt error_messages << check_for_tab_characters(filename) error_messages << check_for_extra_spaces(filename) @@ -122,8 +121,7 @@ RSpec.describe "The library itself" do exempt = /vendor|vcr_cassettes|LICENSE|rbreadline\.diff/ error_messages = [] Dir.chdir(root) do - files = ruby_core? ? `git ls-files -z -- lib/bundler lib/bundler.rb spec/bundler` : `git ls-files -z` - files.split("\x0").each do |filename| + tracked_files.split("\x0").each do |filename| next if filename =~ exempt error_messages << check_for_straneous_quotes(filename) end @@ -135,8 +133,7 @@ RSpec.describe "The library itself" do exempt = %r{quality_spec.rb|support/helpers|vcr_cassettes|\.md|\.ronn|\.txt|\.5|\.1} error_messages = [] Dir.chdir(root) do - files = ruby_core? ? `git ls-files -z -- lib/bundler lib/bundler.rb spec/bundler` : `git ls-files -z` - files.split("\x0").each do |filename| + tracked_files.split("\x0").each do |filename| next if filename =~ exempt error_messages << check_for_debugging_mechanisms(filename) end @@ -148,8 +145,7 @@ RSpec.describe "The library itself" do error_messages = [] exempt = %r{lock/lockfile_spec|quality_spec|vcr_cassettes|\.ronn|lockfile_parser\.rb} Dir.chdir(root) do - files = ruby_core? ? `git ls-files -z -- lib/bundler lib/bundler.rb spec/bundler` : `git ls-files -z` - files.split("\x0").each do |filename| + tracked_files.split("\x0").each do |filename| next if filename =~ exempt error_messages << check_for_git_merge_conflicts(filename) end @@ -174,8 +170,7 @@ RSpec.describe "The library itself" do error_messages = [] exempt = /vendor|vcr_cassettes/ Dir.chdir(root) do - lib_files = ruby_core? ? `git ls-files -z -- lib/bundler lib/bundler.rb` : `git ls-files -z -- lib` - lib_files.split("\x0").each do |filename| + lib_tracked_files.split("\x0").each do |filename| next if filename =~ exempt error_messages << check_for_expendable_words(filename) error_messages << check_for_specific_pronouns(filename) @@ -204,8 +199,7 @@ RSpec.describe "The library itself" do Dir.chdir(root) do key_pattern = /([a-z\._-]+)/i - lib_files = ruby_core? ? `git ls-files -z -- lib/bundler lib/bundler.rb` : `git ls-files -z -- lib` - lib_files.split("\x0").each do |filename| + lib_tracked_files.split("\x0").each do |filename| each_line(filename) do |line, number| line.scan(/Bundler\.settings\[:#{key_pattern}\]/).flatten.each {|s| all_settings[s] << "referenced at `#{filename}:#{number.succ}`" } end @@ -231,30 +225,14 @@ RSpec.describe "The library itself" do end it "can still be built" do - Dir.chdir(root) do - begin - if ruby_core? - spec = Gem::Specification.load(gemspec.to_s) - spec.bindir = "libexec" - File.open(root.join("bundler.gemspec").to_s, "w") {|f| f.write spec.to_ruby } - gem_command! :build, root.join("bundler.gemspec").to_s - FileUtils.rm(root.join("bundler.gemspec").to_s) - else - gem_command! :build, gemspec - end - - expect(err).to be_empty, "bundler should build as a gem without warnings, but\n#{err}" - ensure - # clean up the .gem generated - FileUtils.rm("bundler-#{Bundler::VERSION}.gem") - end + with_built_bundler do |_gem_path| + expect(err).to be_empty, "bundler should build as a gem without warnings, but\n#{err}" end end - it "ships the correct set of files", :ruby_repo do + it "ships the correct set of files" do Dir.chdir(root) do - git_list = IO.popen("git ls-files -z", &:read).split("\x0").select {|f| f.match(%r{^(lib|man|exe)/}) } - git_list += %w[CHANGELOG.md LICENSE.md README.md bundler.gemspec] + git_list = shipped_files.split("\x0") gem_list = Gem::Specification.load(gemspec.to_s).files @@ -271,12 +249,11 @@ RSpec.describe "The library itself" do lib/bundler/vlad.rb lib/bundler/templates/gems.rb ] - lib_files = ruby_core? ? `git ls-files -z -- lib/bundler lib/bundler.rb` : `git ls-files -z -- lib` - lib_files = lib_files.split("\x0").grep(/\.rb$/) - exclusions - lib_files.reject! {|f| f.start_with?("lib/bundler/vendor") } - lib_files.map! {|f| f.chomp(".rb") } + files_to_require = lib_tracked_files.split("\x0").grep(/\.rb$/) - exclusions + files_to_require.reject! {|f| f.start_with?("lib/bundler/vendor") } + files_to_require.map! {|f| f.chomp(".rb") } sys_exec!("ruby -w -Ilib") do |input, _, _| - lib_files.each do |f| + files_to_require.each do |f| input.puts "require '#{f.sub(%r{\Alib/}, "")}'" end end @@ -293,8 +270,7 @@ RSpec.describe "The library itself" do Dir.chdir(root) do exempt = %r{templates/|vendor/} all_bad_requires = [] - lib_files = ruby_core? ? `git ls-files -z -- lib/bundler lib/bundler.rb` : `git ls-files -z -- lib` - lib_files.split("\x0").each do |filename| + lib_tracked_files.split("\x0").each do |filename| next if filename =~ exempt each_line(filename) do |line, number| line.scan(/^ *require "bundler/).each { all_bad_requires << "#{filename}:#{number.succ}" } diff --git a/spec/realworld/double_check_spec.rb b/spec/realworld/double_check_spec.rb index 07593ac493..323e0d5735 100644 --- a/spec/realworld/double_check_spec.rb +++ b/spec/realworld/double_check_spec.rb @@ -25,9 +25,9 @@ RSpec.describe "double checking sources", :realworld => true, :sometimes => true RUBY cmd = <<-RUBY - require "bundler" + require "#{lib}/bundler" require #{File.expand_path("../../support/artifice/vcr.rb", __FILE__).dump} - require "bundler/inline" + require "#{lib}/bundler/inline" gemfile(true) do source "https://rubygems.org" gem "rails", path: "." diff --git a/spec/runtime/gem_tasks_spec.rb b/spec/runtime/gem_tasks_spec.rb index eb9db56ead..af645c8ef1 100644 --- a/spec/runtime/gem_tasks_spec.rb +++ b/spec/runtime/gem_tasks_spec.rb @@ -11,7 +11,7 @@ RSpec.describe "require 'bundler/gem_tasks'" do end bundled_app("Rakefile").open("w") do |f| f.write <<-RAKEFILE - $:.unshift("#{bundler_path}") + $:.unshift("#{lib}") require "bundler/gem_tasks" RAKEFILE end @@ -19,7 +19,7 @@ RSpec.describe "require 'bundler/gem_tasks'" do it "includes the relevant tasks" do with_gem_path_as(Spec::Path.base_system_gems.to_s) do - sys_exec "#{rake} -T", "RUBYOPT" => "-I#{bundler_path}" + sys_exec "#{rake} -T", "RUBYOPT" => "-I#{lib}" end expect(err).to eq("") diff --git a/spec/runtime/inline_spec.rb b/spec/runtime/inline_spec.rb index 6168c0c197..c3d632d75d 100644 --- a/spec/runtime/inline_spec.rb +++ b/spec/runtime/inline_spec.rb @@ -2,7 +2,7 @@ RSpec.describe "bundler/inline#gemfile" do def script(code, options = {}) - requires = ["bundler/inline"] + requires = ["#{lib}/bundler/inline"] requires.unshift File.expand_path("../../support/artifice/" + options.delete(:artifice) + ".rb", __FILE__) if options.key?(:artifice) requires = requires.map {|r| "require '#{r}'" }.join("\n") @out = ruby("#{requires}\n\n" + code, options) @@ -96,7 +96,7 @@ RSpec.describe "bundler/inline#gemfile" do it "lets me use my own ui object" do script <<-RUBY, :artifice => "endpoint" - require 'bundler' + require '#{lib}/bundler' class MyBundlerUI < Bundler::UI::Silent def confirm(msg, newline = nil) puts "CONFIRMED!" @@ -140,7 +140,7 @@ RSpec.describe "bundler/inline#gemfile" do it "does not mutate the option argument" do script <<-RUBY - require 'bundler' + require '#{lib}/bundler' options = { :ui => Bundler::UI::Shell.new } gemfile(false, options) do path "#{lib_path}" do diff --git a/spec/runtime/load_spec.rb b/spec/runtime/load_spec.rb index 80ad692769..acefc1a583 100644 --- a/spec/runtime/load_spec.rb +++ b/spec/runtime/load_spec.rb @@ -58,7 +58,7 @@ RSpec.describe "Bundler.load" do end it "does not find a Gemfile above the testing directory" do - bundler_gemfile = tmp.join("../Gemfile") + bundler_gemfile = Pathname.new(__dir__).join("../../Gemfile") unless File.exist?(bundler_gemfile) FileUtils.touch(bundler_gemfile) @remove_bundler_gemfile = true @@ -80,7 +80,7 @@ RSpec.describe "Bundler.load" do G ruby! <<-RUBY - require "bundler" + require "#{lib}/bundler" Bundler.setup :default Bundler.require :default puts RACK diff --git a/spec/runtime/require_spec.rb b/spec/runtime/require_spec.rb index 016fc14dfe..42d0c2db77 100644 --- a/spec/runtime/require_spec.rb +++ b/spec/runtime/require_spec.rb @@ -193,7 +193,7 @@ RSpec.describe "Bundler.require" do G cmd = <<-RUBY - require 'bundler' + require '#{lib}/bundler' Bundler.require RUBY ruby(cmd) @@ -425,7 +425,7 @@ RSpec.describe "Bundler.require with platform specific dependencies" do source "#{file_uri_for(gem_repo1)}" platforms :#{not_local_tag} do - gem "platform_specific", :require => "omgomg" + gem "fail", :require => "omgomg" end gem "rack", "1.0.0" diff --git a/spec/runtime/setup_spec.rb b/spec/runtime/setup_spec.rb index 866f4862c5..b9d710a9d9 100644 --- a/spec/runtime/setup_spec.rb +++ b/spec/runtime/setup_spec.rb @@ -12,8 +12,7 @@ RSpec.describe "Bundler.setup" do G ruby <<-RUBY - require 'rubygems' - require 'bundler' + require '#{lib}/bundler' Bundler.setup require 'rack' @@ -35,8 +34,7 @@ RSpec.describe "Bundler.setup" do it "doesn't make all groups available" do ruby <<-RUBY - require 'rubygems' - require 'bundler' + require '#{lib}/bundler' Bundler.setup(:default) begin @@ -51,8 +49,7 @@ RSpec.describe "Bundler.setup" do it "accepts string for group name" do ruby <<-RUBY - require 'rubygems' - require 'bundler' + require '#{lib}/bundler' Bundler.setup(:default, 'test') require 'rack' @@ -64,8 +61,7 @@ RSpec.describe "Bundler.setup" do it "leaves all groups available if they were already" do ruby <<-RUBY - require 'rubygems' - require 'bundler' + require '#{lib}/bundler' Bundler.setup Bundler.setup(:default) @@ -78,8 +74,7 @@ RSpec.describe "Bundler.setup" do it "leaves :default available if setup is called twice" do ruby <<-RUBY - require 'rubygems' - require 'bundler' + require '#{lib}/bundler' Bundler.setup(:default) Bundler.setup(:default, :test) @@ -96,7 +91,7 @@ RSpec.describe "Bundler.setup" do it "handles multiple non-additive invocations" do ruby <<-RUBY - require 'bundler' + require '#{lib}/bundler' Bundler.setup(:default, :test) Bundler.setup(:default) require 'rack' @@ -114,7 +109,7 @@ RSpec.describe "Bundler.setup" do def clean_load_path(lp) without_bundler_load_path = ruby!("puts $LOAD_PATH").split("\n") lp -= without_bundler_load_path - lp.map! {|p| p.sub(/^#{Regexp.union system_gem_path.to_s, default_bundle_path.to_s, bundler_path.to_s}/i, "") } + lp.map! {|p| p.sub(/^#{Regexp.union system_gem_path.to_s, default_bundle_path.to_s, lib.to_s}/i, "") } end it "puts loaded gems after -I and RUBYLIB", :ruby_repo do @@ -127,8 +122,7 @@ RSpec.describe "Bundler.setup" do ENV["RUBYLIB"] = "rubylib_dir" ruby <<-RUBY - require 'rubygems' - require 'bundler' + require '#{lib}/bundler' Bundler.setup puts $LOAD_PATH RUBY @@ -150,8 +144,7 @@ RSpec.describe "Bundler.setup" do G ruby! <<-RUBY - require 'rubygems' - require 'bundler' + require '#{lib}/bundler' Bundler.setup puts $LOAD_PATH RUBY @@ -179,8 +172,7 @@ RSpec.describe "Bundler.setup" do G ruby! <<-RUBY - require 'rubygems' - require 'bundler/setup' + require '#{lib}/bundler/setup' puts $LOAD_PATH RUBY @@ -201,8 +193,7 @@ RSpec.describe "Bundler.setup" do G ruby <<-R - require 'rubygems' - require 'bundler' + require '#{lib}/bundler' begin Bundler.setup @@ -222,8 +213,7 @@ RSpec.describe "Bundler.setup" do G ruby <<-R - require 'rubygems' - require 'bundler' + require '#{lib}/bundler' Bundler.setup R @@ -246,8 +236,7 @@ RSpec.describe "Bundler.setup" do G ruby <<-R - require 'rubygems' - require 'bundler' + require '#{lib}/bundler' Bundler.setup R @@ -300,8 +289,7 @@ RSpec.describe "Bundler.setup" do ENV["BUNDLE_GEMFILE"] = "Gemfile" ruby <<-R - require 'rubygems' - require 'bundler' + require '#{lib}/bundler' begin Bundler.setup @@ -456,8 +444,7 @@ RSpec.describe "Bundler.setup" do break_git! ruby <<-R - require 'rubygems' - require 'bundler' + require '#{lib}/bundler' begin Bundler.setup @@ -478,8 +465,7 @@ RSpec.describe "Bundler.setup" do break_git! ruby <<-R - require "rubygems" - require "bundler" + require "#{lib}/bundler" begin Bundler.setup @@ -773,7 +759,7 @@ end full_gem_name = gem_name + "-1.0" ext_dir = File.join(tmp("extensions", full_gem_name)) - install_gem full_gem_name + install_gems full_gem_name install_gemfile <<-G source "#{file_uri_for(gem_repo1)}" @@ -788,7 +774,7 @@ end s.class.send(:define_method, :build_extensions) { nil } end - require 'bundler' + require '#{lib}/bundler' gem '#{gem_name}' puts $LOAD_PATH.count {|path| path =~ /#{gem_name}/} >= 2 @@ -804,7 +790,6 @@ end context "with bundler is located in symlinked GEM_HOME" do let(:gem_home) { Dir.mktmpdir } let(:symlinked_gem_home) { Tempfile.new("gem_home").path } - let(:bundler_dir) { ruby_core? ? File.expand_path("../../../..", __FILE__) : File.expand_path("../../..", __FILE__) } let(:full_name) { "bundler-#{Bundler::VERSION}" } before do @@ -814,24 +799,23 @@ end Dir.mkdir(gems_dir) Dir.mkdir(specifications_dir) - FileUtils.ln_s(bundler_dir, File.join(gems_dir, full_name)) + FileUtils.ln_s(root, File.join(gems_dir, full_name)) - gemspec_file = ruby_core? ? "#{bundler_dir}/lib/bundler/bundler.gemspec" : "#{bundler_dir}/bundler.gemspec" - gemspec = File.binread(gemspec_file). - sub("Bundler::VERSION", %("#{Bundler::VERSION}")) - gemspec = gemspec.lines.reject {|line| line =~ %r{lib/bundler/version} }.join + gemspec_content = File.binread(gemspec). + sub("Bundler::VERSION", %("#{Bundler::VERSION}")). + lines.reject {|line| line =~ %r{lib/bundler/version} }.join File.open(File.join(specifications_dir, "#{full_name}.gemspec"), "wb") do |f| - f.write(gemspec) + f.write(gemspec_content) end end - it "should not remove itself from the LOAD_PATH and require a different copy of 'bundler/setup'", :ruby_repo do + it "should not remove itself from the LOAD_PATH and require a different copy of 'bundler/setup'" do install_gemfile "" ruby <<-R, :env => { "GEM_PATH" => symlinked_gem_home }, :no_lib => true TracePoint.trace(:class) do |tp| - if tp.path.include?("bundler") && !tp.path.start_with?("#{File.expand_path("../..", __dir__)}") + if tp.path.include?("bundler") && !tp.path.start_with?("#{root}") puts "OMG. Defining a class from another bundler at \#{tp.path}:\#{tp.lineno}" end end @@ -939,8 +923,6 @@ end it "does not pull in system gems" do run <<-R - require 'rubygems' - begin; require 'rack' rescue LoadError @@ -1046,7 +1028,7 @@ end bundle "install" ruby <<-RUBY - require 'bundler' + require '#{lib}/bundler' def Bundler.require(path) raise "LOSE" end @@ -1101,7 +1083,7 @@ end context "is not present" do it "does not change the lock" do lockfile lock_with(nil) - ruby "require 'bundler/setup'" + ruby "require '#{lib}/bundler/setup'" lockfile_should_be lock_with(nil) end end @@ -1109,7 +1091,7 @@ end context "is newer" do it "does not change the lock or warn" do lockfile lock_with(Bundler::VERSION.succ) - ruby "require 'bundler/setup'" + ruby "require '#{lib}/bundler/setup'" expect(out).to eq("") expect(err).to eq("") lockfile_should_be lock_with(Bundler::VERSION.succ) @@ -1119,7 +1101,7 @@ end context "is older" do it "does not change the lock" do lockfile lock_with("1.10.1") - ruby "require 'bundler/setup'" + ruby "require '#{lib}/bundler/setup'" lockfile_should_be lock_with("1.10.1") end end @@ -1166,14 +1148,14 @@ end context "is not present" do it "does not change the lock" do - expect { ruby! "require 'bundler/setup'" }.not_to change { lockfile } + expect { ruby! "require '#{lib}/bundler/setup'" }.not_to change { lockfile } end end context "is newer" do let(:ruby_version) { "5.5.5" } it "does not change the lock or warn" do - expect { ruby! "require 'bundler/setup'" }.not_to change { lockfile } + expect { ruby! "require '#{lib}/bundler/setup'" }.not_to change { lockfile } expect(out).to eq("") expect(err).to eq("") end @@ -1182,7 +1164,7 @@ end context "is older" do let(:ruby_version) { "1.0.0" } it "does not change the lock" do - expect { ruby! "require 'bundler/setup'" }.not_to change { lockfile } + expect { ruby! "require '#{lib}/bundler/setup'" }.not_to change { lockfile } end end end @@ -1191,7 +1173,7 @@ end it "does not load Psych" do gemfile "" ruby <<-RUBY - require 'bundler/setup' + require '#{lib}/bundler/setup' puts defined?(Psych::VERSION) ? Psych::VERSION : "undefined" require 'psych' puts Psych::VERSION @@ -1204,7 +1186,7 @@ end it "does not load openssl" do install_gemfile! "" ruby! <<-RUBY - require "bundler/setup" + require "#{lib}/bundler/setup" puts defined?(OpenSSL) || "undefined" require "openssl" puts defined?(OpenSSL) || "undefined" @@ -1223,7 +1205,6 @@ end let(:activation_warning_hack) { strip_whitespace(<<-RUBY) } require #{spec_dir.join("support/hax").to_s.dump} - require "rubygems" if Gem::Specification.instance_methods.map(&:to_sym).include?(:activate) Gem::Specification.send(:alias_method, :bundler_spec_activate, :activate) @@ -1259,7 +1240,7 @@ end it "activates no gems with -rbundler/setup" do install_gemfile! "" - ruby! code, :env => { :RUBYOPT => activation_warning_hack_rubyopt + " -rbundler/setup" } + ruby! code, :env => { :RUBYOPT => activation_warning_hack_rubyopt + " -r#{lib}/bundler/setup" } expect(out).to eq("{}") end @@ -1334,7 +1315,7 @@ end G ruby! <<-RUBY - require "bundler/setup" + require "#{lib}/bundler/setup" Object.new.gem "rack" puts Gem.loaded_specs["rack"].full_name RUBY @@ -1349,7 +1330,7 @@ end G ruby <<-RUBY - require "bundler/setup" + require "#{lib}/bundler/setup" Object.new.gem "rack" puts "FAIL" RUBY @@ -1365,7 +1346,7 @@ end G ruby <<-RUBY - require "bundler/setup" + require "#{lib}/bundler/setup" Object.new.require "rack" puts "FAIL" RUBY diff --git a/spec/runtime/with_unbundled_env_spec.rb b/spec/runtime/with_unbundled_env_spec.rb index 30e8518043..a5140ae463 100644 --- a/spec/runtime/with_unbundled_env_spec.rb +++ b/spec/runtime/with_unbundled_env_spec.rb @@ -1,15 +1,15 @@ # frozen_string_literal: true RSpec.describe "Bundler.with_env helpers" do - def bundle_exec_ruby!(code) - build_bundler_context - bundle! "exec '#{Gem.ruby}' -e #{code}" + def bundle_exec_ruby!(code, options = {}) + build_bundler_context options + bundle! "exec '#{Gem.ruby}' -e #{code}", options end - def build_bundler_context + def build_bundler_context(options = {}) bundle "config set path vendor/bundle" gemfile "" - bundle "install" + bundle "install", options end describe "Bundler.original_env" do @@ -31,7 +31,7 @@ RSpec.describe "Bundler.with_env helpers" do end end - it "works with nested bundle exec invocations", :ruby_repo do + it "works with nested bundle exec invocations" do create_file("exe.rb", <<-'RB') count = ARGV.first.to_i exit if count < 0 @@ -75,7 +75,7 @@ RSpec.describe "Bundler.with_env helpers" do it "should remove '-rbundler/setup' from RUBYOPT" do code = "print #{modified_env}['RUBYOPT']" ENV["RUBYOPT"] = "-W2 -rbundler/setup #{ENV["RUBYOPT"]}" - bundle_exec_ruby! code.dump + bundle_exec_ruby! code.dump, :env => { "BUNDLER_SPEC_DISABLE_DEFAULT_BUNDLER_GEM" => "true" } expect(last_command.stdboth).not_to include("-rbundler/setup") end diff --git a/spec/spec_helper.rb b/spec/spec_helper.rb index 14df93a3da..f10f6c464f 100644 --- a/spec/spec_helper.rb +++ b/spec/spec_helper.rb @@ -66,11 +66,10 @@ RSpec.configure do |config| git_version = Bundler::Source::Git::GitProxy.new(nil, nil, nil).version - config.filter_run_excluding :ruby => RequirementChecker.against(RUBY_VERSION) config.filter_run_excluding :rubygems => RequirementChecker.against(Gem::VERSION) config.filter_run_excluding :git => RequirementChecker.against(git_version) config.filter_run_excluding :bundler => RequirementChecker.against(Bundler::VERSION.split(".")[0]) - config.filter_run_excluding :ruby_repo => !(ENV["BUNDLE_RUBY"] && ENV["BUNDLE_GEM"]).nil? + config.filter_run_excluding :ruby_repo => !ENV["GEM_COMMAND"].nil? config.filter_run_excluding :no_color_tty => Gem.win_platform? || !ENV["GITHUB_ACTION"].nil? config.filter_run_excluding :github_action_linux => !ENV["GITHUB_ACTION"].nil? && (ENV["RUNNER_OS"] == "Linux") @@ -88,12 +87,12 @@ RSpec.configure do |config| end config.around :each do |example| - if ENV["BUNDLE_RUBY"] + if ENV["RUBY"] orig_ruby = Gem.ruby - Gem.ruby = ENV["BUNDLE_RUBY"] + Gem.ruby = ENV["RUBY"] end example.run - Gem.ruby = orig_ruby if ENV["BUNDLE_RUBY"] + Gem.ruby = orig_ruby if ENV["RUBY"] end config.before :suite do @@ -108,7 +107,7 @@ RSpec.configure do |config| original_env = ENV.to_hash - if ENV["BUNDLE_RUBY"] + if ENV["RUBY"] FileUtils.cp_r Spec::Path.bindir, File.join(Spec::Path.root, "lib", "exe") end end @@ -139,7 +138,7 @@ RSpec.configure do |config| end config.after :suite do - if ENV["BUNDLE_RUBY"] + if ENV["RUBY"] FileUtils.rm_rf File.join(Spec::Path.root, "lib", "exe") end end diff --git a/spec/support/artifice/endpoint.rb b/spec/support/artifice/endpoint.rb index d9e9e0ae0a..966681f8d8 100644 --- a/spec/support/artifice/endpoint.rb +++ b/spec/support/artifice/endpoint.rb @@ -44,8 +44,7 @@ class Endpoint < Sinatra::Base def dependencies_for(gem_names, gem_repo = GEM_REPO) return [] if gem_names.nil? || gem_names.empty? - require "rubygems" - require "bundler" + require "#{Spec::Path.lib}/bundler" Bundler::Deprecate.skip_during do all_specs = %w[specs.4.8 prerelease_specs.4.8].map do |filename| Marshal.load(File.open(gem_repo.join(filename)).read) diff --git a/spec/support/builders.rb b/spec/support/builders.rb index 70125ce52a..c7f299487c 100644 --- a/spec/support/builders.rb +++ b/spec/support/builders.rb @@ -557,7 +557,7 @@ module Spec "#!/usr/bin/env ruby\n" end @spec.files << executable - write executable, "#{shebang}require '#{@name}' ; puts #{Builders.constantize(@name)}" + write executable, "#{shebang}require_relative '../lib/#{@name}' ; puts #{Builders.constantize(@name)}" end end diff --git a/spec/support/hax.rb b/spec/support/hax.rb index 4f8d9b89ec..3e1ece2f0a 100644 --- a/spec/support/hax.rb +++ b/spec/support/hax.rb @@ -1,8 +1,14 @@ # frozen_string_literal: true -require "rubygems" - module Gem + def self.ruby=(ruby) + @ruby = ruby + end + + if ENV["RUBY"] + Gem.ruby = ENV["RUBY"] + end + if version = ENV["BUNDLER_SPEC_RUBYGEMS_VERSION"] remove_const(:VERSION) if const_defined?(:VERSION) VERSION = version @@ -13,7 +19,8 @@ module Gem end @platforms = [Gem::Platform::RUBY, Gem::Platform.local] - if defined?(@path_to_default_spec_map) && !ENV["BUNDLER_SPEC_KEEP_DEFAULT_BUNDLER_GEM"] + # We only need this hack for rubygems versions without the BundlerVersionFinder + if Gem::Version.new(Gem::VERSION) < Gem::Version.new("2.7.0") || ENV["BUNDLER_SPEC_DISABLE_DEFAULT_BUNDLER_GEM"] @path_to_default_spec_map.delete_if do |_path, spec| spec.name == "bundler" end diff --git a/spec/support/helpers.rb b/spec/support/helpers.rb index 02ec3c790b..0c05789946 100644 --- a/spec/support/helpers.rb +++ b/spec/support/helpers.rb @@ -77,7 +77,7 @@ module Spec def run(cmd, *args) opts = args.last.is_a?(Hash) ? args.pop : {} groups = args.map(&:inspect).join(", ") - setup = "require 'bundler' ; Bundler.setup(#{groups})\n" + setup = "require '#{lib}/bundler' ; Bundler.setup(#{groups})\n" ruby(setup + cmd, opts) end bang :run @@ -95,10 +95,6 @@ module Spec run(cmd, *args) end - def lib - root.join("lib") - end - def spec spec_dir.to_s end @@ -196,7 +192,6 @@ module Spec end def gembin(cmd) - lib = File.expand_path("../../../lib", __FILE__) old = ENV["RUBYOPT"] ENV["RUBYOPT"] = "#{ENV["RUBYOPT"]} -I#{lib}" cmd = bundled_app("bin/#{cmd}") unless cmd.to_s.include?("/") @@ -205,13 +200,8 @@ module Spec ENV["RUBYOPT"] = old end - def gem_command(command, args = "", options = {}) - if command == :exec && !options[:no_quote] - args = args.gsub(/(?=")/, "\\") - args = %("#{args}") - end - gem = ENV["BUNDLE_GEM"] || "#{Gem.ruby} -rrubygems -S gem --backtrace" - sys_exec("#{gem} #{command} #{args}") + def gem_command(command, args = "") + sys_exec("#{Path.gem_bin} #{command} #{args}") end bang :gem_command @@ -307,32 +297,35 @@ module Spec options = gems.last.is_a?(Hash) ? gems.pop : {} gem_repo = options.fetch(:gem_repo) { gem_repo1 } gems.each do |g| - path = if g == :bundler - if ruby_core? - spec = Gem::Specification.load(gemspec.to_s) - spec.bindir = "libexec" - File.open(root.join("bundler.gemspec").to_s, "w") {|f| f.write spec.to_ruby } - Dir.chdir(root) { gem_command! :build, root.join("bundler.gemspec").to_s } - FileUtils.rm(root.join("bundler.gemspec")) - else - Dir.chdir(root) { gem_command! :build, gemspec.to_s } - end - bundler_path = root + "bundler-#{Bundler::VERSION}.gem" + if g == :bundler + with_built_bundler {|gem_path| install_gem(gem_path) } elsif g.to_s =~ %r{\A(?:[A-Z]:)?/.*\.gem\z} - g + install_gem(g) else - "#{gem_repo}/gems/#{g}.gem" + install_gem("#{gem_repo}/gems/#{g}.gem") end + end + end - raise "OMG `#{path}` does not exist!" unless File.exist?(path) + def install_gem(path) + raise "OMG `#{path}` does not exist!" unless File.exist?(path) - gem_command! :install, "--no-document --ignore-dependencies '#{path}'" + gem_command! :install, "--no-document --ignore-dependencies '#{path}'" + end - bundler_path && bundler_path.rmtree + def with_built_bundler + with_root_gemspec do |gemspec| + Dir.chdir(root) { gem_command! :build, gemspec.to_s } end - end - alias_method :install_gem, :install_gems + bundler_path = root + "bundler-#{Bundler::VERSION}.gem" + + begin + yield(bundler_path) + ensure + bundler_path.rmtree + end + end def with_gem_path_as(path) backup = ENV.to_hash @@ -600,13 +593,5 @@ module Spec end port end - - def bundler_fileutils - if RUBY_VERSION >= "2.4" - ::Bundler::FileUtils - else - ::FileUtils - end - end end end diff --git a/spec/support/parallel.rb b/spec/support/parallel.rb new file mode 100644 index 0000000000..8763cb9ec4 --- /dev/null +++ b/spec/support/parallel.rb @@ -0,0 +1,5 @@ +# frozen_string_literal: true + +RSpec.configure do |config| + config.silence_filter_announcements = true +end diff --git a/spec/support/path.rb b/spec/support/path.rb index b722ec498b..db28454792 100644 --- a/spec/support/path.rb +++ b/spec/support/path.rb @@ -13,16 +13,43 @@ module Spec @gemspec ||= root.join(ruby_core? ? "lib/bundler/bundler.gemspec" : "bundler.gemspec") end + def gemspec_dir + @gemspec_dir ||= gemspec.parent + end + def bindir @bindir ||= root.join(ruby_core? ? "libexec" : "exe") end + def gem_bin + @gem_bin ||= ruby_core? ? ENV["GEM_COMMAND"] : "#{Gem.ruby} -S gem --backtrace" + end + def spec_dir @spec_dir ||= root.join(ruby_core? ? "spec/bundler" : "spec") end + def tracked_files + @tracked_files ||= ruby_core? ? `git ls-files -z -- lib/bundler lib/bundler.rb spec/bundler man/bundler*` : `git ls-files -z` + end + + def shipped_files + @shipped_files ||= ruby_core? ? `git ls-files -z -- lib/bundler lib/bundler.rb man/bundler* libexec/bundle*` : `git ls-files -z -- lib man exe CHANGELOG.md LICENSE.md README.md bundler.gemspec` + end + + def lib_tracked_files + @lib_tracked_files ||= ruby_core? ? `git ls-files -z -- lib/bundler lib/bundler.rb` : `git ls-files -z -- lib` + end + def tmp(*path) - root.join("tmp", *path) + root.join("tmp", scope, *path) + end + + def scope + test_number = ENV["TEST_ENV_NUMBER"] + return "1" if test_number.nil? + + test_number.empty? ? "1" : test_number end def home(*path) @@ -104,7 +131,7 @@ module Spec tmp("libs", *args) end - def bundler_path + def lib root.join("lib") end @@ -120,12 +147,25 @@ module Spec tmp "tmpdir", *args end + def with_root_gemspec + if ruby_core? + root_gemspec = root.join("bundler.gemspec") + spec = Gem::Specification.load(gemspec.to_s) + spec.bindir = "libexec" + File.open(root_gemspec.to_s, "w") {|f| f.write spec.to_ruby } + yield(root_gemspec) + FileUtils.rm(root_gemspec) + else + yield(gemspec) + end + end + def ruby_core? - # avoid to wornings + # avoid to warnings @ruby_core ||= nil if @ruby_core.nil? - @ruby_core = true & (ENV["BUNDLE_RUBY"] && ENV["BUNDLE_GEM"]) + @ruby_core = true & ENV["GEM_COMMAND"] else @ruby_core end diff --git a/spec/support/rubygems_ext.rb b/spec/support/rubygems_ext.rb index 6ca51bee16..faa474a917 100644 --- a/spec/support/rubygems_ext.rb +++ b/spec/support/rubygems_ext.rb @@ -8,6 +8,7 @@ module Spec module Rubygems DEV_DEPS = { "automatiek" => "~> 0.2.0", + "parallel_tests" => "~> 2.29", "rake" => "~> 12.0", "ronn" => "~> 0.7.3", "rspec" => "~> 3.8", @@ -81,7 +82,7 @@ module Spec no_reqs.map!(&:first) reqs.map! {|name, req| "'#{name}:#{req}'" } deps = reqs.concat(no_reqs).join(" ") - gem = Spec::Path.ruby_core? ? ENV["BUNDLE_GEM"] : "#{Gem.ruby} -S gem" + gem = Path.gem_bin cmd = "#{gem} install #{deps} --no-document --conservative" puts cmd system(cmd) || raise("Installing gems #{deps} for the tests to use failed!") |