haskell / cabal

Official upstream development repository for Cabal and cabal-install
https://haskell.org/cabal
Other
1.61k stars 691 forks source link

v2-freeze creates freeze file with non-single-point version ranges. #6110

Open phadej opened 5 years ago

phadej commented 5 years ago

Describe the bug

After v2-freeze I see things like

any.hashable ==1.2.7.0 || ==1.3.0.

in cabal.project.freeze.

To Reproduce

I'm able to reproduce this with a current master of postgresql-simple commit d0fcf2800b184f095c4aac56db4a8a3ed1a8a829

I think that any package with custom-setup packages in dependencies, and suitable situation (see below) can trigger this:

postgresql-simple master % ls
bench  cabal.haskell-ci  cabal.project  CHANGES.md  CONTRIBUTORS  dist-newstyle  LICENSE  postgresql-simple.cabal  README.md  sdist.sh  Setup.hs  src  test  tools

postgresql-simple master % cat cabal.project 
packages: .
tests: true
postgresql-simple master % ls

bench  cabal.haskell-ci  cabal.project  CHANGES.md  CONTRIBUTORS  dist-newstyle  LICENSE  postgresql-simple.cabal  README.md  sdist.sh  Setup.hs  src  test  tools
postgresql-simple master % cat cabal.project 
packages: .
tests: true

postgresql-simple master % cabal v2-freeze -w ghc-7.8.4
Wrote freeze file: /code/public-haskell/postgresql-simple/cabal.project.freeze

/postgresql-simple master % grep '||' cabal.project.freeze 
             any.hashable ==1.2.7.0 || ==1.3.0.0,
             any.nats ==1.1.1 || ==1.1.2,
             any.semigroups ==0.18.5 || ==0.19,
             any.unordered-containers ==0.2.9.0 || ==0.2.10.0,

Expected behavior

I'd expect only thisVersion, i.e. == x.y.z.w. version ranges to exist in cabal.project.freeze. Technically, I'd expect that not being possible at all (i.e. freeze file representation would use Version, not VersionRange, and if independent goals require it, then use proper goal qualification, if any would be ||-ed range)

System informataion

ii  cabal-install-3.0                          3.0+git20190517.1.27ef964-6~18.04

Additional context

The problem is because independent goals are merged together, see Cabal dependencies in custom-setup are merged with "main" stuff. Which makes freeze file more like "gelly".

postgresql-simple-0.6.2
 ├─ Only-0.1
 │  └─ deepseq-1.3.0.2
 │     └─ array-0.5.0.0
 │        └─ base-4.7.0.2
 │           └─ integer-gmp-0.5.1.0
 │              └─ ghc-prim-0.3.1.0
 │                 └─ rts-1.0
 ├─ aeson-1.4.4.0
 │  ├─ attoparsec-0.13.2.2
 │  │  ├─ scientific-0.3.6.2
 │  │  │  ├─ integer-logarithms-1.0.3
 │  │  │  │  └─ nats-1.1.2
 │  │  │  │     ├─ hashable-1.3.0.0
 │  │  │  │     │  └─ text-1.2.3.1
 │  │  │  │     │     └─ binary-0.7.1.0
 │  │  │  │     │        ├─ bytestring-0.10.4.0
 │  │  │  │     │        │  └─ deepseq-1.3.0.2 ┄┄
 │  │  │  │     │        └─ containers-0.5.5.1
 │  │  │  │     │           └─ deepseq-1.3.0.2 ┄┄
 │  │  │  │     └─ template-haskell-2.9.0.0
 │  │  │  │        ├─ containers-0.5.5.1 ┄┄
 │  │  │  │        └─ pretty-1.1.1.1
 │  │  │  │           └─ base-4.7.0.2 ┄┄
 │  │  │  └─ primitive-0.7.0.0
 │  │  │     ├─ fail-4.9.0.0
 │  │  │     │  └─ base-4.7.0.2 ┄┄
 │  │  │     └─ transformers-0.5.6.2
 │  │  │        └─ base-4.7.0.2 ┄┄
 │  │  └─ semigroups-0.19
 │  │     ├─ nats-1.1.2 ┄┄
 │  │     ├─ tagged-0.8.6
 │  │     │  └─ transformers-compat-0.6.5
 │  │     │     ├─ fail-4.9.0.0 ┄┄
 │  │     │     ├─ generic-deriving-1.12.4
 │  │     │     │  └─ th-abstraction-0.3.1.0
 │  │     │     │     └─ template-haskell-2.9.0.0 ┄┄
 │  │     │     └─ transformers-0.5.6.2 ┄┄
 │  │     └─ unordered-containers-0.2.10.0
 │  │        └─ hashable-1.3.0.0 ┄┄
 │  ├─ base-compat-0.10.5
 │  │  └─ unix-2.7.0.1
 │  │     ├─ bytestring-0.10.4.0 ┄┄
 │  │     └─ time-1.4.2
 │  │        ├─ deepseq-1.3.0.2 ┄┄
 │  │        └─ old-locale-1.0.0.6
 │  │           └─ base-4.7.0.2 ┄┄
 │  ├─ contravariant-1.5.2
 │  │  ├─ StateVar-1.2
 │  │  │  ├─ stm-2.5.0.0
 │  │  │  │  └─ nats-1.1.2 ┄┄
 │  │  │  └─ transformers-0.5.6.2 ┄┄
 │  │  └─ void-0.7.3
 │  │     └─ semigroups-0.19 ┄┄
 │  ├─ dlist-0.8.0.6
 │  │  └─ deepseq-1.3.0.2 ┄┄
 │  ├─ time-compat-1.9.2.2
 │  │  ├─ base-orphans-0.8.1
 │  │  │  └─ base-4.7.0.2 ┄┄
 │  │  ├─ semigroups-0.19 ┄┄
 │  │  └─ time-1.4.2 ┄┄
 │  ├─ uuid-types-1.0.3
 │  │  ├─ hashable-1.3.0.0 ┄┄
 │  │  └─ random-1.1
 │  │     └─ time-1.4.2 ┄┄
 │  └─ vector-0.12.0.3
 │     ├─ primitive-0.7.0.0 ┄┄
 │     └─ semigroups-0.19 ┄┄
 ├─ bytestring-builder-0.10.8.2.0
 │  └─ bytestring-0.10.4.0 ┄┄
 ├─ case-insensitive-1.2.1.0
 │  └─ semigroups-0.19 ┄┄
 └─ [postgresql-libpq-0.9.4.2:all]
    ├─ postgresql-libpq-0.9.4.2
    │  └─ [hsc2hs-0.68.3:exe:"hsc2hs"]
    │     ├─ containers-0.5.5.1 ┄┄
    │     └─ process-1.2.0.0
    │        └─ directory-1.2.1.0
    │           ├─ filepath-1.3.0.2
    │           │  └─ base-4.7.0.2 ┄┄
    │           └─ unix-2.7.0.1 ┄┄
    └─ [setup]
       └─ Cabal-2.4.0.1
          ├─ parsec-3.1.13.0
          │  ├─ mtl-2.2.2
          │  │  └─ transformers-0.5.6.2 ┄┄
          │  └─ semigroups-0.18.5
          │     ├─ nats-1.1.1
          │     │  ├─ hashable-1.2.7.0
          │     │  │  └─ text-1.2.3.1 ┄┄
          │     │  └─ template-haskell-2.9.0.0 ┄┄
          │     ├─ tagged-0.8.6 ┄┄
          │     └─ unordered-containers-0.2.9.0
          │        └─ hashable-1.2.7.0 ┄┄
          └─ process-1.2.0.0 ┄┄
hvr commented 5 years ago

Fwiw, the current pragmatic ||-style constraint were a stop-gap solution towards the proper solution that #3502 aims to (I wasn't able to quickly locate the more specific issue/commit that got us the current ||-style constraints to make it possible to generate freeze files at all in the presence of qualified goals, which by design do not guarantee there to exist globally single-versioned plans)

phadej commented 5 years ago

Won't generating something like

hashable ==1.3.0.0,
any.hashable ==1.2.7.0 || ==1.3.0.0,

be already more precise?

hvr commented 5 years ago

sure, that'd be an incremental improvement within the current inadequate constraint-language; but I was trying to point out that we have a far bigger problem at hand... you'd just be improving the current stop-gap solution ;-)

23Skidoo commented 5 years ago

Nothing wrong with making the stop-gap solution better.

alt-romes commented 4 months ago

More than one version of the same package appears in the freeze file when you pick a separate version for a custom-setup dependency because cabal freeze qualifies all packages with any... therefore we can't differentiate between the version for the top-level vs setup dependency thus we simply allow both, which is very bad.

Cabal freeze should not use any qualifier for anything in the freeze file: #9799