Closed. This question is opinion-based 。它目前不接受答案。












想改善这个问题吗?更新问题,以便可以通过 editing this post 用事实和引文来回答。

8 个月前关闭。



Improve this question




CGO_ENABLED=1 我相信是当前的默认值,这意味着它取决于 GLIBC,它可以在更新和发行版之间进行重大更改。
CGO_ENABLED=0 是创建静态独立二进制文件的解决方法,为什么这不是默认值?

最佳答案

一般来说,CGO_ENABLED=1 会导致更快、更小的构建和运行时 - 因为它可以动态加载主机操作系统的 native 库(例如 glibc 、DNS 解析器等) - 在构建操作系统上运行时。这是本地快速发展的理想选择。对于部署,CGO_ENABLED=1 可能不切实际甚至不可能 - 在考虑部署托管操作系统时。
如果您纯粹使用标准库,则它们可能不一定需要启用 CGO。在某些标准库中,如果使用纯 Go 版本( CGO_ENABLED=1 )或启用 CGO 的版本,行为会有所不同:

  • net : 参见 DNS Name Resolution
  • os/users :
  • CGO_ENABLED=1 使用 native 操作系统(例如在 Linux 上 nsswitch )进行 ID 查找
  • CGO_ENABLED=0 使用一个基本的 Go 实现(例如从 /etc/passwd 读取)——它不包括主机可能知道
  • 的其他 ID 注册表


    部署
    虽然 CGO_ENABLED=1 二进制文件的大小可能更小,但它也依赖于提供主机操作系统。比较 Docker 镜像:
  • ubuntu:20.04 是 73.9MB ( glibc : GNU-libc)
  • alpine:3.12.1 是 5.57MB (musl libc)

  • 所以添加一个操作系统(即使是最小的)会增加这个额外的负担。 alpine 的最小尺寸看起来很有吸引力 - 但它的 libc 可能与依赖 glibc 的包不兼容。
    然而,CGO_ENABLED=0 非常适合 scratch docker 镜像部署——因为不需要捆绑主机操作系统。
    但是,如果您的应用程序导入带有 C 代码的包(例如 go-sqlite3 ),那么您的构建必须启用 CGO。

    关于go - 为什么 CGO_ENABLED=1 默认?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/64531437/

    10-09 15:19
    查看更多