class Bundler::Definition

def converge_locked_specs

generated
commonly happen if the Gemfile has changed since the lockfile was last
Remove elements from the locked specs that are expired. This will most
def converge_locked_specs
  deps = []
  # Build a list of dependencies that are the same in the Gemfile
  # and Gemfile.lock. If the Gemfile modified a dependency, but
  # the gem in the Gemfile.lock still satisfies it, this is fine
  # too.
  locked_deps_hash = @locked_deps.inject({}) { |hsh, dep| hsh[dep] = dep; hsh }
  @dependencies.each do |dep|
    locked_dep = locked_deps_hash[dep]
    if in_locked_deps?(dep, locked_dep) || satisfies_locked_spec?(dep)
      deps << dep
    elsif dep.source.is_a?(Source::Path) && dep.current_platform? && (!locked_dep || dep.source != locked_dep.source)
      @locked_specs.each do |s|
        @unlock[:gems] << s.name if s.source == dep.source
      end
      dep.source.unlock! if dep.source.respond_to?(:unlock!)
      dep.source.specs.each { |s| @unlock[:gems] << s.name }
    end
  end
  converged = []
  @locked_specs.each do |s|
    # Replace the locked dependency's source with the equivalent source from the Gemfile
    dep = @dependencies.find { |d| s.satisfies?(d) }
    s.source = (dep && dep.source) || sources.get(s.source)
    # Don't add a spec to the list if its source is expired. For example,
    # if you change a Git gem to Rubygems.
    next if s.source.nil? || @unlock[:sources].include?(s.name)
    # If the spec is from a path source and it doesn't exist anymore
    # then we just unlock it.
    # Path sources have special logic
    if s.source.instance_of?(Source::Path)
      other = s.source.specs[s].first
      # If the spec is no longer in the path source, unlock it. This
      # commonly happens if the version changed in the gemspec
      next unless other
      deps2 = other.dependencies.select { |d| d.type != :development }
      # If the dependencies of the path source have changed, unlock it
      next unless s.dependencies.sort == deps2.sort
    end
    converged << s
  end
  resolve = SpecSet.new(converged)
  resolve = resolve.for(expand_dependencies(deps, true), @unlock[:gems])
  diff    = @locked_specs.to_a - resolve.to_a
  # Now, we unlock any sources that do not have anymore gems pinned to it
  sources.all_sources.each do |source|
    next unless source.respond_to?(:unlock!)
    unless resolve.any? { |s| s.source == source }
      source.unlock! if !diff.empty? && diff.any? { |s| s.source == source }
    end
  end
  resolve
end