问题描述
我正在制作一个 haskell 程序,我正在像这样设置 buildInput
以包含 pkgs.ffmpeg-full
:
(myHaskellPackages.callCabal2nix "App" (./.) {}).overrideAttrs (oldAttrs: {
buildInputs = (oldAttrs.buildInputs or []) ++ [ pkgs.ffmpeg-full ];
})
然而,这似乎使 ffmpeg 包只能在构建时间而不是应用程序运行时访问。
我需要为 ffmpeg-full
设置什么属性才能在运行时可用 - 能够调用 ffmpeg
可执行文件?
在 nix 药丸中有一个关于运行时依赖项的部分,但我不明白该部分,它如何始终仅通过散列确定运行时依赖项是没有意义的?我的意思是,如果我在 shell 脚本中引用一个可执行文件 - 当然 nix 不会解析 shell 脚本来确定我引用的可执行文件。 https://nixos.org/guides/nix-pills/automatic-runtime-dependencies.html#idm140737320205792
但是,运行时依赖项有所不同。建造 一旦使用依赖项,Nix 会自动识别它们 任何派生调用,但我们从不指定运行时是什么 派生的依赖项。
真的有黑魔法。这是一开始的事情 一瞥让你觉得“不,这从长远来看是行不通的”,但在 同时它运行得非常好以至于构建了一个完整的操作系统 在这个魔法之上。
换句话说,Nix 会自动计算所有运行时 派生的依赖关系,这可能要归功于 商店路径。
解决方法
似乎这不是明确声明的依赖项列表直接支持的。然而,我们可以通过“包装”间接实现这一点。
我在此处找到了有关包装的更多信息:https://nixos.wiki/wiki/Nix_Cookbook#Wrapping_packages
所以我可以做一个引用包的 ls
。
...
appPkg = (myHaskellPackages.callCabal2nix "HaskellNixCabalStarter" (./.) {}).overrideAttrs (oldAttrs: {
buildInputs = (oldAttrs.buildInputs or []) ++ [ pkgs.ffmpeg-full ];
});
in
(pkgs.writeScriptBin "finderapp" ''
#!${pkgs.stdenv.shell}
ls ${pkgs.ffmpeg-full}/bin/ffmpeg
exec ${appPkg}/bin/app
''
)
我们可以验证构建的包(?)是否正确依赖于:
nix-store -q --references result
/nix/store/0cq84xic2absp75ciajv4lfx5ah1fb59-ffmpeg-full-4.2.2
/nix/store/rm1hz1lybxangc8sdl7xvzs5dcvigvf7-bash-4.4-p23
/nix/store/wlvnjx53xfangaa4m5rmabknjbgpvq3d-HaskellNixCabalStarter-0.1.0.0