haskellcabal

Cabal build with local dependency


I have two local libraries (and by local I mean located in the local filesystem, pardon the alliteration), called bins and eeep, both building fine. Now the library eeep needs functionality from the bins library, specifically a typeclass. So I tried the following dance:

First add a cabal.project file to eeep with the following contents:

packages:
    .
    ../bins

The relative path ../bins is the path to the root of the bins lib, containing the bins.cabal file. The bins library is at version 0.1, so I add the following line to eeep.cabal in the build-depends field: bins >=0.1 && <0.2. As soon as I cabal build, even if I do not add any code that actually imports bin, I get:

Resolving dependencies...
Error: cabal: Could not resolve dependencies:
[__0] next goal: bins (user goal)
[__0] rejecting: bins-0.1.2.0, bins-0.1.1.1, bins-0.1.1.0 (constraint from
user target requires ==0.1.0.0)
[__0] trying: bins-0.1.0.0
[__1] next goal: eeep (user goal)
[__1] rejecting: eeep-0.1.0.0 (requires library from bins, but the component
does not exist)
[__1] fail (backjumping, conflict set: bins, eeep)
After searching the rest of the dependency tree exhaustively, these were the
goals I've had most trouble fulfilling: bins, eeep

I am clearly missing a step, or many steps , as suggested by the line "requires library from bins, but the component does not exist" but what is it? Tried a couple more things (e. g. using absolute paths in cabal.project) but to no avail. Also tried googling but the google demiurgs must hate me, as nothing useful turned up.

Using ghcup and have ghc 9.6.6 installed (and only that version). I am pretty sure this will be another doh moment, but any other info needed, just ask.

Edit: On a hunch when into Hackage, and sure enough there is a bins lib there already. Renaming my bins to trisagion (and making sure it builds correctly), I get

Resolving dependencies...
Error: cabal: Could not resolve dependencies:
[__0] trying: eeep-0.1.0.0 (user goal)
[__1] next goal: trisagion (user goal)
[__1] rejecting: trisagion-0.1.0.0 (does not contain library, which is
required by eeep)
[__1] fail (backjumping, conflict set: eeep, trisagion)
After searching the rest of the dependency tree exhaustively, these were the
goals I've had most trouble fulfilling: eeep, trisagion

So the "constraint from user target" thingy is gone, but "does not contain library, which is required by eeep" is still here. So what am I missing? the trisagion.cabal is just a simple cabal file with library and test stanzas (builds fine, all tests pass, etc.). What extra step do I need to instruct cabal to: build eeep you will need trisagion, version >=0.1 which can be found at ../trisagion. I have been through the cabal docs (e.g. the local vs. external package distinction), so I am probably misunderstanding them as the dance I described is what I thought I had to do to build a package depending on another local package.

These are the stanzas from trisagion.cabal:

common common-fields
    default-language: GHC2021
    default-extensions:
        DerivingStrategies
        TypeFamilies
    build-depends:
        -- GHC 9.6
        base ^>=4.18 && <4.19,
    ghc-options:
        -Wall
        -Wcompat
        -Widentities
        -Wincomplete-record-updates
        -Wincomplete-uni-patterns
        -Wmissing-export-lists
        -Wmissing-home-modules
        -Wpartial-fields
        -Wredundant-constraints
        -Wmissing-deriving-strategies
        -- -Wunused-packages

library trisagion-lib
    import: common-fields
    hs-source-dirs:
        src
    build-depends:
        mtl >=2.3 && <2.4,
        mono-traversable >=1.0 && <1.1,
        text >=2.0 && <2.2,
        bytestring >=0.11 && <0.13,
        containers >=0.6 && <0.8,
        vector >=0.13 && <0.14,
    other-modules:
    exposed-modules:
        Trisagion.Types.ParseError
        Trisagion.Types.Result
        Trisagion.Typeclasses.Streamable
        Trisagion.Typeclasses.Splittable
        Trisagion.Get
        Trisagion.Getters.Combinators
        Trisagion.Getters.Streamable
        Trisagion.Getters.Splittable
        Trisagion.Getters.Word8
        Trisagion.Getters.Char

test-suite trisagion-tests
    import: common-fields
    type: exitcode-stdio-1.0
    hs-source-dirs:
        tests
    main-is: Spec.hs
    build-depends:
        hspec ^>=2.11 && <2.12,
        trisagion-lib,
    build-tool-depends:
        hspec-discover:hspec-discover
    other-modules:
        Tests.Helpers
        Tests.Getters.StreamableSpec
        Tests.Getters.CombinatorsSpec
        Tests.Getters.SplittableSpec
        Tests.Getters.Word8Spec
        Tests.Getters.CharSpec

And these, the eeep.cabal ones:

common common-fields
    default-language: GHC2021
    default-extensions:
        DerivingStrategies
        TypeFamilies
    build-depends:
        -- GHC 9.6
        base >=4.18 && <4.19,
        mono-traversable >=1.0 && <1.1,
        trisagion >=0.1 && <0.2,
    ghc-options:
        -Wall
        -Wcompat
        -Widentities
        -Wincomplete-record-updates
        -Wincomplete-uni-patterns
        -Wmissing-export-lists
        -Wmissing-home-modules
        -Wpartial-fields
        -Wredundant-constraints
        -Wmissing-deriving-strategies
        -- -Wunused-packages

library
    import: common-fields
    hs-source-dirs: src
    exposed-modules:
        Eeep.Types.Streams

The corresponding repo links are:


Solution

  • You've named your library in trisagion.cabal:

    library trisagion-lib
    

    This implicitly marks it to be available internally only, i.e. only to other components in the trisagion package. The simplest fix is to just delete the name:

    library
    

    See the docs on the library stanza for more details.