Getting started with flakes

This version of the getting started guide is for users who are using Nix Flakes. The non flakes version of the guide is here.

haskell.nix can automatically translate your Cabal or Stack project and its dependencies into Nix code.

Assuming you have Nix installed, you can start setting up your project.

Using flake init and nix

The flake init command create an example hello package from hackage containing an flake.nix and nix/hix.nix file. The project can be used with regular nix tools.

nix flake init --template templates#haskell-nix --impure
# `--impure` is required by `builtins.currentSystem`
nix develop
cabal build

To view the contents of the flake run:

nix flake show

To build a component with nix:

nix build .#hello:exe:hello

To build and run a component:

nix run .#hello:exe:hello

Setting up the binary cache

IMPORTANT: you must do this or you will build several copies of GHC!

You can configure Nix to use our binary cache, which is pushed to by CI, so should contain the artifacts that you need.

You need to add the following sections to /etc/nix/nix.conf or, if you are a trusted user, ~/.config/nix/nix.conf (if you don't know what a "trusted user" is, you probably want to do the former).

trusted-public-keys = [...] hydra.iohk.io:f/Ea+s+dFdN+3Y/G+FDgSq+a5NEWhJGzdjvKNGv0/EQ= [...]
substituters = [...] https://cache.iog.io [...]

If you're running NixOS, you need to add/update the following in your /etc/nixos/configuration.nix files instead.

# Binary Cache for Haskell.nix
nix.settings.trusted-public-keys = [
  "hydra.iohk.io:f/Ea+s+dFdN+3Y/G+FDgSq+a5NEWhJGzdjvKNGv0/EQ="
];
nix.settings.substituters = [
  "https://cache.iog.io"
];

NixOS-21.11 and older use slightly different settings.

# Binary Cache for Haskell.nix  
nix.binaryCachePublicKeys = [
  "hydra.iohk.io:f/Ea+s+dFdN+3Y/G+FDgSq+a5NEWhJGzdjvKNGv0/EQ="
];
nix.binaryCaches = [
  "https://cache.iog.io"
];   

This can be tricky to get setup properly. If you're still having trouble getting cache hits, consult the corresponding troubleshooting section.

Scaffolding

The following work with stack.yaml and cabal.project based projects.

Add flake.nix:

{
  description = "A very basic flake";
  inputs.haskellNix.url = "github:input-output-hk/haskell.nix";
  inputs.nixpkgs.follows = "haskellNix/nixpkgs-unstable";
  inputs.flake-utils.url = "github:numtide/flake-utils";
  outputs = { self, nixpkgs, flake-utils, haskellNix }:
    flake-utils.lib.eachSystem [ "x86_64-linux" "x86_64-darwin" ] (system:
    let
      overlays = [ haskellNix.overlay
        (final: prev: {
          # This overlay adds our project to pkgs
          helloProject =
            final.haskell-nix.project' {
              src = ./.;
              compiler-nix-name = "ghc925";
              # This is used by `nix develop .` to open a shell for use with
              # `cabal`, `hlint` and `haskell-language-server`
              shell.tools = {
                cabal = {};
                hlint = {};
                haskell-language-server = {};
              };
              # Non-Haskell shell tools go here
              shell.buildInputs = with pkgs; [
                nixpkgs-fmt
              ];
              # This adds `js-unknown-ghcjs-cabal` to the shell.
              # shell.crossPlatforms = p: [p.ghcjs];
            };
        })
      ];
      pkgs = import nixpkgs { inherit system overlays; inherit (haskellNix) config; };
      flake = pkgs.helloProject.flake {
        # This adds support for `nix build .#js-unknown-ghcjs:hello:exe:hello`
        # crossPlatforms = p: [p.ghcjs];
      };
    in flake // {
      # Built by `nix build .`
      packages.default = flake.packages."hello:exe:hello";
    });
}

Note: Git dependencies

If you have git dependencies in your project, you'll need to calculate sha256 hashes for them.

Working with a project

Top-level attributes are Haskell packages (incl. dependencies) part of your project.

To build the library component of a package in the project run:

nix build .#your-package-name:lib:your-package-name

There are also other components such as exe, test and benchmark. To build an executable:

nix build .#your-package-name:exe:your-exe-name

To use the devShell provided by the flake run:

nix develop .
cabal repl your-package-name:lib:your-package-name
cabal build your-package-name

To open a shell for use with stack see the following issue.

Going forward

Read through project function reference to see how the API works.

There are a number of things to explore further in the tutorials section.