I built a containerized Azure Function App that internlly runs a haskell program packaged with Nix.
I followed Create your first containerized functions on Azure Container Apps to make a scaffold. Runtime could be anything than can run sub process, which is everything. So I choose dotnet.
And at the end of the generated Dockerfile, I added some nix layers.
# Basic runtime to install nix RUN apt install -y xz-utils curl RUN bash -c "sh <(curl -L https://nixos.org/nix/install) --daemon --yes" # Update PATH to include nix tools ENV PATH="/home/.nix-profile/bin:/nix/var/nix/profiles/default/bin:${PATH}"
Then I copied my haskell project.
ADD haskell-project /opt/haskell-project
Create haskell package using cabal2nix
. I call nix-collect-garbage
to reduce the size of docker layer.
RUN nix-shell -p cabal2nix --run 'cabal2nix --no-check /opt/haskell-project > /opt/haskell-project/foo.nix' && nix-collect-garbage
The default.nix
would look like this. It calls the haskell package and wrap it with justStaticExecutables to leave only runtime dependencies.
let p = (import <nixpkgs> {}).pkgs; in p.haskell.lib.compose.justStaticExecutables (p.haskellPackages.callPackage ./foo.nix {})
Build the nix package
RUN nix-build
In the Function implementation, run the hasell executable as a subprocess
using System.Diagnostics; using (Process hs = new Process()) { hs.StartInfo.UseShellExecute = true; hs.StartInfo.FileName = "/opt/haskell-project/result/bin/exe"; hs.Start(); await hs.WaitForExitAsync(); if (hs.ExitCode != 0) { throw new Exception($"haskell subprocess failed {hs.ExitCode}"); } }
Top comments (0)