I'm awkwardly patting myself on the back here since I'm one of the co-authors, but I really wish more people knew about the package manager we have for Dart[1]. Really, though, I can't take credit, since we basically just do the same thing Bundler does. [1]: https://www.dartlang.org/tools/pub/get-started.html It solves every single one of the problems listed here. It has a very simple workflow: 1. You make a pubspec.…
One thing I've never been able to figure out about these package management systems: why do you specify a version range, and not just always specify a precise version? I don't like dependencies randomly upgrading themselves, and then you don't need "pub upgrade" or "pubspec.lock".
To handle shared constraints.
Let's say myapp uses foo and bar, which both use shared_thing. To solve this, we need to pick a single version of shared_thing that both foo and bar work with. If foo and bar have narrow-to-the-point-of-precise constraints like shared_thing 1.2.3+bug-fix, then it's very likely that no version of shared_thing makes both foo and bar happy. The end result is no solution.
To accommodate that, packages are strongly encouraged to semantically version themselves. Then, when you depend on a package, you use as wide a range as you can. If foo wants shared_thing ">=1.2.3 =1.3.0 <2.0.0" then the solver can pick, say, 1.5.3, and both are happy.