| OLD | NEW |
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 /** | 5 /** |
| 6 * Attempts to resolve a set of version constraints for a package dependency | 6 * Attempts to resolve a set of version constraints for a package dependency |
| 7 * graph and select an appropriate set of best specific versions for all | 7 * graph and select an appropriate set of best specific versions for all |
| 8 * dependent packages. It works iteratively and tries to reach a stable | 8 * dependent packages. It works iteratively and tries to reach a stable |
| 9 * solution where the constraints of all dependencies are met. If it fails to | 9 * solution where the constraints of all dependencies are met. If it fails to |
| 10 * reach a solution after a certain number of iterations, it assumes the | 10 * reach a solution after a certain number of iterations, it assumes the |
| (...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 95 // Kick off the work by adding the root package at its concrete version to | 95 // Kick off the work by adding the root package at its concrete version to |
| 96 // the dependency graph. | 96 // the dependency graph. |
| 97 var ref = new PackageRef( | 97 var ref = new PackageRef( |
| 98 _root.name, new RootSource(_root), _root.version, _root.name); | 98 _root.name, new RootSource(_root), _root.version, _root.name); |
| 99 enqueue(new AddConstraint('(entrypoint)', ref)); | 99 enqueue(new AddConstraint('(entrypoint)', ref)); |
| 100 _pubspecs.cache(ref.atVersion(_root.version), _root.pubspec); | 100 _pubspecs.cache(ref.atVersion(_root.version), _root.pubspec); |
| 101 | 101 |
| 102 Future processNextWorkItem(_) { | 102 Future processNextWorkItem(_) { |
| 103 while (true) { | 103 while (true) { |
| 104 // Stop if we are done. | 104 // Stop if we are done. |
| 105 if (_work.isEmpty()) return new Future.immediate(buildResults()); | 105 if (_work.isEmpty) return new Future.immediate(buildResults()); |
| 106 | 106 |
| 107 // If we appear to be stuck in a loop, then we probably have an unstable | 107 // If we appear to be stuck in a loop, then we probably have an unstable |
| 108 // graph, bail. We guess this based on a rough heuristic that it should | 108 // graph, bail. We guess this based on a rough heuristic that it should |
| 109 // only take a certain number of steps to solve a graph with a given | 109 // only take a certain number of steps to solve a graph with a given |
| 110 // number of connections. | 110 // number of connections. |
| 111 // TODO(rnystrom): These numbers here are magic and arbitrary. Tune | 111 // TODO(rnystrom): These numbers here are magic and arbitrary. Tune |
| 112 // when we have a better picture of real-world package topologies. | 112 // when we have a better picture of real-world package topologies. |
| 113 _numIterations++; | 113 _numIterations++; |
| 114 if (_numIterations > max(50, _packages.length * 5)) { | 114 if (_numIterations > max(50, _packages.length * 5)) { |
| 115 throw new CouldNotSolveException(); | 115 throw new CouldNotSolveException(); |
| (...skipping 422 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 538 /** | 538 /** |
| 539 * Whether this dependency should always select the latest version. | 539 * Whether this dependency should always select the latest version. |
| 540 */ | 540 */ |
| 541 bool useLatestVersion = false; | 541 bool useLatestVersion = false; |
| 542 | 542 |
| 543 /** | 543 /** |
| 544 * Gets whether or not any other packages are currently depending on this | 544 * Gets whether or not any other packages are currently depending on this |
| 545 * one. If `false`, then it means this package is not part of the dependency | 545 * one. If `false`, then it means this package is not part of the dependency |
| 546 * graph and should be omitted. | 546 * graph and should be omitted. |
| 547 */ | 547 */ |
| 548 bool get isDependedOn => !_refs.isEmpty(); | 548 bool get isDependedOn => !_refs.isEmpty; |
| 549 | 549 |
| 550 /** The names of all the packages that depend on this dependency. */ | 550 /** The names of all the packages that depend on this dependency. */ |
| 551 Collection<String> get dependers => _refs.getKeys(); | 551 Collection<String> get dependers => _refs.getKeys(); |
| 552 | 552 |
| 553 /** | 553 /** |
| 554 * Gets the overall constraint that all packages are placing on this one. | 554 * Gets the overall constraint that all packages are placing on this one. |
| 555 * If no packages have a constraint on this one (which can happen when this | 555 * If no packages have a constraint on this one (which can happen when this |
| 556 * package is in the process of being added to the graph), returns `null`. | 556 * package is in the process of being added to the graph), returns `null`. |
| 557 */ | 557 */ |
| 558 VersionConstraint get constraint { | 558 VersionConstraint get constraint { |
| 559 if (_refs.isEmpty()) return null; | 559 if (_refs.isEmpty) return null; |
| 560 return new VersionConstraint.intersect( | 560 return new VersionConstraint.intersect( |
| 561 _refs.getValues().map((ref) => ref.constraint)); | 561 _refs.getValues().map((ref) => ref.constraint)); |
| 562 } | 562 } |
| 563 | 563 |
| 564 /// The source of this dependency's package. | 564 /// The source of this dependency's package. |
| 565 Source get source { | 565 Source get source { |
| 566 var canonical = _canonicalRef(); | 566 var canonical = _canonicalRef(); |
| 567 if (canonical == null) return null; | 567 if (canonical == null) return null; |
| 568 return canonical.source; | 568 return canonical.source; |
| 569 } | 569 } |
| 570 | 570 |
| 571 /// The description of this dependency's package. | 571 /// The description of this dependency's package. |
| 572 get description { | 572 get description { |
| 573 var canonical = _canonicalRef(); | 573 var canonical = _canonicalRef(); |
| 574 if (canonical == null) return null; | 574 if (canonical == null) return null; |
| 575 return canonical.description; | 575 return canonical.description; |
| 576 } | 576 } |
| 577 | 577 |
| 578 /// Return the PackageRef that has the canonical source and description for | 578 /// Return the PackageRef that has the canonical source and description for |
| 579 /// this package. If any dependency requires that this package come from a | 579 /// this package. If any dependency requires that this package come from a |
| 580 /// [RootSource], that will be used; otherwise, it will be the source and | 580 /// [RootSource], that will be used; otherwise, it will be the source and |
| 581 /// description that all dependencies agree upon. | 581 /// description that all dependencies agree upon. |
| 582 PackageRef _canonicalRef() { | 582 PackageRef _canonicalRef() { |
| 583 if (_refs.isEmpty()) return null; | 583 if (_refs.isEmpty) return null; |
| 584 var refs = _refs.getValues(); | 584 var refs = _refs.getValues(); |
| 585 for (var ref in refs) { | 585 for (var ref in refs) { |
| 586 if (ref is RootSource) return ref; | 586 if (ref is RootSource) return ref; |
| 587 } | 587 } |
| 588 return refs[0]; | 588 return refs[0]; |
| 589 } | 589 } |
| 590 | 590 |
| 591 Dependency(this.name) | 591 Dependency(this.name) |
| 592 : _refs = <String, PackageRef>{}; | 592 : _refs = <String, PackageRef>{}; |
| 593 | 593 |
| (...skipping 23 matching lines...) Expand all Loading... |
| 617 } | 617 } |
| 618 } | 618 } |
| 619 | 619 |
| 620 _refs[package] = ref; | 620 _refs[package] = ref; |
| 621 } | 621 } |
| 622 | 622 |
| 623 /// Returns a PackageRef whose source and description any new constraints are | 623 /// Returns a PackageRef whose source and description any new constraints are |
| 624 /// required to match. Returns null if there are no requirements on new | 624 /// required to match. Returns null if there are no requirements on new |
| 625 /// constraints. | 625 /// constraints. |
| 626 PackageRef _requiredRef() { | 626 PackageRef _requiredRef() { |
| 627 if (_refs.isEmpty()) return null; | 627 if (_refs.isEmpty) return null; |
| 628 var refs = _refs.getValues(); | 628 var refs = _refs.getValues(); |
| 629 var first = refs[0]; | 629 var first = refs[0]; |
| 630 if (refs.length == 1) { | 630 if (refs.length == 1) { |
| 631 if (first.source is RootSource) return null; | 631 if (first.source is RootSource) return null; |
| 632 return first; | 632 return first; |
| 633 } | 633 } |
| 634 return refs[1]; | 634 return refs[1]; |
| 635 } | 635 } |
| 636 | 636 |
| 637 /** | 637 /** |
| (...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 724 final description1; | 724 final description1; |
| 725 final description2; | 725 final description2; |
| 726 | 726 |
| 727 DescriptionMismatchException(this.package, this.description1, | 727 DescriptionMismatchException(this.package, this.description1, |
| 728 this.description2); | 728 this.description2); |
| 729 | 729 |
| 730 // TODO(nweiz): Dump to YAML when that's supported | 730 // TODO(nweiz): Dump to YAML when that's supported |
| 731 String toString() => "Package '$package' has conflicting descriptions " | 731 String toString() => "Package '$package' has conflicting descriptions " |
| 732 "'${JSON.stringify(description1)}' and '${JSON.stringify(description2)}'"; | 732 "'${JSON.stringify(description1)}' and '${JSON.stringify(description2)}'"; |
| 733 } | 733 } |
| OLD | NEW |