Go 如何快速构建/安装交叉编译的嵌套包?
我有一个包含一组嵌套go包的存储库,其组织如下:Go 如何快速构建/安装交叉编译的嵌套包?,go,Go,我有一个包含一组嵌套go包的存储库,其组织如下: $GOPATH/src/ - mypackage/common/utils.go - mypackage/app1/main.go - mypackage/app2/main.go ... 它编译成少量二进制文件。对于发布,我正在为多种平台/架构进行交叉编译(我使用不同的GOOS和GOARCH重复部署)。我试图将编译结果写入我选择的目录,但我正在使用工具链 我可以: 在为我自己的体系结构编译时,将GOBIN和go install
$GOPATH/src/
- mypackage/common/utils.go
- mypackage/app1/main.go
- mypackage/app2/main.go
...
它编译成少量二进制文件。对于发布,我正在为多种平台/架构进行交叉编译(我使用不同的GOOS
和GOARCH
重复部署)。我试图将编译结果写入我选择的目录,但我正在使用工具链
我可以:
GOBIN
和go install
结合起来
(即不交叉编译):
但不幸的是,GOBIN
与交叉编译冲突,例如:
# Throws: "cannot install cross-compiled binaries when GOBIN is set"
GOBIN=/somedir/bin GOARCH=amdm64 GOOS=darwin go install mypackage/app1 mypackage/app2
go build
和GOOS=X
和GOARCH=Y
当go build
被赋予多个包时,它不再发出二进制文件——它只是检查代码是否编译。要发出所有二进制文件,似乎我必须为每个子包运行一次go build
,因此需要更长的时间,尤其是使用-a
构建时
像这样使用go build
的另一个可能问题是,它可能会在同一个工作区中跨多个体系结构混合二进制文件和中间结果。但也许这只是品味的问题。希望该工具链能够为不同的体系结构保持缓存结果的独立性- go build vs go install:(关于交叉编译或多包设置的少量信息)
- 使用go 1.5进行交叉编译。:(并没有专门针对多包/通用代码编译。而且,据我所知,关于必须将标准库重新编译到/usr/local/go/pkg中的声明似乎不再适用于1.9.1)
- 转到生成多个嵌套包:。(接受的答案,
的行为与在一个build命令中传递多个包相同,因此不输出二进制文件。该线程也不涉及交叉编译)go build./…
# I'm not on this platform, so this is a cross compile
GOOS=darwin GOARCH=amd64 go install mypackage/app1 mypackage/app2
假设您的包位于$GOPATH/src/mypackage
中,上述命令将把两个二进制文件安装到:
$GOPATH/bin/darwin_amd64/{app1, app2}
以及.a在中编译依赖项文件:
$GOPATH/pkg/darwin_amd64/mypackage/{app1,app2,common}
如果对所有计划支持的平台都在for循环中运行此过程,那么此过程的一个麻烦是,当您传递与本地架构匹配的GOOS=x GOARCH=y
时(即,不交叉编译),那么可执行文件将直接放在$GOPATH/bin/
而不是$GOPATH/bin/x_y/
中
(另一方面,包总是以$GOPATH/pkg/x_y/
结束,不管是否交叉编译)
要确定您的本地体系结构,您可以按照以下回答中的步骤进行操作:
模拟GOBIN=/foo/bin-GOOS=x GOARCH=y安装mypackage/app{1,2,3}
更改$GOPATH
对where-go-install写入输出几乎没有影响。使用一些go命令,如go-get
,可以通过在$GOPATH
前面添加新组件来调整软件包的安装位置。但是在go 1.9中,go install
将始终复制bin/
文件夹中的二进制文件,该文件夹是包含要安装的软件包的src/
的同级文件夹
您可以假装源文件位于/foo/src/mypackage
(您可以使用符号链接),然后执行GOPATH=/foo-GOOS=x GOARCH=y安装mypackage/app{1,2,3}
,而不是使用GOBIN=/foo/bin
。这将把二进制文件放入/foo/bin
,因为我在上一段中描述了这种行为
不过,从您期望的位置获取二进制文件可能比到处复制源代码树更简单。您不应该在
GOROOT
中安装任何东西(甚至不应该设置该变量),您的意思是GOPATH
?如果要将输出放置在特定位置,也可以使用go build-o
。Woops。我是说GOPATH。由于某种原因,我的容器有GOPATH=/usr/local/go,它会干扰一些事情。更新了答案go build-o
无法处理多个子包,因此出现了这个问题。
$GOPATH/bin/darwin_amd64/{app1, app2}
$GOPATH/pkg/darwin_amd64/mypackage/{app1,app2,common}