我在具有以下架构的docker容器中构建了以下代码:
cat / proc / version
Linux版本3.16.7-tinycore64(root @ 064f0e1ce709)(gcc版本4.7.2(Debian 4.7.2-5))#1 SMP Tue 12月16日23:03:39 UTC 2014
package main
import "fmt"
func main() {
fmt.Println("Hello")
}
二进制分发,在busybox容器上运行没有问题,具有相同的体系结构而不安装golang。
当我对以下代码执行相同操作时:
package main
import (
"fmt"
"net/http"
)
const (
port = ":80"
)
var calls = 0
func HelloWorld(w http.ResponseWriter, r *http.Request) {
calls++
fmt.Fprintf(w, "Hello, world! You have called me %d times.\n", calls)
}
func init() {
fmt.Printf("Started server at http://localhost%v.\n", port)
http.HandleFunc("/", HelloWorld)
http.ListenAndServe(port, nil)
}
func main() {}
然后我得到:
ash:./ hello_world:not found
我可能会遗漏一些依赖项 - 比如“net / http”? 但我认为go build会将所有内容构建到二进制文件中 这适用于go build&去安装。
有什么想法吗?
答案 0 :(得分:1)
答案很可能是this article中描述的答案。
标准库的一些关键部分使用CGO [...]如果您交叉编译转到Darwin或Linux,您的程序将不使用系统DNS解析器。他们也无法使用本机主机证书存储区。他们也无法查找用户的主目录。
默认情况下,CGO会动态链接某些标准系统接口。
文章建议使用gonative来解决问题。如果那不是你的一杯茶,有些人建议使用:
go build -ldflags "-linkmode external -extldflags -static"
另请阅读:https://groups.google.com/d/topic/golang-nuts/H-NTwhQVp-8/discussion
答案 1 :(得分:1)
我认为你需要禁用cgo并使用netgo
标志构建:
默认情况下,net package需要cgo,因为主机正在运行 系统通常必须调解网络呼叫设置。在某些系统上, 但是,可以使用没有cgo的网络,并且有用 这样做,例如避免动态链接。新的构建标签netgo (默认情况下关闭)允许在纯Go中构建网络包 在那些可能的系统上。
netgo
代码需要版本1.2 and above。