How to get stack to save dependencies? - haskell

I'm using the stack install command to save dependencies for a new project. How do I get it to save those dependencies into stack.yaml? Unless I'm missing something, I can't see where stack is recording the project dependencies and I can't seem to find anything in a docs about this.

You still keep your dependencies in a .cabal file. From the Stack FAQ:
A .cabal file is provided for each package, and defines all package-level metadata just like it does in the cabal-install world: modules, executables, test suites, etc. No change at all on this front.
A stack.yaml file references 1 or more packages, and provides information on where dependencies come from.
If you need additional versions of dependencies than the LTS Haskell snapshot you're using, you'll add them to the extra-deps portion of the stack.yaml file.

Related

Stack downloading package but sill can not use it

These are my dependencies in package.yaml:
dependencies:
- weasel
- network
- HTTP
- bytestring
but I still get the error
Could not find module ‘Network.HTTP.Base’
Use -v to see a list of the files searched for.
import Network.HTTP.Base
when importing
First, ensure the package.yaml buffer is saved to disk.
Second, assuming you are using stack, ensure that you are not seeing the following warning:
Warning: /Users/dan/scratch/foo/foo.cabal was modified manually. Ignoring
/Users/dan/scratch/foo/package.yaml in favor of the cabal file. If you
want to use the package.yaml file instead of the cabal file, then
please delete the cabal file.
```
If you are seeing this warning, check your foo.cabal file for anything you may want to keep, and port it over to your package.yaml file, and then delete the foo.cabal file so that hpack can generate a fresh one.
Third, ensure that this dependencies section pertains to the particular target you are currently trying to build. For example, if these are listed in the library dependencies, but not for the test suite dependencies, then the corresponding modules will not be available to the test suite. If the dependencies are specified at the top level, then they should in fact be available for all build targets.

Installing local package with Stack

Is it possible to install package from sources with something similar to stack build package-name? (latter works with packages on Stackage, but not with custom ones)
Um, stack build (within the source directory)?
Stack doesn't really have a notion of installing libraries though, it only installs executables. To “install” locally-sourced packages, you need to specify what for you want them installed: add them as dependencies to another project, via a location: field in the packages: field in that project's stack.yaml file.
That's arguably sensible since, one might say, there's nothing you can do with an installed library except invoking it in another Haskell project (or in a REPL, which you can get with stack ghci). I personally don't hold with that though, I like actually being able to say install that library now. Which is one of the reasons I have always stuck to good old cabal-install rather than Stack. With that, you can just
cabal install
from within the source directory.
Cabal-install has often been criticised: its local installs can easily get out of sync and then you have weird dependency conflicts and need to rebuild lots of stuff. I never found this that much of a problem, and anyway this has been adressed in recent Cabal through Nix-style builds, which never produce conflicts.

Create hackage package that can be installed with stack

When running stack sdist in my project directory, the stack.yaml file isn't included in the tarball (this seems to be expected).
Consequently, when I upload the tarball to hackage, then stack install mypackage it complains about missing dependencies (extra-deps) which I specified in the stack.yaml file.
$ stack install pandoc-placetable
Run from outside a project, using implicit global project config
Using resolver: lts-5.17 from implicit global project's config file: ~/.stack/global-project/stack.yaml
While constructing the BuildPlan the following exceptions were encountered:
-- Failure when adding dependencies:
spreadsheet: needed (>=0.1.3 && <0.1.4), not present in build plan (latest applicable is 0.1.3.4)
needed for package: pandoc-placetable-0.4
-- While attempting to add dependency,
Could not find package spreadsheet in known packages
Recommended action: try adding the following to your extra-deps in /Users/maurobieg/.stack/global-project/stack.yaml
- spreadsheet-0.1.3.4
Or what's the recommended way to make a hackage package stack-installable if it has further hackage dependencies?
Update: I just added extra-source-files: stack.yaml to the cabal file and the stack.yaml is indeed included in the tarbal of the newly published version. Nevertheless, stack install pandoc-placetable-0.4.1 still comes up with the same error.
I could also just tell people who don't want to install cabal-install on their system to clone from GitHub, then build with stack. Is that the recommended approach for tiny packages? Or should I ask them to include the dependency of pandoc-placetable (i.e. spreadsheet) in their global stack.yaml? Smells like polluting a global file...
As mentioned by #mgsloan in the comments above: There's an open stack issue about using stack.yaml from hackage package.
I guess until it's fixed I'll just tell people to clone from GitHub (or as mentioned by #MichaelSnoyman to stack unpack) and then cd into the newly created directory and stack install there.

How to update .cabal file using Stack?

I have an older project that I created with Stack. I want to move my project to the latest LTS set from Stackage.
When I change the resolver in the stack.yaml file, the problem is that the versions in the extra-deps in the .cabal file are still for the old LTS set. Is there a way to automatically update the version numbers in the .cabal file using Stack?
You could simply delete (some of) the (upper) bounds of the build-depends in your cabal file.
When it comes to distributing your package, stack can automatically add dependency bounds if you use the --pvp-bounds flag, e.g. stack sdist --pvp-bounds upper, stack upload --pvp-bounds both etc.
There's a blog post by Michael Snoyman on this feature.

Stack: How can I use a multi-package dependency in `Setup.hs`?

I have a stack multi-package project where the "multi-package" is zip-conduit-0.2.2.2 (I needed to tweak some dependency versions to get it to compile with nightly-2015-10-12).
I use zip-conduit in the main package and I also want to in Setup.hs in order to be able to package up zip files.
I have build-type: Custom in my cabal file and stack build attempts to build Setup.hs. The problem is that building Setup.hs cannot find the dependency zip-conduit-0.2.2.2.
Can I use a multi-package dependency in Setup.hs? If so how? and if not, what is my alternative?
Note: I have seen this reference https://github.com/commercialhaskell/stack/pull/899, but I don't understand it.
It looks like you need to set the explicit-setup-deps setting to true for that package. It's unfortunate that Stack can't handle this situation automatically, but without dependency information in .cabal files, there seems to be no alternative.
See the linked issues from the documentation if you're interested in the history here.
I don't think it is possible to declare package dependencies for Setup.hs itself.
Some ideas:
Require that the dependent packages have already been installed.
Have Setup.hs shell out to an external command to perform the zipping, and just require that the external command has to exist.
Make the installer program an additional exe target in the cabal file. Before proceeding with the build of the library, Setup.hs can build the installer program target, then build the library, then use the built installer exe to install the library.

Resources