solve 3.1.1 → 4.0.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +5 -5
- data/lib/solve.rb +10 -11
- data/lib/solve/artifact.rb +10 -10
- data/lib/solve/constraint.rb +47 -47
- data/lib/solve/demand.rb +2 -2
- data/lib/solve/dependency.rb +4 -2
- data/lib/solve/errors.rb +3 -3
- data/lib/solve/gecode_solver.rb +98 -95
- data/lib/solve/graph.rb +3 -3
- data/lib/solve/ruby_solver.rb +128 -63
- data/lib/solve/solver/serializer.rb +53 -53
- data/lib/solve/version.rb +1 -1
- metadata +14 -52
- data/.gitignore +0 -20
- data/.travis.yml +0 -22
- data/Gemfile +0 -33
- data/Guardfile +0 -17
- data/NoGecode.gemfile +0 -4
- data/README.md +0 -85
- data/Rakefile +0 -1
- data/Thorfile +0 -36
- data/solve.gemspec +0 -26
- data/spec/acceptance/benchmark.rb +0 -59
- data/spec/acceptance/large_graph_no_solution.rb +0 -18730
- data/spec/acceptance/opscode_ci_graph.rb +0 -18600
- data/spec/acceptance/ruby_solver_solutions_spec.rb +0 -307
- data/spec/acceptance/solutions_spec.rb +0 -317
- data/spec/spec_helper.rb +0 -25
- data/spec/unit/solve/artifact_spec.rb +0 -137
- data/spec/unit/solve/demand_spec.rb +0 -53
- data/spec/unit/solve/dependency_spec.rb +0 -25
- data/spec/unit/solve/gecode_solver_spec.rb +0 -206
- data/spec/unit/solve/graph_spec.rb +0 -130
- data/spec/unit/solve/ruby_solver_spec.rb +0 -166
- data/spec/unit/solve/solver/serializer_spec.rb +0 -33
- data/spec/unit/solve_spec.rb +0 -19
    
        data/lib/solve/graph.rb
    CHANGED
    
    | @@ -67,7 +67,7 @@ module Solve | |
| 67 67 | 
             
                  return false unless other.is_a?(Graph)
         | 
| 68 68 | 
             
                  return false unless artifacts.size == other.artifacts.size
         | 
| 69 69 |  | 
| 70 | 
            -
                  self_artifacts =  | 
| 70 | 
            +
                  self_artifacts = artifacts
         | 
| 71 71 | 
             
                  other_artifacts = other.artifacts
         | 
| 72 72 |  | 
| 73 73 | 
             
                  self_dependencies = self_artifacts.inject([]) do |list, artifact|
         | 
| @@ -79,8 +79,8 @@ module Solve | |
| 79 79 | 
             
                  end.flatten
         | 
| 80 80 |  | 
| 81 81 | 
             
                  self_dependencies.size == other_dependencies.size &&
         | 
| 82 | 
            -
             | 
| 83 | 
            -
             | 
| 82 | 
            +
                    self_artifacts.all? { |artifact| other_artifacts.include?(artifact) } &&
         | 
| 83 | 
            +
                    self_dependencies.all? { |dependency| other_dependencies.include?(dependency) }
         | 
| 84 84 | 
             
                end
         | 
| 85 85 | 
             
                alias_method :eql?, :==
         | 
| 86 86 | 
             
              end
         | 
    
        data/lib/solve/ruby_solver.rb
    CHANGED
    
    | @@ -1,6 +1,7 @@ | |
| 1 | 
            -
            require  | 
| 2 | 
            -
            require  | 
| 3 | 
            -
             | 
| 1 | 
            +
            require "set" unless defined?(Set)
         | 
| 2 | 
            +
            require "molinillo"
         | 
| 3 | 
            +
            require "molinillo/modules/specification_provider"
         | 
| 4 | 
            +
            require_relative "solver/serializer"
         | 
| 4 5 |  | 
| 5 6 | 
             
            module Solve
         | 
| 6 7 | 
             
              class RubySolver
         | 
| @@ -10,11 +11,11 @@ module Solve | |
| 10 11 | 
             
                  #
         | 
| 11 12 | 
             
                  # @return [Integer]
         | 
| 12 13 | 
             
                  def timeout
         | 
| 13 | 
            -
                    seconds = 30 unless seconds = ENV["SOLVE_TIMEOUT"]
         | 
| 14 | 
            +
                    seconds = 30 unless ( seconds = ENV["SOLVE_TIMEOUT"] )
         | 
| 14 15 | 
             
                    seconds.to_i * 1_000
         | 
| 15 16 | 
             
                  end
         | 
| 16 17 |  | 
| 17 | 
            -
                  # For  | 
| 18 | 
            +
                  # For optional solver engines, this attempts to load depenencies. The
         | 
| 18 19 | 
             
                  # RubySolver is a non-optional component, so this is a no-op
         | 
| 19 20 | 
             
                  def activate
         | 
| 20 21 | 
             
                    true
         | 
| @@ -45,7 +46,7 @@ module Solve | |
| 45 46 | 
             
                  @timeout_ms    = self.class.timeout
         | 
| 46 47 |  | 
| 47 48 | 
             
                  @ui = options[:ui] # could be nil, but that's okay
         | 
| 48 | 
            -
                  @dependency_source = options[:dependency_source] ||  | 
| 49 | 
            +
                  @dependency_source = options[:dependency_source] || "user-specified dependency"
         | 
| 49 50 |  | 
| 50 51 | 
             
                  @molinillo_graph = Molinillo::DependencyGraph.new
         | 
| 51 52 | 
             
                  @resolver = Molinillo::Resolver.new(self, self)
         | 
| @@ -74,10 +75,10 @@ module Solve | |
| 74 75 |  | 
| 75 76 | 
             
                  solved_graph = resolve_with_error_wrapping
         | 
| 76 77 |  | 
| 77 | 
            -
                  solution = | 
| 78 | 
            +
                  solution = solved_graph.map(&:payload)
         | 
| 78 79 |  | 
| 79 80 | 
             
                  unsorted_solution = solution.inject({}) do |stringified_soln, artifact|
         | 
| 80 | 
            -
                    stringified_soln[artifact.name] = artifact.version.to_s | 
| 81 | 
            +
                    stringified_soln[artifact.name] = artifact.version.to_s
         | 
| 81 82 | 
             
                    stringified_soln
         | 
| 82 83 | 
             
                  end
         | 
| 83 84 |  | 
| @@ -106,13 +107,13 @@ module Solve | |
| 106 107 | 
             
                # Callback required by Molinillo, called when the solve starts
         | 
| 107 108 | 
             
                # @return nil
         | 
| 108 109 | 
             
                def before_resolution
         | 
| 109 | 
            -
                  @ui.say( | 
| 110 | 
            +
                  @ui.say("Starting dependency resolution") if @ui
         | 
| 110 111 | 
             
                end
         | 
| 111 112 |  | 
| 112 113 | 
             
                # Callback required by Molinillo, called when the solve is complete.
         | 
| 113 114 | 
             
                # @return nil
         | 
| 114 115 | 
             
                def after_resolution
         | 
| 115 | 
            -
                  @ui.say( | 
| 116 | 
            +
                  @ui.say("Finished dependency resolution") if @ui
         | 
| 116 117 | 
             
                end
         | 
| 117 118 |  | 
| 118 119 | 
             
                # Callback required by Molinillo, called when resolving every progress_rate
         | 
| @@ -123,32 +124,22 @@ module Solve | |
| 123 124 |  | 
| 124 125 | 
             
                # Callback required by Molinillo, gives debug information about the solution
         | 
| 125 126 | 
             
                # @return nil
         | 
| 126 | 
            -
                def debug(current_resolver_depth)
         | 
| 127 | 
            +
                def debug(current_resolver_depth = 0)
         | 
| 127 128 | 
             
                  # debug info will be returned if you call yield here, but it seems to be
         | 
| 128 129 | 
             
                  # broken in current Molinillo
         | 
| 129 130 | 
             
                  @ui.say(yield) if @ui
         | 
| 130 131 | 
             
                end
         | 
| 131 132 |  | 
| 132 | 
            -
                 | 
| 133 | 
            -
                # @return [String] the dependency's name
         | 
| 134 | 
            -
                def name_for(dependency)
         | 
| 135 | 
            -
                  dependency.name
         | 
| 136 | 
            -
                end
         | 
| 137 | 
            -
             | 
| 138 | 
            -
                # Callback required by Molinillo
         | 
| 139 | 
            -
                # @return [Array<Solve::Dependency>] the dependencies sorted by preference.
         | 
| 140 | 
            -
                def sort_dependencies(dependencies, activated, conflicts)
         | 
| 141 | 
            -
                  dependencies.sort_by do |dependency|
         | 
| 142 | 
            -
                    name = name_for(dependency)
         | 
| 143 | 
            -
                    [
         | 
| 144 | 
            -
                      activated.vertex_named(name).payload ? 0 : 1,
         | 
| 145 | 
            -
                      conflicts[name] ? 0 : 1,
         | 
| 146 | 
            -
                      activated.vertex_named(name).payload ? 0 : graph.versions(dependency.name).count,
         | 
| 147 | 
            -
                    ]
         | 
| 148 | 
            -
                  end
         | 
| 149 | 
            -
                end
         | 
| 133 | 
            +
                include Molinillo::SpecificationProvider
         | 
| 150 134 |  | 
| 151 135 | 
             
                # Callback required by Molinillo
         | 
| 136 | 
            +
                # Search for the specifications that match the given dependency.
         | 
| 137 | 
            +
                # The specifications in the returned array will be considered in reverse
         | 
| 138 | 
            +
                # order, so the latest version ought to be last.
         | 
| 139 | 
            +
                # @note This method should be 'pure', i.e. the return value should depend
         | 
| 140 | 
            +
                #   only on the `dependency` parameter.
         | 
| 141 | 
            +
                #
         | 
| 142 | 
            +
                # @param [Object] dependency
         | 
| 152 143 | 
             
                # @return [Array<Solve::Artifact>] the artifacts that match the dependency.
         | 
| 153 144 | 
             
                def search_for(dependency)
         | 
| 154 145 | 
             
                  # This array gets mutated by Molinillo; it's okay because sort returns a
         | 
| @@ -157,29 +148,103 @@ module Solve | |
| 157 148 | 
             
                end
         | 
| 158 149 |  | 
| 159 150 | 
             
                # Callback required by Molinillo
         | 
| 160 | 
            -
                #  | 
| 151 | 
            +
                # Returns the dependencies of `specification`.
         | 
| 152 | 
            +
                # @note This method should be 'pure', i.e. the return value should depend
         | 
| 153 | 
            +
                #   only on the `specification` parameter.
         | 
| 154 | 
            +
                #
         | 
| 155 | 
            +
                # @param [Object] specification
         | 
| 156 | 
            +
                # @return [Array<Solve::Dependency>] the dependencies of the given artifact
         | 
| 157 | 
            +
                def dependencies_for(specification)
         | 
| 158 | 
            +
                  specification.dependencies
         | 
| 159 | 
            +
                end
         | 
| 160 | 
            +
             | 
| 161 | 
            +
                # Callback required by Molinillo
         | 
| 162 | 
            +
                # Determines whether the given `requirement` is satisfied by the given
         | 
| 163 | 
            +
                # `spec`, in the context of the current `activated` dependency graph.
         | 
| 164 | 
            +
                #
         | 
| 165 | 
            +
                # @param [Object] requirement
         | 
| 166 | 
            +
                # @param [DependencyGraph] activated the current dependency graph in the
         | 
| 167 | 
            +
                #   resolution process.
         | 
| 168 | 
            +
                # @param [Object] spec
         | 
| 169 | 
            +
                # @return [Boolean] whether `requirement` is satisfied by `spec` in the
         | 
| 170 | 
            +
                #   context of the current `activated` dependency graph.
         | 
| 161 171 | 
             
                def requirement_satisfied_by?(requirement, activated, spec)
         | 
| 162 | 
            -
                   | 
| 172 | 
            +
                  version = spec.version
         | 
| 173 | 
            +
                  return false unless requirement.constraint.satisfies?(version)
         | 
| 174 | 
            +
             | 
| 175 | 
            +
                  shared_possibility_versions = possibility_versions(requirement, activated)
         | 
| 176 | 
            +
                  return false if !shared_possibility_versions.empty? && !shared_possibility_versions.include?(version)
         | 
| 177 | 
            +
             | 
| 178 | 
            +
                  true
         | 
| 163 179 | 
             
                end
         | 
| 164 180 |  | 
| 181 | 
            +
                # Searches the current dependency graph to find previously activated
         | 
| 182 | 
            +
                # requirements for the current artifact.
         | 
| 183 | 
            +
                #
         | 
| 184 | 
            +
                # @param [Object] requirement
         | 
| 185 | 
            +
                # @param [DependencyGraph] activated the current dependency graph in the
         | 
| 186 | 
            +
                #   resolution process.
         | 
| 187 | 
            +
                # @return [Array<Semverse::Version> the list of currently activated versions
         | 
| 188 | 
            +
                # of this requirement
         | 
| 189 | 
            +
                def possibility_versions(requirement, activated)
         | 
| 190 | 
            +
                  activated.vertices.values.flat_map do |vertex|
         | 
| 191 | 
            +
             | 
| 192 | 
            +
                    next unless vertex.payload
         | 
| 193 | 
            +
             | 
| 194 | 
            +
                    next unless vertex.name == requirement.name
         | 
| 195 | 
            +
             | 
| 196 | 
            +
                    if vertex.payload.respond_to?(:possibilities)
         | 
| 197 | 
            +
                      vertex.payload.possibilities.map(&:version)
         | 
| 198 | 
            +
                    else
         | 
| 199 | 
            +
                      vertex.payload.version
         | 
| 200 | 
            +
                    end
         | 
| 201 | 
            +
                  end.compact
         | 
| 202 | 
            +
                end
         | 
| 203 | 
            +
                private :possibility_versions
         | 
| 204 | 
            +
             | 
| 165 205 | 
             
                # Callback required by Molinillo
         | 
| 166 | 
            -
                #  | 
| 167 | 
            -
                 | 
| 168 | 
            -
             | 
| 206 | 
            +
                # Returns the name for the given `dependency`.
         | 
| 207 | 
            +
                # @note This method should be 'pure', i.e. the return value should depend
         | 
| 208 | 
            +
                #   only on the `dependency` parameter.
         | 
| 209 | 
            +
                #
         | 
| 210 | 
            +
                # @param [Object] dependency
         | 
| 211 | 
            +
                # @return [String] the name for the given `dependency`.
         | 
| 212 | 
            +
                def name_for(dependency)
         | 
| 213 | 
            +
                  dependency.name
         | 
| 169 214 | 
             
                end
         | 
| 170 215 |  | 
| 216 | 
            +
                # Callback required by Molinillo
         | 
| 171 217 | 
             
                # @return [String] the name of the source of explicit dependencies, i.e.
         | 
| 172 218 | 
             
                #   those passed to {Resolver#resolve} directly.
         | 
| 173 219 | 
             
                def name_for_explicit_dependency_source
         | 
| 174 220 | 
             
                  @dependency_source
         | 
| 175 221 | 
             
                end
         | 
| 176 222 |  | 
| 177 | 
            -
                #  | 
| 178 | 
            -
                # | 
| 179 | 
            -
                 | 
| 180 | 
            -
             | 
| 223 | 
            +
                # Callback required by Molinillo
         | 
| 224 | 
            +
                # Sort dependencies so that the ones that are easiest to resolve are first.
         | 
| 225 | 
            +
                # Easiest to resolve is (usually) defined by:
         | 
| 226 | 
            +
                #   1) Is this dependency already activated?
         | 
| 227 | 
            +
                #   2) How relaxed are the requirements?
         | 
| 228 | 
            +
                #   3) Are there any conflicts for this dependency?
         | 
| 229 | 
            +
                #   4) How many possibilities are there to satisfy this dependency?
         | 
| 230 | 
            +
                #
         | 
| 231 | 
            +
                # @param [Array<Object>] dependencies
         | 
| 232 | 
            +
                # @param [DependencyGraph] activated the current dependency graph in the
         | 
| 233 | 
            +
                #   resolution process.
         | 
| 234 | 
            +
                # @param [{String => Array<Conflict>}] conflicts
         | 
| 235 | 
            +
                # @return [Array<Solve::Dependency>] the dependencies sorted by preference.
         | 
| 236 | 
            +
                def sort_dependencies(dependencies, activated, conflicts)
         | 
| 237 | 
            +
                  dependencies.sort_by do |dependency|
         | 
| 238 | 
            +
                    name = name_for(dependency)
         | 
| 239 | 
            +
                    [
         | 
| 240 | 
            +
                      activated.vertex_named(name).payload ? 0 : 1,
         | 
| 241 | 
            +
                      conflicts[name] ? 0 : 1,
         | 
| 242 | 
            +
                      search_for(dependency).count,
         | 
| 243 | 
            +
                    ]
         | 
| 244 | 
            +
                  end
         | 
| 181 245 | 
             
                end
         | 
| 182 246 |  | 
| 247 | 
            +
                # Callback required by Molinillo
         | 
| 183 248 | 
             
                # Returns whether this dependency, which has no possible matching
         | 
| 184 249 | 
             
                # specifications, can safely be ignored.
         | 
| 185 250 | 
             
                #
         | 
| @@ -191,35 +256,35 @@ module Solve | |
| 191 256 |  | 
| 192 257 | 
             
                private
         | 
| 193 258 |  | 
| 194 | 
            -
             | 
| 195 | 
            -
             | 
| 196 | 
            -
             | 
| 197 | 
            -
             | 
| 198 | 
            -
             | 
| 259 | 
            +
                def resolve_with_error_wrapping
         | 
| 260 | 
            +
                  @resolver.resolve(demands, @molinillo_graph)
         | 
| 261 | 
            +
                rescue Molinillo::VersionConflict, Molinillo::CircularDependencyError => e
         | 
| 262 | 
            +
                  raise Solve::Errors::NoSolutionError.new(e.message)
         | 
| 263 | 
            +
                end
         | 
| 199 264 |  | 
| 200 | 
            -
             | 
| 201 | 
            -
             | 
| 202 | 
            -
             | 
| 203 | 
            -
             | 
| 204 | 
            -
             | 
| 265 | 
            +
                def build_sorted_solution(unsorted_solution)
         | 
| 266 | 
            +
                  nodes = {}
         | 
| 267 | 
            +
                  unsorted_solution.each do |name, version|
         | 
| 268 | 
            +
                    nodes[name] = @graph.artifact(name, version).dependencies.map(&:name)
         | 
| 269 | 
            +
                  end
         | 
| 205 270 |  | 
| 206 | 
            -
             | 
| 207 | 
            -
             | 
| 208 | 
            -
             | 
| 209 | 
            -
             | 
| 210 | 
            -
             | 
| 211 | 
            -
             | 
| 212 | 
            -
                      end
         | 
| 213 | 
            -
                    end
         | 
| 214 | 
            -
                    begin
         | 
| 215 | 
            -
                      sorted_names = nodes.tsort
         | 
| 216 | 
            -
                    rescue TSort::Cyclic => e
         | 
| 217 | 
            -
                      raise Solve::Errors::UnsortableSolutionError.new(e, unsorted_solution)
         | 
| 271 | 
            +
                  # Modified from http://ruby-doc.org/stdlib-1.9.3/libdoc/tsort/rdoc/TSort.html
         | 
| 272 | 
            +
                  class << nodes
         | 
| 273 | 
            +
                    include TSort
         | 
| 274 | 
            +
                    alias tsort_each_node each_key
         | 
| 275 | 
            +
                    def tsort_each_child(node, &block)
         | 
| 276 | 
            +
                      fetch(node).each(&block)
         | 
| 218 277 | 
             
                    end
         | 
| 278 | 
            +
                  end
         | 
| 279 | 
            +
                  begin
         | 
| 280 | 
            +
                    sorted_names = nodes.tsort
         | 
| 281 | 
            +
                  rescue TSort::Cyclic => e
         | 
| 282 | 
            +
                    raise Solve::Errors::UnsortableSolutionError.new(e, unsorted_solution)
         | 
| 283 | 
            +
                  end
         | 
| 219 284 |  | 
| 220 | 
            -
             | 
| 221 | 
            -
             | 
| 222 | 
            -
                    end
         | 
| 285 | 
            +
                  sorted_names.map do |artifact|
         | 
| 286 | 
            +
                    [artifact, unsorted_solution[artifact]]
         | 
| 223 287 | 
             
                  end
         | 
| 288 | 
            +
                end
         | 
| 224 289 | 
             
              end
         | 
| 225 290 | 
             
            end
         | 
| @@ -1,5 +1,5 @@ | |
| 1 | 
            -
            require  | 
| 2 | 
            -
             | 
| 1 | 
            +
            require "json" unless defined?(JSON)
         | 
| 2 | 
            +
            require_relative "../graph"
         | 
| 3 3 |  | 
| 4 4 | 
             
            module Solve
         | 
| 5 5 |  | 
| @@ -58,71 +58,71 @@ module Solve | |
| 58 58 |  | 
| 59 59 | 
             
                  private
         | 
| 60 60 |  | 
| 61 | 
            -
             | 
| 62 | 
            -
             | 
| 63 | 
            -
             | 
| 64 | 
            -
                      end
         | 
| 65 | 
            -
                      { "graph" => artifacts }
         | 
| 61 | 
            +
                  def format_graph(graph)
         | 
| 62 | 
            +
                    artifacts = graph.artifacts.inject([]) do |list, artifact|
         | 
| 63 | 
            +
                      list << format_artifact(artifact)
         | 
| 66 64 | 
             
                    end
         | 
| 65 | 
            +
                    { "graph" => artifacts }
         | 
| 66 | 
            +
                  end
         | 
| 67 67 |  | 
| 68 | 
            -
             | 
| 69 | 
            -
             | 
| 70 | 
            -
             | 
| 71 | 
            -
                      end
         | 
| 72 | 
            -
             | 
| 73 | 
            -
                      {
         | 
| 74 | 
            -
                        "name" => artifact.name,
         | 
| 75 | 
            -
                        "version" => artifact.version.to_s,
         | 
| 76 | 
            -
                        "dependencies" => dependencies
         | 
| 77 | 
            -
                      }
         | 
| 68 | 
            +
                  def format_artifact(artifact)
         | 
| 69 | 
            +
                    dependencies = artifact.dependencies.inject([]) do |list, dependency|
         | 
| 70 | 
            +
                      list << format_dependency(dependency)
         | 
| 78 71 | 
             
                    end
         | 
| 79 72 |  | 
| 80 | 
            -
                     | 
| 81 | 
            -
                       | 
| 82 | 
            -
             | 
| 83 | 
            -
             | 
| 84 | 
            -
             | 
| 85 | 
            -
             | 
| 73 | 
            +
                    {
         | 
| 74 | 
            +
                      "name" => artifact.name,
         | 
| 75 | 
            +
                      "version" => artifact.version.to_s,
         | 
| 76 | 
            +
                      "dependencies" => dependencies,
         | 
| 77 | 
            +
                    }
         | 
| 78 | 
            +
                  end
         | 
| 86 79 |  | 
| 87 | 
            -
             | 
| 88 | 
            -
             | 
| 89 | 
            -
             | 
| 90 | 
            -
                       | 
| 91 | 
            -
             | 
| 92 | 
            -
             | 
| 80 | 
            +
                  def format_dependency(dependency)
         | 
| 81 | 
            +
                    {
         | 
| 82 | 
            +
                      "name" => dependency.name,
         | 
| 83 | 
            +
                      "constraint" => dependency.constraint.to_s,
         | 
| 84 | 
            +
                    }
         | 
| 85 | 
            +
                  end
         | 
| 93 86 |  | 
| 94 | 
            -
             | 
| 95 | 
            -
             | 
| 96 | 
            -
             | 
| 97 | 
            -
                        "constraint" => demand[1]
         | 
| 98 | 
            -
                      }
         | 
| 87 | 
            +
                  def format_demands(demands)
         | 
| 88 | 
            +
                    demands_list = demands.inject([]) do |list, demand|
         | 
| 89 | 
            +
                      list << format_demand(demand)
         | 
| 99 90 | 
             
                    end
         | 
| 91 | 
            +
                    { "demands" => demands_list }
         | 
| 92 | 
            +
                  end
         | 
| 100 93 |  | 
| 101 | 
            -
             | 
| 102 | 
            -
             | 
| 103 | 
            -
                       | 
| 104 | 
            -
             | 
| 105 | 
            -
             | 
| 106 | 
            -
             | 
| 107 | 
            -
                    end
         | 
| 94 | 
            +
                  def format_demand(demand)
         | 
| 95 | 
            +
                    {
         | 
| 96 | 
            +
                      "name" => demand[0],
         | 
| 97 | 
            +
                      "constraint" => demand[1],
         | 
| 98 | 
            +
                    }
         | 
| 99 | 
            +
                  end
         | 
| 108 100 |  | 
| 109 | 
            -
             | 
| 110 | 
            -
             | 
| 111 | 
            -
             | 
| 112 | 
            -
             | 
| 113 | 
            -
                      end
         | 
| 114 | 
            -
                      artifact
         | 
| 101 | 
            +
                  def load_graph(artifacts_list)
         | 
| 102 | 
            +
                    graph = Solve::Graph.new
         | 
| 103 | 
            +
                    artifacts_list.each do |artifact_spec|
         | 
| 104 | 
            +
                      load_artifact(graph, artifact_spec)
         | 
| 115 105 | 
             
                    end
         | 
| 106 | 
            +
                    graph
         | 
| 107 | 
            +
                  end
         | 
| 116 108 |  | 
| 117 | 
            -
             | 
| 118 | 
            -
             | 
| 109 | 
            +
                  def load_artifact(graph, artifact_spec)
         | 
| 110 | 
            +
                    artifact = graph.artifact(artifact_spec["name"], artifact_spec["version"])
         | 
| 111 | 
            +
                    artifact_spec["dependencies"].each do |dependency_spec|
         | 
| 112 | 
            +
                      load_dependency(artifact, dependency_spec)
         | 
| 119 113 | 
             
                    end
         | 
| 114 | 
            +
                    artifact
         | 
| 115 | 
            +
                  end
         | 
| 120 116 |  | 
| 121 | 
            -
             | 
| 122 | 
            -
             | 
| 123 | 
            -
             | 
| 124 | 
            -
             | 
| 117 | 
            +
                  def load_dependency(artifact, dependency_spec)
         | 
| 118 | 
            +
                    artifact.depends(dependency_spec["name"], dependency_spec["constraint"])
         | 
| 119 | 
            +
                  end
         | 
| 120 | 
            +
             | 
| 121 | 
            +
                  def load_demands(demand_specs)
         | 
| 122 | 
            +
                    demand_specs.inject([]) do |list, demand_spec|
         | 
| 123 | 
            +
                      list << [demand_spec["name"], demand_spec["constraint"]]
         | 
| 125 124 | 
             
                    end
         | 
| 125 | 
            +
                  end
         | 
| 126 126 | 
             
                end
         | 
| 127 127 | 
             
              end
         | 
| 128 128 | 
             
            end
         | 
    
        data/lib/solve/version.rb
    CHANGED
    
    
    
        metadata
    CHANGED
    
    | @@ -1,16 +1,16 @@ | |
| 1 1 | 
             
            --- !ruby/object:Gem::Specification
         | 
| 2 2 | 
             
            name: solve
         | 
| 3 3 | 
             
            version: !ruby/object:Gem::Version
         | 
| 4 | 
            -
              version:  | 
| 4 | 
            +
              version: 4.0.4
         | 
| 5 5 | 
             
            platform: ruby
         | 
| 6 6 | 
             
            authors:
         | 
| 7 7 | 
             
            - Jamie Winsor
         | 
| 8 8 | 
             
            - Andrew Garson
         | 
| 9 9 | 
             
            - Thibaud Guillaume-Gentil
         | 
| 10 | 
            -
            autorequire: | 
| 10 | 
            +
            autorequire:
         | 
| 11 11 | 
             
            bindir: bin
         | 
| 12 12 | 
             
            cert_chain: []
         | 
| 13 | 
            -
            date:  | 
| 13 | 
            +
            date: 2020-08-17 00:00:00.000000000 Z
         | 
| 14 14 | 
             
            dependencies:
         | 
| 15 15 | 
             
            - !ruby/object:Gem::Dependency
         | 
| 16 16 | 
             
              name: semverse
         | 
| @@ -21,7 +21,7 @@ dependencies: | |
| 21 21 | 
             
                    version: '1.1'
         | 
| 22 22 | 
             
                - - "<"
         | 
| 23 23 | 
             
                  - !ruby/object:Gem::Version
         | 
| 24 | 
            -
                    version: ' | 
| 24 | 
            +
                    version: '4.0'
         | 
| 25 25 | 
             
              type: :runtime
         | 
| 26 26 | 
             
              prerelease: false
         | 
| 27 27 | 
             
              version_requirements: !ruby/object:Gem::Requirement
         | 
| @@ -31,21 +31,21 @@ dependencies: | |
| 31 31 | 
             
                    version: '1.1'
         | 
| 32 32 | 
             
                - - "<"
         | 
| 33 33 | 
             
                  - !ruby/object:Gem::Version
         | 
| 34 | 
            -
                    version: ' | 
| 34 | 
            +
                    version: '4.0'
         | 
| 35 35 | 
             
            - !ruby/object:Gem::Dependency
         | 
| 36 36 | 
             
              name: molinillo
         | 
| 37 37 | 
             
              requirement: !ruby/object:Gem::Requirement
         | 
| 38 38 | 
             
                requirements:
         | 
| 39 | 
            -
                - - " | 
| 39 | 
            +
                - - "~>"
         | 
| 40 40 | 
             
                  - !ruby/object:Gem::Version
         | 
| 41 | 
            -
                    version: '0. | 
| 41 | 
            +
                    version: '0.6'
         | 
| 42 42 | 
             
              type: :runtime
         | 
| 43 43 | 
             
              prerelease: false
         | 
| 44 44 | 
             
              version_requirements: !ruby/object:Gem::Requirement
         | 
| 45 45 | 
             
                requirements:
         | 
| 46 | 
            -
                - - " | 
| 46 | 
            +
                - - "~>"
         | 
| 47 47 | 
             
                  - !ruby/object:Gem::Version
         | 
| 48 | 
            -
                    version: '0. | 
| 48 | 
            +
                    version: '0.6'
         | 
| 49 49 | 
             
            - !ruby/object:Gem::Dependency
         | 
| 50 50 | 
             
              name: thor
         | 
| 51 51 | 
             
              requirement: !ruby/object:Gem::Requirement
         | 
| @@ -111,15 +111,7 @@ executables: [] | |
| 111 111 | 
             
            extensions: []
         | 
| 112 112 | 
             
            extra_rdoc_files: []
         | 
| 113 113 | 
             
            files:
         | 
| 114 | 
            -
            - ".gitignore"
         | 
| 115 | 
            -
            - ".travis.yml"
         | 
| 116 | 
            -
            - Gemfile
         | 
| 117 | 
            -
            - Guardfile
         | 
| 118 114 | 
             
            - LICENSE
         | 
| 119 | 
            -
            - NoGecode.gemfile
         | 
| 120 | 
            -
            - README.md
         | 
| 121 | 
            -
            - Rakefile
         | 
| 122 | 
            -
            - Thorfile
         | 
| 123 115 | 
             
            - lib/solve.rb
         | 
| 124 116 | 
             
            - lib/solve/artifact.rb
         | 
| 125 117 | 
             
            - lib/solve/constraint.rb
         | 
| @@ -131,26 +123,11 @@ files: | |
| 131 123 | 
             
            - lib/solve/ruby_solver.rb
         | 
| 132 124 | 
             
            - lib/solve/solver/serializer.rb
         | 
| 133 125 | 
             
            - lib/solve/version.rb
         | 
| 134 | 
            -
            - solve.gemspec
         | 
| 135 | 
            -
            - spec/acceptance/benchmark.rb
         | 
| 136 | 
            -
            - spec/acceptance/large_graph_no_solution.rb
         | 
| 137 | 
            -
            - spec/acceptance/opscode_ci_graph.rb
         | 
| 138 | 
            -
            - spec/acceptance/ruby_solver_solutions_spec.rb
         | 
| 139 | 
            -
            - spec/acceptance/solutions_spec.rb
         | 
| 140 | 
            -
            - spec/spec_helper.rb
         | 
| 141 | 
            -
            - spec/unit/solve/artifact_spec.rb
         | 
| 142 | 
            -
            - spec/unit/solve/demand_spec.rb
         | 
| 143 | 
            -
            - spec/unit/solve/dependency_spec.rb
         | 
| 144 | 
            -
            - spec/unit/solve/gecode_solver_spec.rb
         | 
| 145 | 
            -
            - spec/unit/solve/graph_spec.rb
         | 
| 146 | 
            -
            - spec/unit/solve/ruby_solver_spec.rb
         | 
| 147 | 
            -
            - spec/unit/solve/solver/serializer_spec.rb
         | 
| 148 | 
            -
            - spec/unit/solve_spec.rb
         | 
| 149 126 | 
             
            homepage: https://github.com/berkshelf/solve
         | 
| 150 127 | 
             
            licenses:
         | 
| 151 | 
            -
            - Apache | 
| 128 | 
            +
            - Apache-2.0
         | 
| 152 129 | 
             
            metadata: {}
         | 
| 153 | 
            -
            post_install_message: | 
| 130 | 
            +
            post_install_message:
         | 
| 154 131 | 
             
            rdoc_options: []
         | 
| 155 132 | 
             
            require_paths:
         | 
| 156 133 | 
             
            - lib
         | 
| @@ -165,23 +142,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement | |
| 165 142 | 
             
                - !ruby/object:Gem::Version
         | 
| 166 143 | 
             
                  version: '0'
         | 
| 167 144 | 
             
            requirements: []
         | 
| 168 | 
            -
             | 
| 169 | 
            -
             | 
| 170 | 
            -
            signing_key: 
         | 
| 145 | 
            +
            rubygems_version: 3.1.2
         | 
| 146 | 
            +
            signing_key:
         | 
| 171 147 | 
             
            specification_version: 4
         | 
| 172 148 | 
             
            summary: A Ruby version constraint solver implementing Semantic Versioning 2.0.0-rc.1
         | 
| 173 | 
            -
            test_files:
         | 
| 174 | 
            -
            - spec/acceptance/benchmark.rb
         | 
| 175 | 
            -
            - spec/acceptance/large_graph_no_solution.rb
         | 
| 176 | 
            -
            - spec/acceptance/opscode_ci_graph.rb
         | 
| 177 | 
            -
            - spec/acceptance/ruby_solver_solutions_spec.rb
         | 
| 178 | 
            -
            - spec/acceptance/solutions_spec.rb
         | 
| 179 | 
            -
            - spec/spec_helper.rb
         | 
| 180 | 
            -
            - spec/unit/solve/artifact_spec.rb
         | 
| 181 | 
            -
            - spec/unit/solve/demand_spec.rb
         | 
| 182 | 
            -
            - spec/unit/solve/dependency_spec.rb
         | 
| 183 | 
            -
            - spec/unit/solve/gecode_solver_spec.rb
         | 
| 184 | 
            -
            - spec/unit/solve/graph_spec.rb
         | 
| 185 | 
            -
            - spec/unit/solve/ruby_solver_spec.rb
         | 
| 186 | 
            -
            - spec/unit/solve/solver/serializer_spec.rb
         | 
| 187 | 
            -
            - spec/unit/solve_spec.rb
         | 
| 149 | 
            +
            test_files: []
         |