lib/bundler/lazy_specification.rb in bundler-2.3.27 vs lib/bundler/lazy_specification.rb in bundler-2.4.0

- old
+ new

@@ -1,20 +1,25 @@ # frozen_string_literal: true +require_relative "force_platform" + module Bundler class LazySpecification include MatchPlatform + include ForcePlatform attr_reader :name, :version, :dependencies, :platform attr_accessor :source, :remote, :force_ruby_platform def initialize(name, version, platform, source = nil) @name = name @version = version @dependencies = [] @platform = platform || Gem::Platform::RUBY @source = source + @specification = nil + @force_ruby_platform = default_force_ruby_platform end def full_name if platform == Gem::Platform::RUBY "#{@name}-#{@version}" @@ -73,50 +78,41 @@ end def materialize_for_installation source.local! - matching_specs = source.specs.search(use_exact_resolved_specifications? ? self : [name, version]) - return self if matching_specs.empty? + candidates = if source.is_a?(Source::Path) || !ruby_platform_materializes_to_ruby_platform? + target_platform = ruby_platform_materializes_to_ruby_platform? ? platform : local_platform - candidates = if use_exact_resolved_specifications? - matching_specs + GemHelpers.select_best_platform_match(source.specs.search([name, version]), target_platform) else - target_platform = ruby_platform_materializes_to_ruby_platform? ? platform : local_platform + source.specs.search(self) + end - installable_candidates = GemHelpers.select_best_platform_match(matching_specs, target_platform) + return self if candidates.empty? - specification = __materialize__(installable_candidates, :fallback_to_non_installable => false) - return specification unless specification.nil? + __materialize__(candidates) + end - if target_platform != platform - installable_candidates = GemHelpers.select_best_platform_match(matching_specs, platform) + def __materialize__(candidates) + @specification = begin + search = candidates.reverse.find do |spec| + spec.is_a?(StubSpecification) || + (spec.matches_current_ruby? && + spec.matches_current_rubygems?) end - - installable_candidates + if search.nil? && Bundler.frozen_bundle? + search = candidates.last + else + search.dependencies = dependencies if search && search.full_name == full_name && (search.is_a?(RemoteSpecification) || search.is_a?(EndpointSpecification)) + end + search end - - __materialize__(candidates) end - # If in frozen mode, we fallback to a non-installable candidate because by - # doing this we avoid re-resolving and potentially end up changing the - # lock file, which is not allowed. In that case, we will give a proper error - # about the mismatch higher up the stack, right before trying to install the - # bad gem. - def __materialize__(candidates, fallback_to_non_installable: Bundler.frozen_bundle?) - search = candidates.reverse.find do |spec| - spec.is_a?(StubSpecification) || - (spec.matches_current_ruby? && - spec.matches_current_rubygems?) - end - if search.nil? && fallback_to_non_installable - search = candidates.last - else - search.dependencies = dependencies if search && search.full_name == full_name && (search.is_a?(RemoteSpecification) || search.is_a?(EndpointSpecification)) - end - search + def respond_to?(*args) + super || @specification ? @specification.respond_to?(*args) : nil end def to_s @__to_s ||= if platform == Gem::Platform::RUBY "#{name} (#{version})" @@ -134,11 +130,19 @@ " #{source.revision[0..6]}" end private - def use_exact_resolved_specifications? - @use_exact_resolved_specifications ||= !source.is_a?(Source::Path) && ruby_platform_materializes_to_ruby_platform? + def to_ary + nil + end + + def method_missing(method, *args, &blk) + raise "LazySpecification has not been materialized yet (calling :#{method} #{args.inspect})" unless @specification + + return super unless respond_to?(method) + + @specification.send(method, *args, &blk) end # # For backwards compatibility with existing lockfiles, if the most specific # locked platform is not a specific platform like x86_64-linux or