]> Cypherpunks repositories - gostls13.git/commitdiff
go/build: change the search order for "vendor/" paths based on srcDir
authorBryan C. Mills <bcmills@google.com>
Thu, 28 Feb 2019 21:04:43 +0000 (16:04 -0500)
committerBryan C. Mills <bcmills@google.com>
Fri, 8 Mar 2019 18:03:06 +0000 (18:03 +0000)
If srcDir is within GOROOT, prefer GOROOT.
Otherwise, prefer GOPATH.

The attached tests may seem a bit strange; they will make more sense
in a followup CL.

Updates #16333
Updates #30241
Updates #30228

Change-Id: Ic5f1334cce5e242d7f49080aba083bcf2080dee3
Reviewed-on: https://go-review.googlesource.com/c/go/+/164619
Run-TryBot: Bryan C. Mills <bcmills@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Jay Conrod <jayconrod@google.com>
src/cmd/go/testdata/script/gopath_std_vendor.txt [new file with mode: 0644]
src/go/build/build.go

diff --git a/src/cmd/go/testdata/script/gopath_std_vendor.txt b/src/cmd/go/testdata/script/gopath_std_vendor.txt
new file mode 100644 (file)
index 0000000..d53744b
--- /dev/null
@@ -0,0 +1,41 @@
+env GO111MODULE=off
+
+[!gc] skip
+
+# A package importing 'net/http' should resolve its dependencies
+# to the package 'vendor/golang.org/x/net/http2/hpack' within GOROOT.
+cd importnethttp
+go list -deps -f '{{.ImportPath}} {{.Dir}}'
+stdout ^internal/x/net/http2/hpack
+stdout $GOROOT[/\\]src[/\\]internal[/\\]x[/\\]net[/\\]http2[/\\]hpack
+! stdout $GOPATH[/\\]src[/\\]vendor
+
+# In the presence of $GOPATH/src/vendor/golang.org/x/net/http2/hpack,
+# a package in GOPATH importing 'golang.org/x/net/http2/hpack' should
+# resolve its dependencies in GOPATH/src.
+cd ../issue16333
+go build .
+
+go list -deps -f '{{.ImportPath}} {{.Dir}}' .
+stdout $GOPATH[/\\]src[/\\]vendor[/\\]golang.org[/\\]x[/\\]net[/\\]http2[/\\]hpack
+! stdout $GOROOT[/\\]src[/\\]vendor
+
+go list -test -deps -f '{{.ImportPath}} {{.Dir}}' .
+stdout $GOPATH[/\\]src[/\\]vendor[/\\]golang.org[/\\]x[/\\]net[/\\]http2[/\\]hpack
+! stdout $GOROOT[/\\]src[/\\]vendor
+
+-- issue16333/issue16333.go --
+package vendoring17
+
+import _ "golang.org/x/net/http2/hpack"
+-- issue16333/issue16333_test.go --
+package vendoring17
+
+import _ "testing"
+import _ "golang.org/x/net/http2/hpack"
+-- importnethttp/http.go --
+package importnethttp
+
+import _ "net/http"
+-- $GOPATH/src/vendor/golang.org/x/net/http2/hpack/hpack.go --
+package hpack
index 94db198764c12aefbdb3441f1f8cca805c09aa53..c8aa872bd2df2e9e31054e7505d445e38d655503 100644 (file)
@@ -647,18 +647,28 @@ func (ctxt *Context) Import(path string, srcDir string, mode ImportMode) (*Packa
 
                // Determine directory from import path.
                if ctxt.GOROOT != "" {
-                       dir := ctxt.joinPath(ctxt.GOROOT, "src", path)
-                       if ctxt.Compiler != "gccgo" {
-                               isDir := ctxt.isDir(dir)
-                               binaryOnly = !isDir && mode&AllowBinary != 0 && pkga != "" && ctxt.isFile(ctxt.joinPath(ctxt.GOROOT, pkga))
-                               if isDir || binaryOnly {
-                                       p.Dir = dir
-                                       p.Goroot = true
-                                       p.Root = ctxt.GOROOT
-                                       goto Found
+                       // If the package path starts with "vendor/", only search GOROOT before
+                       // GOPATH if the importer is also within GOROOT. That way, if the user has
+                       // vendored in a package that is subsequently included in the standard
+                       // distribution, they'll continue to pick up their own vendored copy.
+                       gorootFirst := srcDir == "" || !strings.HasPrefix(path, "vendor/")
+                       if !gorootFirst {
+                               _, gorootFirst = ctxt.hasSubdir(ctxt.GOROOT, srcDir)
+                       }
+                       if gorootFirst {
+                               dir := ctxt.joinPath(ctxt.GOROOT, "src", path)
+                               if ctxt.Compiler != "gccgo" {
+                                       isDir := ctxt.isDir(dir)
+                                       binaryOnly = !isDir && mode&AllowBinary != 0 && pkga != "" && ctxt.isFile(ctxt.joinPath(ctxt.GOROOT, pkga))
+                                       if isDir || binaryOnly {
+                                               p.Dir = dir
+                                               p.Goroot = true
+                                               p.Root = ctxt.GOROOT
+                                               goto Found
+                                       }
                                }
+                               tried.goroot = dir
                        }
-                       tried.goroot = dir
                }
                if ctxt.Compiler == "gccgo" && goroot.IsStandardPackage(ctxt.GOROOT, ctxt.Compiler, path) {
                        p.Dir = ctxt.joinPath(ctxt.GOROOT, "src", path)
@@ -678,6 +688,24 @@ func (ctxt *Context) Import(path string, srcDir string, mode ImportMode) (*Packa
                        tried.gopath = append(tried.gopath, dir)
                }
 
+               // If we tried GOPATH first due to a "vendor/" prefix, fall back to GOPATH.
+               // That way, the user can still get useful results from 'go list' for
+               // standard-vendored paths passed on the command line.
+               if ctxt.GOROOT != "" && tried.goroot == "" {
+                       dir := ctxt.joinPath(ctxt.GOROOT, "src", path)
+                       if ctxt.Compiler != "gccgo" {
+                               isDir := ctxt.isDir(dir)
+                               binaryOnly = !isDir && mode&AllowBinary != 0 && pkga != "" && ctxt.isFile(ctxt.joinPath(ctxt.GOROOT, pkga))
+                               if isDir || binaryOnly {
+                                       p.Dir = dir
+                                       p.Goroot = true
+                                       p.Root = ctxt.GOROOT
+                                       goto Found
+                               }
+                       }
+                       tried.goroot = dir
+               }
+
                // package was not found
                var paths []string
                format := "\t%s (vendor tree)"