ruby-changes:40465
From: hsbt <ko1@a...>
Date: Thu, 12 Nov 2015 13:50:19 +0900 (JST)
Subject: [ruby-changes:40465] hsbt:r52546 (trunk): * lib/rubygems: Update to RubyGems 2.5.0+ HEAD(db78980).
hsbt 2015-11-12 13:50:06 +0900 (Thu, 12 Nov 2015) New Revision: 52546 http://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=revision&revision=52546 Log: * lib/rubygems: Update to RubyGems 2.5.0+ HEAD(db78980). this version includes #1367 , #1373 , #1375 * test/rubygems: ditto. Modified files: trunk/ChangeLog trunk/lib/rubygems/basic_specification.rb trunk/lib/rubygems/config_file.rb trunk/lib/rubygems/resolver.rb trunk/lib/rubygems/specification.rb trunk/lib/rubygems/stub_specification.rb trunk/lib/rubygems/test_case.rb trunk/lib/rubygems.rb trunk/test/rubygems/test_gem_config_file.rb trunk/test/rubygems/test_gem_stub_specification.rb Index: ChangeLog =================================================================== --- ChangeLog (revision 52545) +++ ChangeLog (revision 52546) @@ -1,3 +1,9 @@ https://github.com/ruby/ruby/blob/trunk/ChangeLog#L1 +Thu Nov 12 13:49:50 2015 SHIBATA Hiroshi <hsbt@r...> + + * lib/rubygems: Update to RubyGems 2.5.0+ HEAD(db78980). + this version includes #1367 , #1373 , #1375 + * test/rubygems: ditto. + Thu Nov 12 10:53:41 2015 Eric Wong <e@8...> * benchmark/bm_io_nonblock_noex2.rb: new benchmark based Index: lib/rubygems/basic_specification.rb =================================================================== --- lib/rubygems/basic_specification.rb (revision 52545) +++ lib/rubygems/basic_specification.rb (revision 52546) @@ -38,6 +38,14 @@ class Gem::BasicSpecification https://github.com/ruby/ruby/blob/trunk/lib/rubygems/basic_specification.rb#L38 end ## + # The path to the gem.build_complete file within the extension install + # directory. + + def gem_build_complete_path # :nodoc: + File.join extension_dir, 'gem.build_complete' + end + + ## # True when the gem has been activated def activated? @@ -50,12 +58,7 @@ class Gem::BasicSpecification https://github.com/ruby/ruby/blob/trunk/lib/rubygems/basic_specification.rb#L58 # eg: /usr/local/lib/ruby/gems/1.8 def base_dir - return Gem.dir unless loaded_from - @base_dir ||= if default_gem? then - File.dirname File.dirname File.dirname loaded_from - else - File.dirname File.dirname loaded_from - end + raise NotImplementedError end ## @@ -65,7 +68,7 @@ class Gem::BasicSpecification https://github.com/ruby/ruby/blob/trunk/lib/rubygems/basic_specification.rb#L68 @contains_requirable_file ||= {} @contains_requirable_file[file] ||= begin - if instance_variable_defined?(:@ignored) then + if @ignored then return false elsif missing_extensions? then @ignored = true @@ -75,12 +78,7 @@ class Gem::BasicSpecification https://github.com/ruby/ruby/blob/trunk/lib/rubygems/basic_specification.rb#L78 return false end - suffixes = Gem.suffixes - - full_require_paths.any? do |dir| - base = "#{dir}/#{file}" - suffixes.any? { |suf| File.file? "#{base}#{suf}" } - end + have_file? file, Gem.suffixes end ? :yes : :no @contains_requirable_file[file] == :yes end @@ -94,7 +92,7 @@ class Gem::BasicSpecification https://github.com/ruby/ruby/blob/trunk/lib/rubygems/basic_specification.rb#L92 # Returns full path to the directory where gem's extensions are installed. def extension_dir - @extension_dir ||= File.expand_path File.join(extensions_dir, full_name) + @extension_dir ||= File.expand_path(File.join(extensions_dir, full_name)).untaint end ## @@ -110,7 +108,7 @@ class Gem::BasicSpecification https://github.com/ruby/ruby/blob/trunk/lib/rubygems/basic_specification.rb#L108 # TODO: also, shouldn't it default to full_name if it hasn't been written? path = File.expand_path File.join(gems_dir, full_name) path.untaint - path if File.directory? path + path end private :find_full_gem_path @@ -148,13 +146,21 @@ class Gem::BasicSpecification https://github.com/ruby/ruby/blob/trunk/lib/rubygems/basic_specification.rb#L146 File.join full_gem_path, path.untaint end - full_paths << extension_dir unless @extensions.nil? || @extensions.empty? + full_paths << extension_dir if have_extensions? full_paths end end ## + # The path to the data directory for this gem. + + def datadir +# TODO: drop the extra ", gem_name" which is uselessly redundant + File.expand_path(File.join(gems_dir, full_name, "data", name)).untaint + end + + ## # Full path of the target library file. # If the file is not in this gem, return nil. @@ -189,8 +195,7 @@ class Gem::BasicSpecification https://github.com/ruby/ruby/blob/trunk/lib/rubygems/basic_specification.rb#L195 # gem directory. eg: /usr/local/lib/ruby/1.8/gems def gems_dir - # TODO: this logic seems terribly broken, but tests fail if just base_dir - @gems_dir ||= File.join(loaded_from && base_dir || Gem.dir, "gems") + raise NotImplementedError end def internal_init # :nodoc: @@ -198,8 +203,7 @@ class Gem::BasicSpecification https://github.com/ruby/ruby/blob/trunk/lib/rubygems/basic_specification.rb#L203 @extensions_dir = nil @full_gem_path = nil @gem_dir = nil - @gems_dir = nil - @base_dir = nil + @ignored = nil end ## @@ -217,7 +221,7 @@ class Gem::BasicSpecification https://github.com/ruby/ruby/blob/trunk/lib/rubygems/basic_specification.rb#L221 end def raw_require_paths # :nodoc: - Array(@require_paths) + raise NotImplementedError end ## @@ -238,7 +242,7 @@ class Gem::BasicSpecification https://github.com/ruby/ruby/blob/trunk/lib/rubygems/basic_specification.rb#L242 # spec.require_path = '.' def require_paths - return raw_require_paths if @extensions.nil? || @extensions.empty? + return raw_require_paths unless have_extensions? [extension_dir].concat raw_require_paths end @@ -250,8 +254,8 @@ class Gem::BasicSpecification https://github.com/ruby/ruby/blob/trunk/lib/rubygems/basic_specification.rb#L254 def source_paths paths = raw_require_paths.dup - if @extensions then - ext_dirs = @extensions.map do |extension| + if have_extensions? then + ext_dirs = extensions.map do |extension| extension.split(File::SEPARATOR, 2).first end.uniq @@ -307,5 +311,23 @@ class Gem::BasicSpecification https://github.com/ruby/ruby/blob/trunk/lib/rubygems/basic_specification.rb#L311 raise NotImplementedError end + private + + def have_extensions?; !extensions.empty?; end + + def have_file? file, suffixes + return true if raw_require_paths.any? do |path| + base = File.join(gems_dir, full_name, path.untaint, file).untaint + suffixes.any? { |suf| File.file? base + suf } + end + + if have_extensions? + base = File.join extension_dir, file + suffixes.any? { |suf| File.file? base + suf } + else + false + end + end + end Index: lib/rubygems/config_file.rb =================================================================== --- lib/rubygems/config_file.rb (revision 52545) +++ lib/rubygems/config_file.rb (revision 52546) @@ -321,12 +321,12 @@ if you believe they were disclosed to a https://github.com/ruby/ruby/blob/trunk/lib/rubygems/config_file.rb#L321 @rubygems_api_key = api_key end - YAMLErrors = [ArgumentError] - YAMLErrors << Psych::SyntaxError if defined?(Psych::SyntaxError) - def load_file(filename) Gem.load_yaml + yaml_errors = [ArgumentError] + yaml_errors << Psych::SyntaxError if defined?(Psych::SyntaxError) + return {} unless filename and File.exist? filename begin @@ -336,7 +336,7 @@ if you believe they were disclosed to a https://github.com/ruby/ruby/blob/trunk/lib/rubygems/config_file.rb#L336 return {} end return content - rescue *YAMLErrors => e + rescue *yaml_errors => e warn "Failed to load #{filename}, #{e}" rescue Errno::EACCES warn "Failed to load #{filename} due to permissions problem." Index: lib/rubygems/specification.rb =================================================================== --- lib/rubygems/specification.rb (revision 52545) +++ lib/rubygems/specification.rb (revision 52546) @@ -740,23 +740,41 @@ class Gem::Specification < Gem::BasicSpe https://github.com/ruby/ruby/blob/trunk/lib/rubygems/specification.rb#L740 end def self.gemspec_stubs_in dir, pattern - Dir[File.join(dir, pattern)].map { |path| - if dir == default_specifications_dir - Gem::StubSpecification.default_gemspec_stub(path) - else - Gem::StubSpecification.gemspec_stub(path) - end - }.select(&:valid?) + Dir[File.join(dir, pattern)].map { |path| yield path }.select(&:valid?) end private_class_method :gemspec_stubs_in + def self.default_stubs pattern + base_dir = Gem.default_dir + gems_dir = File.join base_dir, "gems" + gemspec_stubs_in(default_specifications_dir, pattern) do |path| + Gem::StubSpecification.default_gemspec_stub(path, base_dir, gems_dir) + end + end + private_class_method :default_stubs + + def self.installed_stubs dirs, pattern + map_stubs(dirs, pattern) do |path, base_dir, gems_dir| + Gem::StubSpecification.gemspec_stub(path, base_dir, gems_dir) + end + end + private_class_method :installed_stubs + if [].respond_to? :flat_map def self.map_stubs(dirs, pattern) # :nodoc: - dirs.flat_map { |dir| gemspec_stubs_in(dir, pattern) } + dirs.flat_map { |dir| + base_dir = File.dirname dir + gems_dir = File.join base_dir, "gems" + gemspec_stubs_in(dir, pattern) { |path| yield path, base_dir, gems_dir } + } end else # FIXME: remove when 1.8 is dropped def self.map_stubs(dirs, pattern) # :nodoc: - dirs.map { |dir| gemspec_stubs_in(dir, pattern) }.flatten 1 + dirs.map { |dir| + base_dir = File.dirname dir + gems_dir = File.join base_dir, "gems" + gemspec_stubs_in(dir, pattern) { |path| yield path, base_dir, gems_dir } + }.flatten 1 end end private_class_method :map_stubs @@ -803,7 +821,8 @@ class Gem::Specification < Gem::BasicSpe https://github.com/ruby/ruby/blob/trunk/lib/rubygems/specification.rb#L821 def self.stubs @@stubs ||= begin - stubs = map_stubs([default_specifications_dir] + dirs, "*.gemspec") + pattern = "*.gemspec" + stubs = default_stubs(pattern).concat installed_stubs(dirs, pattern) stubs = uniq_by(stubs) { |stub| stub.full_name } _resort!(stubs) @@ -818,10 +837,11 @@ class Gem::Specification < Gem::BasicSpe https://github.com/ruby/ruby/blob/trunk/lib/rubygems/specification.rb#L837 # Returns a Gem::StubSpecification for installed gem named +name+ def self.stubs_for name - if @@stubs || @@stubs_by_name[name] + if @@stubs @@stubs_by_name[name] || [] else - stubs = map_stubs([default_specifications_dir] + dirs, "#{name}-*.gemspec") + pattern = "#{name}-*.gemspec" + stubs = default_stubs(pattern) + installed_stubs(dirs, pattern) stubs = uniq_by(stubs) { |stub| stub.full_name }.group_by(&:name) stubs.each_value { |v| sort_by!(v) { |i| i.version } } @@ -1006,8 +1026,9 @@ class Gem::Specification < Gem::BasicSpe https://github.com/ruby/ruby/blob/trunk/lib/rubygems/specification.rb#L1026 # Return the best specification that contains the file matching +path+. def self.find_by_path path + path = path.dup.freeze stub = stubs.find { |spec| - spec.contains_requirable_file? path if spec + spec.contains_requirable_file? path } stub && stub.to_spec end @@ -1018,7 +1039,7 @@ class Gem::Specification < Gem::BasicSpe https://github.com/ruby/ruby/blob/trunk/lib/rubygems/specification.rb#L1039 def self.find_inactive_by_path path stub = stubs.find { |s| - s.contains_requirable_file? path unless s.nil? || s.activated? + s.contains_requirable_file? path unless s.activated? } stub && stub.to_spec end @@ -1030,7 +1051,7 @@ class Gem::Specification < Gem::BasicSpe https://github.com/ruby/ruby/blob/trunk/lib/rubygems/specification.rb#L1051 # TODO: do we need these?? Kill it specs = unresolved_deps.values.map { |dep| dep.to_specs }.flatten - specs.find_all { |spec| spec.contains_requirable_file? path if spec } + specs.find_all { |spec| spec.contains_requirable_file? path } end ## @@ -1924,30 +1945,22 @@ class Gem::Specification < Gem::BasicSpe https://github.com/ruby/ruby/blob/trunk/lib/rubygems/specification.rb#L1945 spec end - def find_full_gem_path # :nodoc: - super || File.expand_path(File.join(gems_dir, original_name)) - end - private :find_full_gem_path - def full_name @full_name ||= super end ## - # The path to the gem.build_complete file within the extension install - # directory. - - def gem_build_complete_path # :nodoc: - File.join extension_dir, 'gem.build_complete' - end - - ## # Work around bundler removing my methods def gem_dir # :nodoc: super end + def gems_dir + # TODO: this logic seems terribly broken, but tests fail if just base_dir + @gems_dir ||= File.join(loaded_from && base_dir || Gem.dir, "gems") + end + ## # Deprecated and ignored, defaults to true. # @@ -1995,6 +2008,8 @@ class Gem::Specification < Gem::BasicSpe https://github.com/ruby/ruby/blob/trunk/lib/rubygems/specification.rb#L2008 def initialize name = nil, version = nil super() + @gems_dir = nil + @base_dir = nil @loaded = false @activated = false @loaded_from = nil @@ -2044,6 +2059,15 @@ class Gem::Specification < Gem::BasicSpe https://github.com/ruby/ruby/blob/trunk/lib/rubygems/specification.rb#L2059 end end + def base_dir + return Gem.dir unless loaded_from + @base_dir ||= if default_gem? then + File.dirname File.dirname File.dirname loaded_from + else + File.dirname File.dirname loaded_from + end + end + ## # Expire memoized instance variables that can incorrectly generate, replace # or miss files due changes in certain attributes used to compute them. @@ -2954,6 +2978,10 @@ open-ended dependency on #{dep} is not r https://github.com/ruby/ruby/blob/trunk/lib/rubygems/specification.rb#L2978 alert_warning statement end + def raw_require_paths # :nodoc: + @require_paths + end + extend Gem::Deprecate # TODO: Index: lib/rubygems/stub_specification.rb =================================================================== --- lib/rubygems/stub_specification.rb (revision 52545) +++ lib/rubygems/stub_specification.rb (revision 52546) @@ -15,33 +15,65 @@ class Gem::StubSpecification < Gem::Basi https://github.com/ruby/ruby/blob/trunk/lib/rubygems/stub_specification.rb#L15 end class StubLine # :nodoc: all - attr_reader :name, :version, :platform, :require_paths + attr_reader :name, :version, :platform, :require_paths, :extensions, + :full_name - def initialize(data) - parts = data[PREFIX.length..-1].split(" ") + NO_EXTENSIONS = [].freeze + + # These are common require paths. + REQUIRE_PATHS = { # :nodoc: + 'lib' => 'lib'.freeze, + 'test' => 'test'.freeze, + 'ext' => 'ext'.freeze, + } + + # These are common require path lists. This hash is used to optimize + # and consolidate require_path objects. Most specs just specify "lib" + # in their require paths, so lets take advantage of that by pre-allocating + # a require path list for that case. + REQUIRE_PATH_LIST = { # :nodoc: + 'lib' => ['lib'].freeze + } + + def initialize data, extensions + parts = data[PREFIX.length..-1].split(" ".freeze, 4) @name = parts[0].freeze @version = Gem::Version.new parts[1] @platform = Gem::Platform.new parts[2] - @require_paths = parts.drop(3).join(" ").split("\0") + @extensions = extensions + @full_name = if platform == Gem::Platform::RUBY + "#{name}-#{version}" + else + "#{name}-#{version}-#{platform}" + end + + path_list = parts.last + @require_paths = REQUIRE_PATH_LIST[path_list] || path_list.split("\0".freeze).map! { |x| + REQUIRE_PATHS[x] || x + } end end - def self.default_gemspec_stub filename - new filename, true + def self.default_gemspec_stub filename, base_dir, gems_dir + new filename, base_dir, gems_dir, true end - def self.gemspec_stub filename - new filename, false + def self.gemspec_stub filename, base_dir, gems_dir + new filename, base_dir, gems_dir, false end - def initialize filename, default_gem + attr_reader :base_dir, :gems_dir + + def initialize filename, base_dir, gems_dir, default_gem + super() filename.untaint self.loaded_from = filename @data = nil - @extensions = nil @name = nil @spec = nil + @base_dir = base_dir + @gems_dir = gems_dir @default_gem = default_gem end @@ -73,8 +105,6 @@ class Gem::StubSpecification < Gem::Basi https://github.com/ruby/ruby/blob/trunk/lib/rubygems/stub_specification.rb#L105 def data unless @data - @extensions = [] - begin saved_lineno = $. open loaded_from, OPEN_MODE do |file| @@ -82,10 +112,13 @@ class Gem::StubSpecification < Gem::Basi https://github.com/ruby/ruby/blob/trunk/lib/rubygems/stub_specification.rb#L112 file.readline # discard encoding line stubline = file.readline.chomp if stubline.start_with?(PREFIX) then - @data = StubLine.new stubline + extensions = if /\A#{PREFIX}/ =~ file.readline.chomp + $'.split "\0" + else + StubLine::NO_EXTENSIONS + end - @extensions = $'.split "\0" if - /\A#{PREFIX}/ =~ file.readline.chomp + @data = StubLine.new stubline, extensions end rescue EOFError end @@ -100,41 +133,14 @@ class Gem::StubSpecification < Gem::Basi https://github.com/ruby/ruby/blob/trunk/lib/rubygems/stub_specification.rb#L133 private :data - ## - # Extensions for this gem - - def extensions - return @extensions if @extensions - - data # load - - @extensions - end - - ## - # If a gem has a stub specification it doesn't need to bother with - # compatibility with original_name gems. It was installed with the - # normalized name. - - def find_full_gem_path # :nodoc: - path = File.expand_path File.join gems_dir, full_name - path.untaint - path - end - - ## - # Full paths in the gem to add to <code>$LOAD_PATH</code> when this gem is - # activated. - - def full_require_paths - @require_paths ||= data.require_paths - - super + def raw_require_paths # :nodoc: + data.require_paths end def missing_extensions? return false if default_gem? return false if extensions.empty? + return false if File.exist? gem_build_complete_path to_spec.missing_extensions? end @@ -154,12 +160,21 @@ class Gem::StubSpecification < Gem::Basi https://github.com/ruby/ruby/blob/trunk/lib/rubygems/stub_specification.rb#L160 end ## - # Require paths of the gem + # Extensions for this gem - def require_paths - @require_paths ||= data.require_paths + def extensions + data.extensions + end - super + ## + # Version of the gem + + def version + data.version + end + + def full_name + data.full_name end ## @@ -173,7 +188,7 @@ class Gem::StubSpecification < Gem::Basi https://github.com/ruby/ruby/blob/trunk/lib/rubygems/stub_specification.rb#L188 end @spec ||= Gem::Specification.load(loaded_from) - @spec.ignored = @ignored if instance_variable_defined? :@ignored + @spec.ignored = @ignored if @spec @spec end @@ -187,13 +202,6 @@ class Gem::StubSpecification < Gem::Basi https://github.com/ruby/ruby/blob/trunk/lib/rubygems/stub_specification.rb#L202 end ## - # Version of the gem - - def version - @version ||= data.version - end - - ## # Is there a stub line present for this StubSpecification? def stubbed? Index: lib/rubygems/res (... truncated) -- ML: ruby-changes@q... Info: http://www.atdot.net/~ko1/quickml/