Search code examples
haskelldependency-managementcabal

Is it possible to install Cabal package locally à la npm?


In npm, dependencies are installed in a directory node_modules relative to the directory of the dependent package. Each package stores its dependencies inside itself.

With Cabal, however, installing a package always installs it globally (i.e. in ~/.cabal), which is a perfect recipe for nightmares and tears because different versions of packages get to conflict with eachother and everything will fail and go wrong.

I would like to install Cabal packages locally, i.e. in a subdirectory of my own package, rather than globally. All the dependencies of these packages would do the same. An example of the directory tree of my package could look like this:

my_package/
  dependencies/
    json/
      dependencies/
        foo/
          etc...
        bar/
          etc...
    mtl/
      etc...
  my_package.cabal
  src/
    Main.hs

Is this possible to do, and if so how?


Solution

  • EDIT: With newer versions of cabal, you should use cabal sandboxes, which are now built-in, rather than cabal-dev.

    Take a look at the cabal-dev tool. It's similar to virtualenv for Python.

    Basically, where you would use the command cabal, use cabal-dev. So to install the package you're working on, go that directory and do cabal-dev install. You can also run ghc-pkg through cabal-dev, so you can do something like cabal-dev ghc-pkg unregister foo-bar. Also, you can start GHCi with it too: cabal-dev ghci.

    By default, cabal-dev installs packages into a cabal-dev directory inside your project--this is what you call dependencies in your example.