Right, part of the issue with having dependency solving at the core of your workflow is that you never really know who's to blame. When running into this circumstance, either:
1) Some maintainer made a mistake.
2) Some maintainer did not have perfect knowledge of the future and has not yet updated some upper bounds. Or, upper bounds didn't get retroactively bumped (usual).
3) You're asking cabal to do something that can't be done.
4) There's a bug in the solver.
So the only thing to do is to say "something went wrong". In a way it is similar to type inference, it is difficult to give specific, concrete error messages without making some arbitrary choices about which constraints have gotten pushed around.
I think upper bounds could potentially be made viable by having both hard and soft constraints. Until then, people are putting 2 meanings into one thing. By having the distinction, I think cabal-install could provide much better errors than it does currently. This has come up before, I'm not sure what came of those discussions. My thoughts on how this would work:
* The dependency solver would prioritize hard constraints, and tell you which soft constraints need to be lifted. I believe the solver even already has this. Stack's integration with the solver will actually first try to get a plan that doesn't override any snapshot versions, by specifying them as hard constraints. If that doesn't work, it tries again with soft constraints.
* "--allow-soft" or something would ignore soft constraints. Ideally this would be selective on a per package / upper vs lower.
* It may be worth having the default be "--allow-soft" + be noisy about which constraints got ignored. Then, you could have a "--pedantic-bounds" flag that forces following soft bounds.
I could get behind upper bounds if they allowed maintainers to actually communicate their intention, and if we had good automation for their maintenance. As is, putting upper bounds on everything seems to cause more problems than it solves.
-Michael