I do wish Cabal’s solver were more easily observable, though I don’t know exactly what I’d want from it in general. It’s a pretty hard UX problem.
Anyway, the solver is, for whatever reason*, prioritising picking a new containers
over picking a new hakyll
. Some change to some package on Hackage in the last few days has meant that we’re newly able to pick containers-0.7
. This is out of bounds for lrucache
, a dependency of hakyll
which hasn’t been updated in 6 years. So a very old hakyll
is chosen which doesn’t depend on lrucache
.
I notice that hakyll
has in that time been given a revision bumping it’s pandoc
bound so it may well be some consequence of that. I haven’t looked in to it any further. Similarly, I don’t know why we end up with hakyll-3.2.0.10
when its lrucache
dependency wasn’t added until hakyll-3.4.1.0
.
For the record, some commands that helped me work this out:
cd web/site
copy-plan() {
cat dist-newstyle/cache/plan.json | jq > $1
cat $1 | jq -r '.["install-plan"] | map(select(.["pkg-name"] == "hakyll")) | .[0].["pkg-version"]'
cat $1 | jq -r '.["install-plan"] | map(select(.["pkg-name"] == "containers")) | .[0].["pkg-version"]'
}
cabal build --dry
copy-plan basic.json # 3.2.0.10, 0.7
cabal build --dry --constraint='hakyll>4'
copy-plan constrained.json # 4.16.2.2, 0.6.8
cabal build --dry --index-state=2024-10-05T00:00:00Z
copy-plan old-index.json # 4.16.2.2, 0.6.8
GET_VERSIONS='.["install-plan"] | map({"pkg-name": .["pkg-name"], "pkg-version": .["pkg-version"]})'
diff -C3 <(cat basic.json | jq "$GET_VERSIONS") <(cat constrained.json | jq "$GET_VERSIONS")
* I don’t actually know quite what heuristic is used when there are multiple potential build plans, or whether this is documented anywhere? Usually, it’s just “use the latest version of everything” but in circumstances like this it’s not quite so simple.
tl;dr Use --allow-newer=lrucache:containers
.