overlay - nixos:覆盖调用覆盖
问题描述
我在我的 ~/.config/nixpkgs/overlays/tmft.nix 中定义了一个覆盖,如下所示:
self: super: {
tfmt = import ../dists/tfmt/default.nix {};
}
没关系,我可以安装它。它是一个 haskell 包,我想将它作为我的 ghc 安装的一部分进行安装。所以我在 myHaskellEnv.nix 中有另一个覆盖,看起来像这样:
self: super: {
myHaskellEnv = super.haskellPackages.ghcWithHoogle
(haskellPackages: with haskellPackages;
[ tfmt ]);
}
只是,它抱怨它看不到 tfmt ( error: undefined variable 'tfmt'
)。
我可以通过直接导入包来解决这个问题:
let tfmt = import ../dists/tfmt/default.nix {};
in self: super: {
myHaskellEnv = super.haskellPackages.ghcWithHoogle
(haskellPackages: with haskellPackages;
[ tfmt ]);
}
但这会破坏重用。
如何使用另一个叠加层?我尝试参考 super.tfmt,但这显示了同样的问题。
解决方案
叠加层只是属性集(通常是包)self
的函数。super
与任何 Nix 函数定义相同的范围规则适用。因此,当您想使用先前叠加层中的某些内容时,它并没有神奇地出现在范围内。您必须从self
或super
仅代表早期覆盖的最终包集和定义中获取它。
通过更改[ tfmt ]
为,[ self.tfmt ]
您应该能够插入 - 的最终定义,tfmt
因为它可能会在后续覆盖中被覆盖。或者,您可以tfmt
从获取super
,不推荐这样做,因为它不太灵活,但有时您需要super
避免创建导致评估期间无限递归的循环定义。
编写覆盖时,应避免直接或间接重新导入 Nixpkgs。这很重要,因为<nixpkgs>
可能是错误的 Nixpkgs 版本供某人使用,如果您做对了,您将重新评估 Nixpkgs 固定点,这需要时间,您将丢失原始 Nixpkgs 中的任何配置,例如config
和overlays
交叉编译参数。
相反,您应该使用self
andsuper
属性。特别是,super.callPackage
它派上用场,但对于 Haskell 包,您最好覆盖一个 haskell 包集,用您自己的包扩展它,以保持一致性。
这是一个例子。
另外,我建议您将叠加层的数量保持在最低限度。仅在从软件分发的角度来看有意义的情况下才拆分它们——这就是它们的目的。
推荐阅读
- reactjs - 赛普拉斯 while 循环
- mysql - 在 mySQL 工作台 MAC 中,secure_file_priv=NULL
- asp.net-core - 如何摆脱警告“从应用程序代码调用'BuildServiceProvider'......”
- swift - 作为参数传递的 ViewController 未被取消初始化(Swift)
- python - 如何在 Python 中做这个特定的列表理解?
- asp.net - 带有 PagedList 问题的 ASP.NET Core 中的下拉 PageSize 选择
- c# - 获取实体框架中按不同属性分组的最新项目列表
- python - 如何在 Python 列表初始化中放置条件
- json - 确保字符串为 JSON 格式的方法
- php - Wordpress 自定义插件将表单提交到另一个表单