go build 是啥意思? (去构建与去安装)

Posted

技术标签:

【中文标题】go build 是啥意思? (去构建与去安装)【英文标题】:What does go build build? (go build vs. go install)go build 是什么意思? (去构建与去安装) 【发布时间】:2015-08-17 05:18:44 【问题描述】:

新的 Go 程序员通常不知道或对基本的 go build 命令的作用感到困惑。

go buildgo install 命令的具体作用是什么?它们将结果/输出放在哪里?

【问题讨论】:

go build vs go install 【参考方案1】:

go 命令的作用取决于我们是为“普通”包还是为特殊的"main" 包运行它。

对于包裹

go build   构建你的包然后丢弃结果go install 构建然后安装您的$GOPATH/pkg 目录中的包。

对于命令(包main

go build   构建命令并将结果留在当前工作目录go install 在临时目录中构建命令,然后将其移动到 $GOPATH/bin

将什么传递给go build

您可以将 packages 传递给 go build,您想要构建的软件包。您还可以从单个目录传递.go 文件列表,然后将其视为指定单个包的源文件列表。

如果没有提供包(导入路径),则构建应用到当前目录。

导入路径可能包含一个或多个"..." 通配符(在这种情况下,它是一个模式)。 ... 可以匹配任何字符串,例如net/... 匹配 net 包和位于其任何子文件夹中的包。命令

go build ./...

常用于在当前文件夹中构建包,所有包递归下来。在项目根目录中发出的这个命令会构建完整的项目。

有关指定包的更多信息,请运行go help packages

关于模块

在 Go 1.11 中引入了对 Go 模块的初步支持,从 Go 1.13 开始,模块成为默认模块。当go 工具从包含go.mod 文件(或当前文件夹的父文件夹之一)的文件夹运行时,go 工具以模块感知 模式运行(传统模式称为 GOPATH 模式)。

在模块感知模式下,GOPATH 不再定义导入的含义 在构建期间,但它仍然存储下载的依赖项(在 GOPATH/pkg/mod 中) 并安装命令(在 GOPATH/bin 中,除非设置了 GOBIN)。

构建模块时,构建的内容由构建列表指定。构建列表最初只包含主模块(包含运行go命令的目录的模块),并且主模块的依赖被递归地添加到构建列表中(依赖的依赖也被添加)。

如需更多信息,请运行go help modules


基本上,您可以使用go build 来检查是否可以构建包(连同它们的依赖项),而go install 也(永久)将结果安装在$GOPATH 的正确文件夹中。

go build 将在一切正常时静默终止,如果包无法构建/编译,则会给您错误消息。

每当go 工具安装包或二进制文件时,它也会安装它所具有的任何依赖项,因此运行go install 还将自动安装您的程序所依赖的包(公开可用,“可获取”包)。

首先,请阅读官方How to Write Go Code 页面。

有关go 工具的更多信息:Command go

您还可以通过运行以下命令获得更多帮助:

go help build

还值得注意的是,从 Go 1.5 开始 go install 也会删除由 go build (source) 创建的可执行文件:

如果'go install'(不带参数,表示当前目录) 成功,删除由“go build”编写的可执行文件(如果存在)。这样可以避免留下陈旧的二进制文件...

为了完成列表,go run 将您的应用程序编译到一个临时文件夹中,并启动该可执行二进制文件。当应用程序退出时,它会正确清理临时文件。

问题灵感来自 Dave Cheney 的 What does go build build?

【讨论】:

看起来很奇怪,如果 go install 与以前安装的可执行文件相同,它不会更新可执行文件......这里有什么见解吗?【参考方案2】:

对于包裹:

go build:构建你的包然后丢弃结果

在 Go 1.10(2018 年第一季度)之后,这将不是真的,感谢 CL 68116 和 CL 75473。请参阅this thread,我在这里引用。

go buildgo install 命令构建的具体作用

每当 go 工具安装一个包或二进制文件时,它也会安装它拥有的任何依赖项,因此运行 go install 还会自动安装您的程序所依赖的包(公开可用的“go gettable”包)。

其实...go install 也会随着 Go 1.10 的变化而改变,除了新的缓存:

go install”命令不再安装指定包的依赖项 (CL 75850)。

如果您运行“go install foo”,则安装的唯一内容是foo

以前,它是多种多样的。如果依赖项已过期,“go install”也会安装任何依赖项。 在“go install”期间隐式安装依赖项给用户带来了很多困惑和头痛,但以前需要启用增量构建。 没有了。 我们认为新的“install what I said”语义将更容易理解,特别是因为从错误报告中可以清楚地看出许多用户已经期望它们。要在“go install”期间强制安装依赖项,请使用新的“go install -i,类似于“go build -i”和“go test -i”。

go install”用于安装任何重建的依赖项这一事实最常与 -a 一起导致混淆,这意味着“force rebuild of all dependencies”。 现在,“go install -a myprog”将强制完全重建 myprog 以及 myprog 本身的所有依赖项,但只会安装 myprog。 (当然,所有重建的依赖项仍将保存在构建缓存中。) 结合新的基于内容的陈旧性分析,使这个案例更易于理解尤其重要,因为它看到了比以前更频繁地重建依赖项的充分理由,这会增加“为什么要安装我的依赖项”的困惑。 例如,如果您运行“go install -gcflags=-N myprog”,它会安装一个没有编译器优化的 myprog,但它不再重新安装 myprog 使用的标准库中没有编译器优化的包。

【讨论】:

go build,有gets吗?我有一个构建错误cannot find package "github.com/spf13/cobra" in any of:…。我不知道如何告诉它得到它。我需要明确得到吗? @ctrl-alt-delor 使用哪个版本的 Go?您的项目中是否有 go.mod 文件? go version go1.11.4 linux/amd64。我不知道 go.mod。我正在重新构建https://github.com/cbroglie/mustache/blob/master/cmd/mustache/main.go,这很奇怪,因为我刚刚构建了整个包,并使用这个示例作为基础,并且我确实创建了一个更基本的版本(但不使用这个库)。我看不出它是如何与 mustache 包一起安装的。 @ctrl-alt-delor 所以 cobr 被出售给github.com/cbroglie/mustache/tree/master/cmd/mustache/vendor/…。你的 GOPATH 设置正确了吗? 我发现了你已经发现的东西。该软件包位于供应商子目录中:这就是它没有安装的原因。但是我不知道为什么它现在不安装它。或者如何使用供应商目录(如果我将它复制到我的目录)。

以上是关于go build 是啥意思? (去构建与去安装)的主要内容,如果未能解决你的问题,请参考以下文章

go build和go install的区别

build.xml是啥

build.xml是啥?

忍者中的词法错误是啥意思?

qmake 中的 host_build 是啥?

我怎么安不了IE9,下载了之后会弹出这样一个对话框,大家看看是啥意思,帮帮忙啊