opam 2.0 小贴士
这篇文章回顾了 opam 2.0 中的一些改进,并提供了一些关于新工作流程的技巧。
包开发环境管理
Opam 2.0 已经大大改进,可以处理本地定义的包。假设你有一个项目 ~/projects/foo
,定义了两个包 foo-lib
和 foo-bin
,你将拥有
~/projects/foo
|-- foo-lib.opam
|-- foo-bin.opam
`-- src/ ...
(另请参见有关 计算依赖约束 的内容,以处理具有相互约束的多个包定义)
自动固定
底层机制相同,但这是一个界面改进,它取代了大多数基于 opam pin
的 opam 1.2 工作流程。
通常的命令(install
、upgrade
、remove
等)已被扩展为支持指定目录作为参数。因此,在处理项目 foo
时,只需编写
cd ~/projects/foo
opam install .
foo-lib
和 foo-bin
将自动固定到当前目录(如果你的项目是版本化的,则使用 git),并安装。你可能更喜欢使用
opam install . --deps-only
仅在开始修改项目之前准备好包依赖项。 参见下文,了解如何更精确地重现构建环境。请注意,opam depext .
目前无法正常工作,这将在下一个版本中得到修复,届时将集成外部依赖处理(opam 仍然会在失败时列出适合你操作系统的正确包)。
如果你的项目是版本化的,并且你做出了更改,请记住要么提交,要么添加 --working-dir
,以便你的未提交更改被考虑在内。
本地开关
Opam 2.0 引入了一项名为“本地开关”的新功能。本节将解释它是什么,为什么,何时以及如何使用它。
Opam 开关 允许维护多个独立的开发环境,每个环境都有自己的一组已安装的包。当你需要不同的 OCaml 版本,或者在具有不同依赖集的项目上工作时,这尤其有用。
但是,有时管理或记住要将哪个开关与哪个项目一起使用会很繁琐。这就是“本地开关”发挥作用的地方。
本地开关如何处理
本地开关简单地存储在 _opam/
目录中,并且每当你的当前目录在其父目录下时,opam 都会自动选择它。
注意:强烈建议你在使用本地开关时启用新的shell 钩子。只需运行
opam init --enable-shell-hook
:这将确保你的 PATH 始终为正确的开关设置。否则,你将需要不断记住每次
cd
到包含本地开关的目录时运行eval $(opam env)
。另请参见 如何在提示符中显示当前开关
例如,如果你有 ~/projects/foo/_opam
,每当你在项目 foo
中时,开关都会被选中,允许你根据项目的需要定制它的安装内容。
如果你删除了开关目录,或整个项目,opam 将会透明地忘记它。不过,小心不要移动它,因为一些包仍然包含硬编码的路径,并且不能很好地处理重新定位(我们正在努力解决这个问题)。
创建本地开关
这通常可以从以下开始
cd ~/projects/foo
opam switch create . --deps-only
本地开关句柄只是它们的路径,而不是原始名称。此外,以上内容将检测 ~/projects/foo
中存在的包定义,选择一个兼容的 OCaml 版本(如果你没有明确提及任何版本),并自动安装所有本地包依赖项。
如果没有 --deps-only
,这些包本身也会安装到本地开关中。
使用现有开关
如果你只希望自动选择现有的开关,而不需要为每个项目重新编译,你可以使用 opam switch link
cd ~/projects/bar
opam switch link 4.07.1
将确保每当你在项目 bar
中时,都会选择开关 4.07.1
。你甚至可以在这里链接到 ../foo
,以便在两个项目之间共享 foo
的本地开关。
重现构建环境
固定
如果你的包依赖于某些依赖项的开发版本(例如,你需要将修复程序推送到上游),请在你的 opam 文件中添加
depends: [ "some-package" ] # Remember that pin-depends are depends too
pin-depends: [
[ "some-package.version" "git+https://gitfoo.com/blob.git#mybranch" ]
]
当你的包发布到存储库中时,这将没有影响,但是当它被固定到它的开发版本时,opam 将首先确保将 some-package
固定到给定的 URL。
锁定文件
依赖约束有时过于宽泛,你不想在开发过程中探索所有依赖项的版本。出于这个原因,你可能希望重现一组已知的有效依赖项。如果你使用
opam lock .
opam 将检查你的当前开关中安装的依赖项版本,并在 *.opam.locked
文件中明确它们。opam lock
目前是一个插件,但会在需要时自动安装。
然后,假设你将这些文件检入版本控制,任何用户都可以执行
opam install . --deps-only --locked
以指示 opam 重现相同的构建环境(--locked
选项也适用于 opam switch create
,使事情更容易)。
生成的锁定文件还将包含添加的约束,以重现可选依赖项的存在/不存在,并使用 pin-depends
重现适当的依赖固定。如果你不希望强制执行所有递归依赖项的版本,而只希望强制执行直接依赖项的版本,则添加 --direct-only
选项。