input-output-hk / haskell.nix

Alternative Haskell Infrastructure for Nixpkgs
https://input-output-hk.github.io/haskell.nix
Apache License 2.0
559 stars 237 forks source link

`nix-shell` tool Ormolu builds with incompatible version of Cabal #1337

Closed peterbecich closed 2 years ago

peterbecich commented 2 years ago

ormolu-0.4.0.0 fails to build in nix-shell. I'm not certain this is an issue with haskell.nix

This demonstrates the issue: https://github.com/peterbecich/haskell.nix-ghcjs-issue/tree/test-ormolu

...
    # Some common tools can be added with the `tools` argument
    tools = {
      cabal = "3.6.2.0";
      hlint = "latest"; # Selects the latest version in the hackage.nix snapshot
      haskell-language-server = "latest";
      ormolu = "latest";
    };
...
% nix-shell
...

src/Ormolu/Utils/Extensions.hs:24:1: error:
    Could not find module 'Distribution.Utils.Path'
    Perhaps you meant
      Distribution.Utils.IOData (from Cabal-3.2.1.0)
      Distribution.Utils.MD5 (from Cabal-3.2.1.0)
      Distribution.Utils.Base62
    Use -v (or `:set -v` in ghci) to see a list of the files searched for.
   |
24 | import Distribution.Utils.Path (getSymbolicPath)
   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

Ormolu 0.4.0.0 specifies Cabal 3.6.*, but this appears to be ignored: https://hackage.haskell.org/package/ormolu-0.4.0.0

Cabal-3.6.2.0 has Distribution.Utils.Path https://hackage.haskell.org/package/Cabal-3.6.2.0/docs/Distribution-Utils-Path.html and Cabal-3.2.1.0 doesn't: https://hackage.haskell.org/package/Cabal-3.2.1.0

Thank you

angerman commented 2 years ago

This is the lib:Cabal that ships with the compiler I assume? So it's built against that lib:Cabal. You'll need to look into nonReinstallablePkgs for this. If you reduce the closure to not include Cabal, it should build the one from Hackage as specified. Any package in nonReinstallablePkgs is ignored and the ones from the ghc distribution is used. This is a bit of a wart. Maybe an improvement would be to add __trace messages if this happens.

amesgen commented 2 years ago

In Ormolu, we work around this with a hack using nonReinstallablePkgs as mentioned by @angerman:

options.nonReinstallablePkgs = lib.mkOption { apply = lib.remove "Cabal"; };

https://github.com/tweag/ormolu/blob/b9eaa3d9a709b7467c444173ab9295f10608b614/default.nix#L32-L34

purefn commented 2 years ago

To be explicit for anyone wanting to know exactly how to fix it, this means the original should change to

    # Some common tools can be added with the `tools` argument
    tools = {
      cabal = "3.6.2.0";
      hlint = "latest"; # Selects the latest version in the hackage.nix snapshot
      haskell-language-server = "latest";
      ormolu = {
        version = "latest";
        modules = [
          ({ lib, ... }: {
            options.nonReinstallablePkgs = lib.mkOption { apply = lib.remove "Cabal"; };
          })
        ];
    };
purefn commented 2 years ago

Should we maybe add that to the hackage-quirks so users don't have to do that themselves?

adetokunbo commented 2 years ago

I am experiencing a similar issue; I don't know if it's the same or should be reported as a separate bug

I am upgrading a small library (wai-middleware-delegate) that I develop with haskell.nix to use the text-2.0 dependency.

The change builds ok with nix-build, but when I try to drop into a nix-shell, Cabal is installed with a version of text that Cabal is built with (1.2.4.1), rather than the version of text that I have specified (2.0), so all cabal commands fail because the dependency is not satisfied.

Should I be using nonReinstallablePkgs in nix-shell to address this somehow ?

adetokunbo commented 2 years ago

I am experiencing a similar issue; I don't know if it's the same or should be reported as a separate bug

I am upgrading a small library (wai-middleware-delegate) that I develop with haskell.nix to use the text-2.0 dependency.

The change builds ok with nix-build, but when I try to drop into a nix-shell, Cabal is installed with a version of text that Cabal is built with (1.2.4.1), rather than the version of text that I have specified (2.0), so all cabal commands fail because the dependency is not satisfied.

Should I be using nonReinstallablePkgs in nix-shell to address this somehow ?

I've opened #1345 to track this issue