Skip to content

Cabal REPL stack overflows when working around lack of support for multiple home units #9240

Open
@habibalamin

Description

Describe the bug

Since Cabal lacks multiple home units support, when using Cabal to power the REPL that GHCid sends reload commands to, you can either load the test suite component, watch for changes to the test suite only and not the library and auto-rerun the test suite on build success, or you can load the library component, watch for changes to the library only and not the test-suite and auto-rerun a library entrypoint on build success (like a web server).

I'm sure you could even run two GHCid processes so that one reruns the tests and the other reruns the server, but the server will only reload when the library changes (not a problem) and the tests will only reload when the tests change (a pretty big problem).

The workaround is to add the library hs-source-dir to the test suite component, as well as the library modules to the test suite's other-modules, so that GHCid can detect changes to library files as changes to the test suite files as well. Any exposed-modules library entrypoints that you want GHCid to also be able to run (like a server) on build success, perhaps in a second process, must be in the other-modules of the test suite.

You can do all this with a common stanza, and I haven't tried without it (way too much duplication otherwise). All good, as the common GHCid refrain goes, right? Wrong!

All good if you run ghcid directly from the Cabal store (which you can get by doing cabal v2-exec -- which ghcid or similar), but if you just run ghcid via cabal v2-exec, running the GHCid process which watches the library and auto-reruns the server right after running the GHCid process which watches the test suite and auto-reruns the test suite results in a stack overflow before GHCid can even open the REPL it will send commands to.

This then necessitates another workaround on top of the fact that I'm already only doing this to work around Cabal's lack of support for multiple home units.

To Reproduce

Check out my repo https://github.com/habibalamin/ghc-env-breaks-ghcid-server-watch-using-lib-home-and-test-suite-imports-lib-deps-from-common-stanza.

Run make watch-test, Ctrl-C it, then run make watch-server-broken.

Expected behavior

I expect Cabal to just be able to load multiple units, and this will even allow me to just do the whole thing in a single GHCid process that watches both library and test code, then on build success, either runs the test suite to completion and the server right afterwards, or just runs them both in parallel somehow (which requires handling interleaving screen output, but that'd be my responsibility, not Cabal's or GHCid's).

Barring that, with the workaround, I expect to be able to just use cabal v2-exec to run any command line tool that is installed in my build-tool-depends, like GHCid (although it's more of a dev tool than a build tool, perhaps that can be another ticket), without it causing funky interaction and state issues.

System information

  • macOS Ventura 13.5.1 on Apple Silicon M1 Pro
  • GHCup 0.1.19.4
  • Cabal library 3.10.1.0 via aforementioned GHCup
  • Cabal 3.4 package description file
  • GHC 9.4.7 via aforementioned GHCup

Additional context

I found two workarounds.

The cabal v2-exec sets a GHC_ENVIRONMENT environment variable that seems to cause the breakage, which you can unset with env before running the Cabal REPL.

The other workaround is to run the Cabal REPL with the test suite component instead of the library component even when running the GHCid process that watches the library and auto-reruns the server instead of the test suite.

In the reproduction repo, see Make rules, watch-server-workaround-use-test-suite-home-unit and watch-server-workaround-no-ghc-environment, for the implementations of watch-server w/ the respective workarounds.

Basic code quality issues with these are outlined in the reproduction repo.

See ndmitchell/ghcid#320 for the GHCid ticket relating to its inability to monitor test-suite AND library changes with Cabal, due to Cabal's lack of support for multiple home units.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions