mirror of https://github.com/k3s-io/k3s
130 lines
3.2 KiB
Go
130 lines
3.2 KiB
Go
package main
|
|
|
|
import (
|
|
"fmt"
|
|
"log"
|
|
"os"
|
|
"os/exec"
|
|
"path/filepath"
|
|
"strings"
|
|
)
|
|
|
|
var cmdGo = &Command{
|
|
Name: "go",
|
|
Args: "command [arguments]",
|
|
Short: "run the go tool with saved dependencies",
|
|
Long: `
|
|
Go runs the go tool with a modified GOPATH giving access to
|
|
dependencies saved in Godeps.
|
|
|
|
Any go tool command can run this way, but "godep go get"
|
|
is unnecessary and has been disabled. Instead, use
|
|
"godep go install".
|
|
`,
|
|
Run: runGo,
|
|
OnlyInGOPATH: true,
|
|
}
|
|
|
|
// Find the godep GOPATH for this file tree and run the go tool.
|
|
func runGo(cmd *Command, args []string) {
|
|
gopath := prepareGopath()
|
|
if s := os.Getenv("GOPATH"); s != "" {
|
|
gopath += string(os.PathListSeparator) + os.Getenv("GOPATH")
|
|
}
|
|
if len(args) > 0 && args[0] == "get" {
|
|
log.Printf("invalid subcommand: %q", "go get")
|
|
fmt.Fprintln(os.Stderr, "Use 'godep go install' instead.")
|
|
fmt.Fprintln(os.Stderr, "Run 'godep help go' for usage.")
|
|
os.Exit(2)
|
|
}
|
|
c := exec.Command("go", args...)
|
|
c.Env = append(envNoGopath(), "GOPATH="+gopath)
|
|
c.Stdin = os.Stdin
|
|
c.Stdout = os.Stdout
|
|
c.Stderr = os.Stderr
|
|
err := c.Run()
|
|
if err != nil {
|
|
log.Fatalln("go", err)
|
|
}
|
|
}
|
|
|
|
// prepareGopath reads dependency information from the filesystem
|
|
// entry name, fetches any necessary code, and returns a gopath
|
|
// causing the specified dependencies to be used.
|
|
func prepareGopath() (gopath string) {
|
|
dir, isDir := findGodeps()
|
|
if dir == "" {
|
|
log.Fatalln("No Godeps found (or in any parent directory)")
|
|
}
|
|
if !isDir {
|
|
log.Fatalln(strings.TrimSpace(needSource))
|
|
}
|
|
return filepath.Join(dir, "Godeps", "_workspace")
|
|
}
|
|
|
|
// findGodeps looks for a directory entry "Godeps" in the
|
|
// current directory or any parent, and returns the containing
|
|
// directory and whether the entry itself is a directory.
|
|
// If Godeps can't be found, findGodeps returns "".
|
|
// For any other error, it exits the program.
|
|
func findGodeps() (dir string, isDir bool) {
|
|
wd, err := os.Getwd()
|
|
if err != nil {
|
|
log.Fatalln(err)
|
|
}
|
|
return findInParents(wd, "Godeps")
|
|
}
|
|
|
|
// isRoot returns true iff a path is a root.
|
|
// On Unix: "/".
|
|
// On Windows: "C:\", "D:\", ...
|
|
func isRoot(p string) bool {
|
|
p = filepath.Clean(p)
|
|
volume := filepath.VolumeName(p)
|
|
|
|
p = strings.TrimPrefix(p, volume)
|
|
p = filepath.ToSlash(p)
|
|
|
|
return p == "/"
|
|
}
|
|
|
|
// findInParents returns the path to the directory containing name
|
|
// in dir or any ancestor, and whether name itself is a directory.
|
|
// If name cannot be found, findInParents returns the empty string.
|
|
func findInParents(dir, name string) (container string, isDir bool) {
|
|
for {
|
|
fi, err := os.Stat(filepath.Join(dir, name))
|
|
if os.IsNotExist(err) && isRoot(dir) {
|
|
return "", false
|
|
}
|
|
if os.IsNotExist(err) {
|
|
dir = filepath.Dir(dir)
|
|
continue
|
|
}
|
|
if err != nil {
|
|
log.Fatalln(err)
|
|
}
|
|
return dir, fi.IsDir()
|
|
}
|
|
}
|
|
|
|
func envNoGopath() (a []string) {
|
|
for _, s := range os.Environ() {
|
|
if !strings.HasPrefix(s, "GOPATH=") {
|
|
a = append(a, s)
|
|
}
|
|
}
|
|
return a
|
|
}
|
|
|
|
const needSource = `
|
|
outdated Godeps missing source code
|
|
|
|
This dependency list was created with an old version of godep.
|
|
|
|
To work around this, you have two options:
|
|
1. Run 'godep restore', and try again.
|
|
2. Ask the maintainer to switch to a newer version of godep,
|
|
then try again with the updated package.
|
|
`
|