如何从代码中获取当前GOPATH
如何从代码块中获取当前的如何从代码中获取当前GOPATH,go,Go,如何从代码块中获取当前的GOPATH runtime只有GOROOT: // GOROOT returns the root of the Go tree. // It uses the GOROOT environment variable, if set, // or else the root used during the Go build. func GOROOT() string { s := gogetenv("GOROOT") if s != "" {
GOPATH
runtime
只有GOROOT
:
// GOROOT returns the root of the Go tree.
// It uses the GOROOT environment variable, if set,
// or else the root used during the Go build.
func GOROOT() string {
s := gogetenv("GOROOT")
if s != "" {
return s
}
return defaultGoroot
}
我可以制作一个用GOPATH
替换GOROOT
的函数,但是是否有用于此的内置程序?使用
从文档:
Getenv检索由
钥匙它返回值,如果变量不为空,则该值为空
现在
例如:
package main
import (
"fmt"
"os"
)
func main() {
fmt.Println(os.Getenv("GOPATH"))
}
更新Go 1.8+
Go 1.8具有通过Go/build导出的默认GOPATH:
package main
import (
"fmt"
"go/build"
"os"
)
func main() {
gopath := os.Getenv("GOPATH")
if gopath == "" {
gopath = build.Default.GOPATH
}
fmt.Println(gopath)
}
自Go 1.8以来,有一个:
GOPATH
环境变量指定
工作空间。它默认为一个名为go in your home的目录
目录,因此在Unix上是$HOME/go
,在Plan 9上是$HOME/go
,以及
Windows上的%USERPROFILE%\go
(通常是C:\Users\YourName\go
)
这意味着GOPATH
环境变量不一定设置为任何特定的值
您仍然可以使用os.Getenv
获取该值,但如果未设置该值,则需要确保使用特定于平台的默认值,例如使用:
你应该使用软件包
今天我为了我正在做的事情而把这件事搞砸了,这比我想象的要烦人得多。最后,在我对它进行的各种测试中,这似乎对我有效(而不是“严格”的测试) 注意,如果GOPATH上列出了多条路径,我决定只使用第1条路径,因为我怀疑很少有人会列出超过1条路径,第一条路径是
go-get
放置源的位置(我猜)。此代码也不考虑路径是否有效
还要注意,要在获得GOPATH后构建文件路径,我必须使用
path/filepath.Join()
notpath.Join()
。如果第一个参数包含\,则前者将在windows上使用\和/或用于其他参数。虽然windows显然可以接受/for路径,但所有类似my PATH和GOPATH的环境变量都是使用windows的普通\来编写的path.Join()
used/,生成无效路径。在go 1.8中,GOPATH env变量是可选的。如果用户没有呢?有没有办法得到默认值?我认为go运行时应该有办法获得gopath,让go自己为您解决。@tothemario我给出了一个答案,告诉您如何从go 1.8中获得有效的gopath
。不过,我同意理想情况下,运行时应该提供一种方法,使用Go 1.8默认Go path实现中的代码获取用户的GOPATH
@tothemario更新答案。别忘了GOPATH可以列出多个路径,并用操作系统的路径分隔符分隔。这有点过分。我们可以使用Go自己源代码中的代码来获得默认的Go路径。看@codefank,当然有更简单的方法,你的答案也是有效的。我喜欢的是,当有疑问时,它会尝试多种方法来查找主目录,如果都失败了,它实际上会返回一个错误。因此,此代码的用户可以返回有意义的错误消息。如果您只是返回一个空字符串,用户必须检查它是否为空。如果他们忽略了这一点,在某些边缘情况下,这可能会导致意外的行为或奇怪的错误。go homedir对于查找home dir非常有用。但如果Go本身使用defaultGOPATH函数,那么处理Go构建代码本身不处理的边缘情况又有什么意义呢。总之,让用户决定他们最喜欢什么:)
package main
import (
"fmt"
"log"
"os"
"github.com/mitchellh/go-homedir"
)
func main() {
p, err := gopath()
if err != nil {
log.Fatalf("Error finding GOPATH: %v", err)
}
fmt.Println(p)
}
func gopath() (string, error) {
s := os.Getenv("GOPATH")
if s != "" {
return s, nil
}
return homedir.Expand("~/go")
}
package main
import (
"fmt"
"go/build"
)
func main() {
fmt.Println(build.Default.GOPATH)
}
goPath := strings.Split(os.Getenv("GOPATH"), string(os.PathListSeparator))
if len(goPath) == 0 {
goPath = append(goPath, build.Default.GOPATH)
} else if goPath[0] == "" {
goPath[0] = build.Default.GOPATH
}