diff --git a/lib/src/solver/deducer.dart b/lib/src/solver/deducer.dart
index 252d92a650ccb881ad5c76a9962196fca7ed8a22..0785f0fe25e69fb16822b0a929c023c94420b3cc 100644
--- a/lib/src/solver/deducer.dart
+++ b/lib/src/solver/deducer.dart
@@ -286,6 +286,98 @@ class Deducer {
     }
   }
 
+  Dependency _dependencyIntoDependency(Dependency fact) {
+    // Check whether [fact] can be merged with other dependencies with the same
+    // depender and allowed.
+    for (var dependency in _dependenciesByDepender(fact.depender.toRef())) {
+      if (dependency.allowed.toRef() != fact.allowed.toRef()) continue;
+
+      if (dependency.allowed.constraint == fact.allowed.constraint) {
+        // If [fact] has the same allowed constraint as [dependency], they can
+        // be merged.
+
+        var merged = _mergeDeps([dependency.depender, fact.depender]);
+        if (merged.constraint != dependency.depender.constraint) {
+          // If [fact] adds new information to [dependency], create a new
+          // dependency for it.
+          _removeDependency(dependency);
+          _dependenciesByDepender[fact.depender.toRef()] =
+              new Dependency(merged, fact.allowed, [dependency, fact]);
+        }
+
+        return null;
+      } else if (
+          dependency.depender.constraint.allowsAny(fact.depender.constraint)) {
+        // If [fact] has a different allowed constraint than [dependency] but
+        // their dependers overlap, remove the part that's overlapping and maybe
+        // create a new narrower constraint from the overlap.
+
+        if (fact.allowed.constraint.allowsAll(dependency.allowed.constraint)) {
+          // If [fact] allows strictly more versions than [dependency], remove
+          // any overlap from [fact] because it's less specific.
+          var difference = fact.depender.constraint.difference(
+              dependency.depender.constraint);
+          if (difference.isEmpty) return null;
+
+          fact = new Dependency(
+              fact.depender.withConstraint(difference), 
+              fact.allowed,
+              [dependency, fact]);
+        } else if (dependency.allowed.constraint
+            .allowsAll(fact.allowed.constraint)) {
+          _removeDependency(dependency);
+
+          // If [dependency] allows strictly more versions than [fact], remove
+          // any overlap from [dependency] because it's less specific.
+          var difference = dependency.depender.constraint.difference(
+              fact.depender.constraint);
+          if (difference.isEmpty) continue;
+
+          _toProcess.add(new Dependency(
+              dependency.depender.withConstraint(difference),
+              dependency.allowed,
+              [dependency, fact]));
+        } else {
+          // If [fact] and [dependency]'s allowed targets overlap without one
+          // being a subset of the other, we need to create a third dependency
+          // that represents the intersection.
+          _removeDependency(dependency);
+
+          var intersection = _intersectDeps(dependency.depender, fact.depender);
+          _toProcess.add(new Dependency(
+              intersection,
+              _intersectDeps(dependency.allowed, fact.allowed),
+              [dependency, fact]));
+
+          if (!intersection.constraint.allowsAll(
+              dependency.depender.constraint)) {
+            // If [intersection] covers the entirety of [dependency], throw it
+            // away; otherwise, trim it to exclude [intersection].
+            _toProcess.add(new Dependency(
+                dependency.depender.withConstraint(
+                    dependency.depender.constraint.difference(
+                        intersection.constraint)),
+                dependency.allowed,
+                [dependency, fact]));
+          }
+
+          if (!intersection.constraint.allowsAll(fact.depender.constraint)) {
+            // If [intersection] covers the entirety of [fact], throw it away;
+            // otherwise, trim it to exclude [intersection].
+            fact = new Dependency(
+                fact.depender.withConstraint(
+                    fact.depender.constraint.difference(
+                        intersection.constraint)),
+                fact.allowed,
+                [dependency, fact]);
+          } else {
+            return null;
+          }
+        }
+      }
+    }
+  }
+
   // Resolves [required] and [disallowed], which should refer to the same
   // package. Returns whether any required versions were trimmed.
   bool _requiredAndDisallowed(Required required, Disallowed disallowed) {