如何强制柯南从源代码构建,但前提是它不在缓存中?

问题描述

我在企业环境中使用 conan,该环境中的操作系统相当陈旧,并且拥有旧版本的 glibc (2.11)。因此,conan.io 上的许多预构建二进制文件最终无法在我的环境中运行。但是,conan 不知道这一点,并且很乐意将它们下载并安装到我的系统上,从而导致链接错误

我发现如果我从源代码构建,我可以让库工作。

我想要的行为如下

  • 第一次使用 conan install 安装库(例如它不在我的缓存中)然后 conan 将从源代码构建并将其放置在我的缓存中,然后使用它。
  • 在后续调用 conan install 时,conan 会找到缓存的库并使用它,而无需从源代码重建。
  • 我正在调用 conan install 作为自动构建脚本的一部分,因此我不想根据是否是第一次安装库来修改调用(但修改配置文件很好)。

我在实践中遇到了这种行为的问题。 以下是我遇到的挑战

  • 如果我使用 conan install --build=thelibrary,那么 conan 将在每次调用 conan install --build=thelibrary 时从源重建该库,即使它已经存在于我的缓存中。
  • 如果我使用 conan install --build=missing,那么我可以通过设置一些没有与它们关联的预构建二进制文件的构建选项来欺骗 conan 来构建库。
    • 这很脆弱,因为它仅适用于具有足够构建选项的项目,因此无法为所有组合创建预构建选项。
    • 如果我需要的所有构建选项都对应于预构建的二进制文件,那么它也不起作用。

这是我要找的(我假设存在但找不到):

  • 我可以在我的 conanfile.txt(或其他一些配置文件)中放置一些设置,它告诉 conan 忽略给定库的预构建二进制文件,而是从源代码构建,但使用缓存版本(如果可用)。
    • 理想情况下,这应该可以工作,而我不必修改构建选项。
  • 我不一定想从源代码构建所有库,只是那些不能在我的旧操作系统上运行的库,但如果我不得不满足于“全有或全无”我会接受“全部”。

这可以通过 conan 实现吗?

解决方法

glibc 版本是令柯南头疼的老问题,因为它不是设置的一部分,因此不算作包 ID 的一部分。 Conan Docker 映像正在运行 Ubuntu,其中一些是旧的,其他的是新的。但是有一个运行 CentOS6 的特定 Docker 镜像,它是由于 glibc 2.12 创建的,可以帮助生成包。

对于您的具体情况,我们有几个选择:

  • 添加 glibc 作为设置的一部分,因此 Conan 不会因为包 ID 而替换您的包。由于您应该有更多的同事,您可以使用 conan config 命令进行设置分发。

    # ~/.conan/settings.yml
    glibc: [None,2.11,...]
    

    添加后,您也可以更新您的个人资料,将 glibc=2.11 设为默认设置。

  • 另一种选择是 package revisions 功能,您可以在其中锁定特定的二进制包以供使用,这意味着您想要使用该特定的包。您只需要使用 glibc 上传生成的包并使用其二进制包修订版,例如lib/1.0@conan/stable#RREV:PACKAGE_ID#PREV

另外,回答您的问题:

我可以在我的 conanfile.txt(或其他一些配置文件)中放置一些设置,它告诉 conan 忽略给定库的预构建二进制文件,而是从源代码构建,但如果可用,则使用缓存版本.

您的缓存是 Conan 的第一选择,它会首先在那里寻找一个预先构建的包,如果它不可用,它会按照排序的顺序查看您的遥控器。您的请求是不可能的,首先是因为 conanfile.txt 不支持 build policies,其次是因为 conanfile.py 仅支持从源构建全部,或者仅构建缺失。

我的建议是,安装一个 Artifactory 实例,构建您需要的内容,上传您的自定义软件包,并将其设为您的默认远程。

我不一定想从源代码构建所有库,只是那些不能在我古老的操作系统上运行的库,但如果我不得不满足于“全有或全无”,我会选择“全部”。

您可以将一些包引用与远程运行的 conan remote 命令相关联。假设您要下载使用 zlib/1.2.11 构建的 glibc-2.11,并且它仅在您的组织远程可用:

$ conan remote add_ref zlib/1.2.11@org/stable my_org_repo
$ conan remote list_ref # only to validate,not mandatory
zlib/1.2.11@org/stable: my_org_repo

现在您的特定包与您的组织相关联。 Conan 仍会首先在您的本地缓存中查找该包,但如果找不到,它会尝试在您的 Artifactory 中查找。

如您所见,使用新设置可以更轻松地解决您的问题,而不是尝试破解构建策略。作为另一种选择,您可以将 glib 设置替换为 distro 及其版本。