使用cabal2nix为不在nixpkgs中的包创建本地nix环境

时间:2014-11-30 16:17:41

标签: haskell yesod cabal-install nixos

我目前有一个我在NixOS上开发的Yesod Web应用程序。我使用的是default.nix文件,如O' Charles' blog post

{ haskellPackages ? (import <nixpkgs> {}).haskellPackages }:

haskellPackages.cabal.mkDerivation (self: {
  pname = "myblog";
  version = "0.0.0";
  src = ./.;
  isLibrary = true;
  isExecutable = true;
  buildDepends = with haskellPackages; [
    aeson bson conduit dataDefault fastLogger hjsmin
    httpConduit monadControl monadLogger mongoDB persistent
    #persistentMongoDB
    persistentTemplate poolConduit shakespeare text
    waiExtra waiLogger warp yaml yesod yesodAuth
    yesodCore yesodDefault yesodForm yesodStatic
  ];
  testDepends = with haskellPackages; [
    hspec monadLogger persistent
    #persistentMongoDB
    resourcet transformers yesod yesodCore yesodTest
  ];
  buildTools = with haskellPackages; [
    cabalInstall ghcMod yesodBin
  ];
  jailbreak = true;
})

这非常有效。我可以正常使用yesod二进制文件和cabal。但是,我遇到了一个问题。运行cabal haddock时,我收到以下错误:

Running Haddock for mycoolblog-0.0.0...
Preprocessing library mycoolblog-0.0.0...
Warning: The documentation for the following packages are not installed. No
links will be generated to these packages: persistent-mongoDB-2.1.1
<command line>: cannot satisfy -package-id aeson-0.8.0.2-9e93bdd6f8e68379314dd5f31414f87f
    (use -v for more information)

在Google上搜索以下链接:github: cabal haddock 'cannot satisfy -package-id' #2468。好像是说应该使用ghcWithPackages。

关于ghcWithPackages的Google搜索带来了查尔斯&#39; (个人?)wiki on Nix。它有一个使用ghcWithPackages来开发已经在nixpkgs中的软件包的示例,但是我无法使用一个尚未在nixpkgs中的软件包(我的cms / blog)。

像O&#39; Charles&#39; wiki并运行nix-shell -v,我收到以下错误:

evaluating file `/nix/store/an4sg7cxi1ii3vids8417kajl3ss13vd-nix-1.7/share/nix/corepkgs/derivation.nix'
error: cannot auto-call a function that has an argument without a default value (`cabal')

为什么我收到上述错误?如何为naskpkgs中尚未包含的Haskell项目编写default.nixshell.nix?理想情况下,它会使用ghcWithPackages,以便cabal haddock有效。

1 个答案:

答案 0 :(得分:4)

O'Charles' Nix wiki上使用该方法后,我能够正常工作。我还没有确定为什么这种方法以前不起作用。

基本上,首先运行cabal2nix。然后创建一个通用的shell.nix(可以在所有Haskell包之间共享)。

$ cabal2nix --jailbreak --sha256=X ./$cabal > default.nix
$ sed -i 's#sha = .*#src = builtins.filterSource (path: type: type != "unknown") ./.;#' default.nix
$ cat - > shell.nix <<EOF
let
  pkgs = import <nixpkgs> {};
  haskellPackages = pkgs.haskellPackages.override {
    extension = self: super: {
      thispackage = self.callPackage ./. {};
    };
  };
in pkgs.myEnvFun {
     name = haskellPackages.thispackage.name;
     buildInputs = [
       (haskellPackages.ghcWithPackages (hs: ([
         hs.cabalInstall
         hs.hscolour
         hs.ghcMod
       ] ++ hs.thispackage.propagatedNativeBuildInputs)))
     ];
   }      
EOF
$ nix-shell