// Copyright 2020 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package packages_test

import (
	"fmt"
	"log"
	"os"
	"path/filepath"
	"reflect"
	"sort"
	"testing"

	"golang.org/x/tools/go/packages"
	"golang.org/x/tools/go/packages/packagestest"
	"golang.org/x/tools/internal/testenv"
)

const (
	commonMode = packages.NeedName | packages.NeedFiles |
		packages.NeedCompiledGoFiles | packages.NeedImports | packages.NeedSyntax
	everythingMode = commonMode | packages.NeedDeps | packages.NeedTypes |
		packages.NeedTypesSizes
)

func TestOverlayChangesPackageName(t *testing.T) {
	testAllOrModulesParallel(t, testOverlayChangesPackageName)
}
func testOverlayChangesPackageName(t *testing.T, exporter packagestest.Exporter) {
	log.SetFlags(log.Lshortfile)
	exported := packagestest.Export(t, exporter, []packagestest.Module{{
		Name: "fake",
		Files: map[string]interface{}{
			"a.go": "package foo\nfunc f(){}\n",
		},
		Overlay: map[string][]byte{
			"a.go": []byte("package foox\nfunc f(){}\n"),
		},
	}})
	defer exported.Cleanup()
	exported.Config.Mode = packages.NeedName

	initial, err := packages.Load(exported.Config,
		filepath.Dir(exported.File("fake", "a.go")))
	if err != nil {
		t.Fatalf("failed to load: %v", err)
	}
	if len(initial) != 1 || initial[0].ID != "fake" || initial[0].Name != "foox" {
		t.Fatalf("got %v, expected [fake]", initial)
	}
	if len(initial[0].Errors) != 0 {
		t.Fatalf("got %v, expected no errors", initial[0].Errors)
	}
	log.SetFlags(0)
}
func TestOverlayChangesBothPackageNames(t *testing.T) {
	testAllOrModulesParallel(t, testOverlayChangesBothPackageNames)
}
func testOverlayChangesBothPackageNames(t *testing.T, exporter packagestest.Exporter) {
	log.SetFlags(log.Lshortfile)
	exported := packagestest.Export(t, exporter, []packagestest.Module{{
		Name: "fake",
		Files: map[string]interface{}{
			"a.go":      "package foo\nfunc g(){}\n",
			"a_test.go": "package foo\nfunc f(){}\n",
		},
		Overlay: map[string][]byte{
			"a.go":      []byte("package foox\nfunc g(){}\n"),
			"a_test.go": []byte("package foox\nfunc f(){}\n"),
		},
	}})
	defer exported.Cleanup()
	exported.Config.Mode = commonMode

	initial, err := packages.Load(exported.Config,
		filepath.Dir(exported.File("fake", "a.go")))
	if err != nil {
		t.Fatalf("failed to load: %v", err)
	}
	if len(initial) != 3 {
		t.Errorf("got %d packges, expected 3", len(initial))
	}
	want := []struct {
		id, name string
		count    int
	}{
		{"fake", "foox", 1},
		{"fake [fake.test]", "foox", 2},
		{"fake.test", "main", 1},
	}
	if len(initial) != 3 {
		t.Fatalf("expected 3 packages, got %v", len(initial))
	}
	for i := 0; i < 3; i++ {
		if ok := checkPkg(t, initial[i], want[i].id, want[i].name, want[i].count); !ok {
			t.Errorf("%d: got {%s %s %d}, expected %v", i, initial[i].ID,
				initial[i].Name, len(initial[i].Syntax), want[i])
		}
		if len(initial[i].Errors) != 0 {
			t.Errorf("%d: got %v, expected no errors", i, initial[i].Errors)
		}
	}
	log.SetFlags(0)
}
func TestOverlayChangesTestPackageName(t *testing.T) {
	testAllOrModulesParallel(t, testOverlayChangesTestPackageName)
}
func testOverlayChangesTestPackageName(t *testing.T, exporter packagestest.Exporter) {
	exported := packagestest.Export(t, exporter, []packagestest.Module{{
		Name: "fake",
		Files: map[string]interface{}{
			"a_test.go": "package foo\nfunc f(){}\n",
		},
		Overlay: map[string][]byte{
			"a_test.go": []byte("package foox\nfunc f(){}\n"),
		},
	}})
	defer exported.Cleanup()
	exported.Config.Mode = commonMode

	initial, err := packages.Load(exported.Config,
		filepath.Dir(exported.File("fake", "a_test.go")))
	if err != nil {
		t.Fatalf("failed to load: %v", err)
	}
	if len(initial) != 3 {
		t.Errorf("got %d packges, expected 3", len(initial))
	}
	want := []struct {
		id, name string
		count    int
	}{
		{"fake", "foox", 0},
		{"fake [fake.test]", "foox", 1},
		{"fake.test", "main", 1},
	}
	if len(initial) != 3 {
		t.Fatalf("expected 3 packages, got %v", len(initial))
	}
	for i := 0; i < 3; i++ {
		if ok := checkPkg(t, initial[i], want[i].id, want[i].name, want[i].count); !ok {
			t.Errorf("got {%s %s %d}, expected %v", initial[i].ID,
				initial[i].Name, len(initial[i].Syntax), want[i])
		}
	}
	if len(initial[0].Errors) != 0 {
		t.Fatalf("got %v, expected no errors", initial[0].Errors)
	}
	log.SetFlags(0)
}

func checkPkg(t *testing.T, p *packages.Package, id, name string, syntax int) bool {
	t.Helper()
	if p.ID == id && p.Name == name && len(p.Syntax) == syntax {
		return true
	}
	return false
}

func TestOverlayXTests(t *testing.T) {
	testAllOrModulesParallel(t, testOverlayXTests)
}

// This test checks the behavior of go/packages.Load with an overlaid
// x test. The source of truth is the go/packages.Load results for the
// exact same package, just on-disk.
func testOverlayXTests(t *testing.T, exporter packagestest.Exporter) {
	const aFile = `package a; const C = "C"; func Hello() {}`
	const aTestVariant = `package a

import "testing"

const TestC = "test" + C

func TestHello(){
	Hello()
}`
	const aXTest = `package a_test

import (
	"testing"

	"golang.org/fake/a"
)

const xTestC = "x" + a.C

func TestHello(t *testing.T) {
	a.Hello()
}`

	// First, get the source of truth by loading the package, all on disk.
	onDisk := packagestest.Export(t, exporter, []packagestest.Module{{
		Name: "golang.org/fake",
		Files: map[string]interface{}{
			"a/a.go":        aFile,
			"a/a_test.go":   aTestVariant,
			"a/a_x_test.go": aXTest,
		},
	}})
	defer onDisk.Cleanup()

	onDisk.Config.Mode = commonMode
	onDisk.Config.Tests = true
	onDisk.Config.Mode = packages.LoadTypes
	initial, err := packages.Load(onDisk.Config, fmt.Sprintf("file=%s", onDisk.File("golang.org/fake", "a/a_x_test.go")))
	if err != nil {
		t.Fatal(err)
	}
	wantPkg := initial[0]

	exported := packagestest.Export(t, exporter, []packagestest.Module{{
		Name: "golang.org/fake",
		Files: map[string]interface{}{
			"a/a.go":        aFile,
			"a/a_test.go":   aTestVariant,
			"a/a_x_test.go": ``, // empty x test on disk
		},
		Overlay: map[string][]byte{
			"a/a_x_test.go": []byte(aXTest),
		},
	}})
	defer exported.Cleanup()

	if len(initial) != 1 {
		t.Fatalf("expected 1 package, got %d", len(initial))
	}
	// Confirm that the overlaid package is identical to the on-disk version.
	pkg := initial[0]
	if !reflect.DeepEqual(wantPkg, pkg) {
		t.Fatalf("mismatched packages: want %#v, got %#v", wantPkg, pkg)
	}
	xTestC := constant(pkg, "xTestC")
	if xTestC == nil {
		t.Fatalf("no value for xTestC")
	}
	got := xTestC.Val().String()
	// TODO(rstambler): Ideally, this test would check that the test variant
	// was imported, but that's pretty complicated.
	if want := `"xC"`; got != want {
		t.Errorf("got: %q, want %q", got, want)
	}
}

func TestOverlay(t *testing.T) { testAllOrModulesParallel(t, testOverlay) }
func testOverlay(t *testing.T, exporter packagestest.Exporter) {
	exported := packagestest.Export(t, exporter, []packagestest.Module{{
		Name: "golang.org/fake",
		Files: map[string]interface{}{
			"a/a.go":      `package a; import "golang.org/fake/b"; const A = "a" + b.B`,
			"b/b.go":      `package b; import "golang.org/fake/c"; const B = "b" + c.C`,
			"c/c.go":      `package c; const C = "c"`,
			"c/c_test.go": `package c; import "testing"; func TestC(t *testing.T) {}`,
			"d/d.go":      `package d; const D = "d"`,
		}}})
	defer exported.Cleanup()

	for i, test := range []struct {
		overlay  map[string][]byte
		want     string // expected value of a.A
		wantErrs []string
	}{
		{nil, `"abc"`, nil},                 // default
		{map[string][]byte{}, `"abc"`, nil}, // empty overlay
		{map[string][]byte{exported.File("golang.org/fake", "c/c.go"): []byte(`package c; const C = "C"`)}, `"abC"`, nil},
		{map[string][]byte{exported.File("golang.org/fake", "b/b.go"): []byte(`package b; import "golang.org/fake/c"; const B = "B" + c.C`)}, `"aBc"`, nil},
		// Overlay with an existing file in an existing package adding a new import.
		{map[string][]byte{exported.File("golang.org/fake", "b/b.go"): []byte(`package b; import "golang.org/fake/d"; const B = "B" + d.D`)}, `"aBd"`, nil},
		// Overlay with an existing file in an existing package.
		{map[string][]byte{exported.File("golang.org/fake", "c/c.go"): []byte(`package c; import "net/http"; const C = http.MethodGet`)}, `"abGET"`, nil},
		// Overlay with a new file in an existing package.
		{map[string][]byte{
			exported.File("golang.org/fake", "c/c.go"):                                               []byte(`package c;`),
			filepath.Join(filepath.Dir(exported.File("golang.org/fake", "c/c.go")), "c_new_file.go"): []byte(`package c; const C = "Ç"`)},
			`"abÇ"`, nil},
		// Overlay with a new file in an existing package, adding a new dependency to that package.
		{map[string][]byte{
			exported.File("golang.org/fake", "c/c.go"):                                               []byte(`package c;`),
			filepath.Join(filepath.Dir(exported.File("golang.org/fake", "c/c.go")), "c_new_file.go"): []byte(`package c; import "golang.org/fake/d"; const C = "c" + d.D`)},
			`"abcd"`, nil},
	} {
		exported.Config.Overlay = test.overlay
		exported.Config.Mode = packages.LoadAllSyntax
		initial, err := packages.Load(exported.Config, "golang.org/fake/a")
		if err != nil {
			t.Error(err)
			continue
		}

		// Check value of a.A.
		a := initial[0]
		aA := constant(a, "A")
		if aA == nil {
			t.Errorf("%d. a.A: got nil", i)
			continue
		}
		got := aA.Val().String()
		if got != test.want {
			t.Errorf("%d. a.A: got %s, want %s", i, got, test.want)
		}

		// Check errors.
		var errors []packages.Error
		packages.Visit(initial, nil, func(pkg *packages.Package) {
			errors = append(errors, pkg.Errors...)
		})
		if errs := errorMessages(errors); !reflect.DeepEqual(errs, test.wantErrs) {
			t.Errorf("%d. got errors %s, want %s", i, errs, test.wantErrs)
		}
	}
}

func TestOverlayDeps(t *testing.T) { testAllOrModulesParallel(t, testOverlayDeps) }
func testOverlayDeps(t *testing.T, exporter packagestest.Exporter) {
	exported := packagestest.Export(t, exporter, []packagestest.Module{{
		Name: "golang.org/fake",
		Files: map[string]interface{}{
			"c/c.go":      `package c; const C = "c"`,
			"c/c_test.go": `package c; import "testing"; func TestC(t *testing.T) {}`,
		},
	}})
	defer exported.Cleanup()

	exported.Config.Overlay = map[string][]byte{exported.File("golang.org/fake", "c/c.go"): []byte(`package c; import "net/http"; const C = http.MethodGet`)}
	exported.Config.Mode = packages.NeedName |
		packages.NeedFiles |
		packages.NeedCompiledGoFiles |
		packages.NeedImports |
		packages.NeedDeps |
		packages.NeedTypesSizes
	pkgs, err := packages.Load(exported.Config, fmt.Sprintf("file=%s", exported.File("golang.org/fake", "c/c.go")))
	if err != nil {
		t.Error(err)
	}

	// Find package golang.org/fake/c
	sort.Slice(pkgs, func(i, j int) bool { return pkgs[i].ID < pkgs[j].ID })
	if len(pkgs) != 2 {
		t.Fatalf("expected 2 packages, got %v", len(pkgs))
	}
	pkgc := pkgs[0]
	if pkgc.ID != "golang.org/fake/c" {
		t.Errorf("expected first package in sorted list to be \"golang.org/fake/c\", got %v", pkgc.ID)
	}

	// Make sure golang.org/fake/c imports net/http, as per the overlay.
	contains := func(imports map[string]*packages.Package, wantImport string) bool {
		for imp := range imports {
			if imp == wantImport {
				return true
			}
		}
		return false
	}
	if !contains(pkgc.Imports, "net/http") {
		t.Errorf("expected import of %s in package %s, got the following imports: %v",
			"net/http", pkgc.ID, pkgc.Imports)
	}

}

func TestNewPackagesInOverlay(t *testing.T) { testAllOrModulesParallel(t, testNewPackagesInOverlay) }
func testNewPackagesInOverlay(t *testing.T, exporter packagestest.Exporter) {
	exported := packagestest.Export(t, exporter, []packagestest.Module{
		{
			Name: "golang.org/fake",
			Files: map[string]interface{}{
				"a/a.go": `package a; import "golang.org/fake/b"; const A = "a" + b.B`,
				"b/b.go": `package b; import "golang.org/fake/c"; const B = "b" + c.C`,
				"c/c.go": `package c; const C = "c"`,
				"d/d.go": `package d; const D = "d"`,
			},
		},
		{
			Name: "example.com/extramodule",
			Files: map[string]interface{}{
				"pkg/x.go": "package pkg\n",
			},
		},
	})
	defer exported.Cleanup()

	dir := filepath.Dir(filepath.Dir(exported.File("golang.org/fake", "a/a.go")))

	for _, test := range []struct {
		name    string
		overlay map[string][]byte
		want    string // expected value of e.E
	}{
		{"one_file",
			map[string][]byte{
				filepath.Join(dir, "e", "e.go"): []byte(`package e; import "golang.org/fake/a"; const E = "e" + a.A`)},
			`"eabc"`},
		{"multiple_files_same_package",
			map[string][]byte{
				filepath.Join(dir, "e", "e.go"):      []byte(`package e; import "golang.org/fake/a"; const E = "e" + a.A + underscore`),
				filepath.Join(dir, "e", "e_util.go"): []byte(`package e; const underscore = "_"`),
			},
			`"eabc_"`},
		{"multiple_files_two_packages",
			map[string][]byte{
				filepath.Join(dir, "e", "e.go"):      []byte(`package e; import "golang.org/fake/f"; const E = "e" + f.F + underscore`),
				filepath.Join(dir, "e", "e_util.go"): []byte(`package e; const underscore = "_"`),
				filepath.Join(dir, "f", "f.go"):      []byte(`package f; const F = "f"`),
			},
			`"ef_"`},
		{"multiple_files_three_packages",
			map[string][]byte{
				filepath.Join(dir, "e", "e.go"):      []byte(`package e; import "golang.org/fake/f"; const E = "e" + f.F + underscore`),
				filepath.Join(dir, "e", "e_util.go"): []byte(`package e; const underscore = "_"`),
				filepath.Join(dir, "f", "f.go"):      []byte(`package f; import "golang.org/fake/g"; const F = "f" + g.G`),
				filepath.Join(dir, "g", "g.go"):      []byte(`package g; const G = "g"`),
			},
			`"efg_"`},
		{"multiple_files_four_packages",
			map[string][]byte{
				filepath.Join(dir, "e", "e.go"):      []byte(`package e; import "golang.org/fake/f"; import "golang.org/fake/h"; const E = "e" + f.F + h.H + underscore`),
				filepath.Join(dir, "e", "e_util.go"): []byte(`package e; const underscore = "_"`),
				filepath.Join(dir, "f", "f.go"):      []byte(`package f; import "golang.org/fake/g"; const F = "f" + g.G`),
				filepath.Join(dir, "g", "g.go"):      []byte(`package g; const G = "g"`),
				filepath.Join(dir, "h", "h.go"):      []byte(`package h; const H = "h"`),
			},
			`"efgh_"`},
		{"multiple_files_four_packages_again",
			map[string][]byte{
				filepath.Join(dir, "e", "e.go"):      []byte(`package e; import "golang.org/fake/f"; const E = "e" + f.F + underscore`),
				filepath.Join(dir, "e", "e_util.go"): []byte(`package e; const underscore = "_"`),
				filepath.Join(dir, "f", "f.go"):      []byte(`package f; import "golang.org/fake/g"; const F = "f" + g.G`),
				filepath.Join(dir, "g", "g.go"):      []byte(`package g; import "golang.org/fake/h"; const G = "g" + h.H`),
				filepath.Join(dir, "h", "h.go"):      []byte(`package h; const H = "h"`),
			},
			`"efgh_"`},
		{"main_overlay",
			map[string][]byte{
				filepath.Join(dir, "e", "main.go"): []byte(`package main; import "golang.org/fake/a"; const E = "e" + a.A; func main(){}`)},
			`"eabc"`},
	} {
		t.Run(test.name, func(t *testing.T) {
			exported.Config.Overlay = test.overlay
			exported.Config.Mode = packages.LoadAllSyntax
			exported.Config.Logf = t.Logf

			// With an overlay, we don't know the expected import path,
			// so load with the absolute path of the directory.
			initial, err := packages.Load(exported.Config, filepath.Join(dir, "e"))
			if err != nil {
				t.Fatal(err)
			}

			// Check value of e.E.
			e := initial[0]
			eE := constant(e, "E")
			if eE == nil {
				t.Fatalf("e.E: was nil in %#v", e)
			}
			got := eE.Val().String()
			if got != test.want {
				t.Fatalf("e.E: got %s, want %s", got, test.want)
			}
		})
	}
}

// Test that we can create a package and its test package in an overlay.
func TestOverlayNewPackageAndTest(t *testing.T) {
	testAllOrModulesParallel(t, testOverlayNewPackageAndTest)
}
func testOverlayNewPackageAndTest(t *testing.T, exporter packagestest.Exporter) {
	exported := packagestest.Export(t, exporter, []packagestest.Module{
		{
			Name: "golang.org/fake",
			Files: map[string]interface{}{
				"foo.txt": "placeholder",
			},
		},
	})
	defer exported.Cleanup()

	dir := filepath.Dir(exported.File("golang.org/fake", "foo.txt"))
	exported.Config.Overlay = map[string][]byte{
		filepath.Join(dir, "a.go"):      []byte(`package a;`),
		filepath.Join(dir, "a_test.go"): []byte(`package a; import "testing";`),
	}
	initial, err := packages.Load(exported.Config, "file="+filepath.Join(dir, "a.go"), "file="+filepath.Join(dir, "a_test.go"))
	if err != nil {
		t.Fatal(err)
	}
	if len(initial) != 2 {
		t.Errorf("got %v packages, wanted %v", len(initial), 2)
	}
}

func TestAdHocOverlays(t *testing.T) {
	t.Parallel()
	testenv.NeedsTool(t, "go")

	// This test doesn't use packagestest because we are testing ad-hoc packages,
	// which are outside of $GOPATH and outside of a module.
	tmp, err := os.MkdirTemp("", "testAdHocOverlays")
	if err != nil {
		t.Fatal(err)
	}
	defer os.RemoveAll(tmp)

	filename := filepath.Join(tmp, "a.go")
	content := []byte(`package a
const A = 1
`)

	// Make sure that the user's value of GO111MODULE does not affect test results.
	for _, go111module := range []string{"off", "auto", "on"} {
		t.Run("GO111MODULE="+go111module, func(t *testing.T) {
			config := &packages.Config{
				Dir:  tmp,
				Env:  append(os.Environ(), "GOPACKAGESDRIVER=off", fmt.Sprintf("GO111MODULE=%s", go111module)),
				Mode: packages.LoadAllSyntax,
				Overlay: map[string][]byte{
					filename: content,
				},
				Logf: t.Logf,
			}
			initial, err := packages.Load(config, fmt.Sprintf("file=%s", filename))
			if err != nil {
				t.Fatal(err)
			}
			if len(initial) == 0 {
				t.Fatalf("no packages for %s", filename)
			}
			// Check value of a.A.
			a := initial[0]
			if a.Errors != nil {
				t.Fatalf("a: got errors %+v, want no error", err)
			}
			aA := constant(a, "A")
			if aA == nil {
				t.Errorf("a.A: got nil")
				return
			}
			got := aA.Val().String()
			if want := "1"; got != want {
				t.Errorf("a.A: got %s, want %s", got, want)
			}
		})
	}
}

// TestOverlayModFileChanges tests the behavior resulting from having files
// from multiple modules in overlays.
func TestOverlayModFileChanges(t *testing.T) {
	t.Parallel()
	testenv.NeedsTool(t, "go")

	// Create two unrelated modules in a temporary directory.
	tmp, err := os.MkdirTemp("", "tmp")
	if err != nil {
		t.Fatal(err)
	}
	defer os.RemoveAll(tmp)

	// mod1 has a dependency on golang.org/x/xerrors.
	mod1, err := os.MkdirTemp(tmp, "mod1")
	if err != nil {
		t.Fatal(err)
	}
	if err := os.WriteFile(filepath.Join(mod1, "go.mod"), []byte(`module mod1

	require (
		golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7
	)
	`), 0775); err != nil {
		t.Fatal(err)
	}

	// mod2 does not have any dependencies.
	mod2, err := os.MkdirTemp(tmp, "mod2")
	if err != nil {
		t.Fatal(err)
	}

	want := `module mod2

go 1.11
`
	if err := os.WriteFile(filepath.Join(mod2, "go.mod"), []byte(want), 0775); err != nil {
		t.Fatal(err)
	}

	// Run packages.Load on mod2, while passing the contents over mod1/main.go in the overlay.
	config := &packages.Config{
		Dir:  mod2,
		Env:  append(os.Environ(), "GOPACKAGESDRIVER=off"),
		Mode: packages.LoadImports,
		Overlay: map[string][]byte{
			filepath.Join(mod1, "main.go"): []byte(`package main
import "golang.org/x/xerrors"
func main() {
	_ = errors.New("")
}
`),
			filepath.Join(mod2, "main.go"): []byte(`package main
func main() {}
`),
		},
	}
	if _, err := packages.Load(config, fmt.Sprintf("file=%s", filepath.Join(mod2, "main.go"))); err != nil {
		t.Fatal(err)
	}

	// Check that mod2/go.mod has not been modified.
	got, err := os.ReadFile(filepath.Join(mod2, "go.mod"))
	if err != nil {
		t.Fatal(err)
	}
	if string(got) != want {
		t.Errorf("expected %s, got %s", want, string(got))
	}
}

func TestOverlayGOPATHVendoring(t *testing.T) {
	t.Parallel()

	exported := packagestest.Export(t, packagestest.GOPATH, []packagestest.Module{{
		Name: "golang.org/fake",
		Files: map[string]interface{}{
			"vendor/vendor.com/foo/foo.go": `package foo; const X = "hi"`,
			"user/user.go":                 `package user`,
		},
	}})
	defer exported.Cleanup()

	exported.Config.Mode = packages.LoadAllSyntax
	exported.Config.Logf = t.Logf
	exported.Config.Overlay = map[string][]byte{
		exported.File("golang.org/fake", "user/user.go"): []byte(`package user; import "vendor.com/foo"; var x = foo.X`),
	}
	initial, err := packages.Load(exported.Config, "golang.org/fake/user")
	if err != nil {
		t.Fatal(err)
	}
	user := initial[0]
	if len(user.Imports) != 1 {
		t.Fatal("no imports for user")
	}
	if user.Imports["vendor.com/foo"].Name != "foo" {
		t.Errorf("failed to load vendored package foo, imports: %#v", user.Imports["vendor.com/foo"])
	}
}

func TestContainsOverlay(t *testing.T) { testAllOrModulesParallel(t, testContainsOverlay) }
func testContainsOverlay(t *testing.T, exporter packagestest.Exporter) {
	exported := packagestest.Export(t, exporter, []packagestest.Module{{
		Name: "golang.org/fake",
		Files: map[string]interface{}{
			"a/a.go": `package a; import "golang.org/fake/b"`,
			"b/b.go": `package b; import "golang.org/fake/c"`,
			"c/c.go": `package c`,
		}}})
	defer exported.Cleanup()
	bOverlayFile := filepath.Join(filepath.Dir(exported.File("golang.org/fake", "b/b.go")), "b_overlay.go")
	exported.Config.Mode = packages.LoadImports
	exported.Config.Overlay = map[string][]byte{bOverlayFile: []byte(`package b;`)}
	initial, err := packages.Load(exported.Config, "file="+bOverlayFile)
	if err != nil {
		t.Fatal(err)
	}

	graph, _ := importGraph(initial)
	wantGraph := `
* golang.org/fake/b
  golang.org/fake/c
  golang.org/fake/b -> golang.org/fake/c
`[1:]
	if graph != wantGraph {
		t.Errorf("wrong import graph: got <<%s>>, want <<%s>>", graph, wantGraph)
	}
}

func TestContainsOverlayXTest(t *testing.T) { testAllOrModulesParallel(t, testContainsOverlayXTest) }
func testContainsOverlayXTest(t *testing.T, exporter packagestest.Exporter) {
	exported := packagestest.Export(t, exporter, []packagestest.Module{{
		Name: "golang.org/fake",
		Files: map[string]interface{}{
			"a/a.go": `package a; import "golang.org/fake/b"`,
			"b/b.go": `package b; import "golang.org/fake/c"`,
			"c/c.go": `package c`,
		}}})
	defer exported.Cleanup()

	bOverlayXTestFile := filepath.Join(filepath.Dir(exported.File("golang.org/fake", "b/b.go")), "b_overlay_x_test.go")
	exported.Config.Mode = packages.NeedName | packages.NeedFiles | packages.NeedImports
	exported.Config.Overlay = map[string][]byte{bOverlayXTestFile: []byte(`package b_test; import "golang.org/fake/b"`)}
	initial, err := packages.Load(exported.Config, "file="+bOverlayXTestFile)
	if err != nil {
		t.Fatal(err)
	}

	graph, _ := importGraph(initial)
	wantGraph := `
  golang.org/fake/b
* golang.org/fake/b_test [golang.org/fake/b.test]
  golang.org/fake/c
  golang.org/fake/b -> golang.org/fake/c
  golang.org/fake/b_test [golang.org/fake/b.test] -> golang.org/fake/b
`[1:]
	if graph != wantGraph {
		t.Errorf("wrong import graph: got <<%s>>, want <<%s>>", graph, wantGraph)
	}
}

func TestInvalidFilesBeforeOverlay(t *testing.T) {
	testAllOrModulesParallel(t, testInvalidFilesBeforeOverlay)
}

func testInvalidFilesBeforeOverlay(t *testing.T, exporter packagestest.Exporter) {
	exported := packagestest.Export(t, exporter, []packagestest.Module{
		{
			Name: "golang.org/fake",
			Files: map[string]interface{}{
				"d/d.go":  ``,
				"main.go": ``,
			},
		},
	})
	defer exported.Cleanup()

	dir := filepath.Dir(filepath.Dir(exported.File("golang.org/fake", "d/d.go")))

	exported.Config.Mode = everythingMode
	exported.Config.Tests = true

	// First, check that all packages returned have files associated with them.
	// Tests the work-around for golang/go#39986.
	t.Run("no overlay", func(t *testing.T) {
		initial, err := packages.Load(exported.Config, fmt.Sprintf("%s/...", dir))
		if err != nil {
			t.Fatal(err)
		}
		for _, pkg := range initial {
			if len(pkg.CompiledGoFiles) == 0 {
				t.Fatalf("expected at least 1 CompiledGoFile for %s, got none", pkg.PkgPath)
			}
		}
	})

}

// Tests golang/go#35973, fixed in Go 1.14.
func TestInvalidFilesBeforeOverlayContains(t *testing.T) {
	testAllOrModulesParallel(t, testInvalidFilesBeforeOverlayContains)
}
func testInvalidFilesBeforeOverlayContains(t *testing.T, exporter packagestest.Exporter) {
	exported := packagestest.Export(t, exporter, []packagestest.Module{
		{
			Name: "golang.org/fake",
			Files: map[string]interface{}{
				"d/d.go":      `package d; import "net/http"; const Get = http.MethodGet; const Hello = "hello";`,
				"d/util.go":   ``,
				"d/d_test.go": ``,
				"main.go":     ``,
			},
		},
	})
	defer exported.Cleanup()

	dir := filepath.Dir(filepath.Dir(exported.File("golang.org/fake", "d/d.go")))

	// Additional tests for test variants.
	for i, tt := range []struct {
		name    string
		overlay map[string][]byte
		want    string // expected value of d.D
		wantID  string // expected value for the package ID
	}{
		// Overlay with a test variant.
		{
			"test_variant",
			map[string][]byte{
				filepath.Join(dir, "d", "d_test.go"): []byte(`package d; import "testing"; const D = Get + "_test"; func TestD(t *testing.T) {};`),
			},
			`"GET_test"`, "golang.org/fake/d [golang.org/fake/d.test]",
		},
		// Overlay in package.
		{
			"second_file",
			map[string][]byte{
				filepath.Join(dir, "d", "util.go"): []byte(`package d; const D = Get + "_util";`),
			},
			`"GET_util"`, "golang.org/fake/d",
		},
		// Overlay on the main file.
		{
			"main",
			map[string][]byte{
				filepath.Join(dir, "main.go"): []byte(`package main; import "golang.org/fake/d"; const D = d.Get + "_main"; func main() {};`),
			},
			`"GET_main"`, "golang.org/fake",
		},
		{
			"xtest",
			map[string][]byte{
				filepath.Join(dir, "d", "d_test.go"): []byte(`package d_test; import "golang.org/fake/d"; import "testing"; const D = d.Get + "_xtest"; func TestD(t *testing.T) {};`),
			},
			`"GET_xtest"`, "golang.org/fake/d_test [golang.org/fake/d.test]",
		},
	} {
		t.Run(tt.name, func(t *testing.T) {
			exported.Config.Overlay = tt.overlay
			exported.Config.Mode = everythingMode
			exported.Config.Tests = true

			for f := range tt.overlay {
				initial, err := packages.Load(exported.Config, fmt.Sprintf("file=%s", f))
				if err != nil {
					t.Fatal(err)
				}
				if len(initial) != 1 &&
					(len(initial) != 2 || !isTestVariant(initial[0].ID, initial[1].ID)) {
					t.Fatalf("expected 1 package (perhaps with test variant), got %v", len(initial))
				}
				pkg := initial[0]
				if pkg.ID != tt.wantID {
					t.Fatalf("expected package ID %q, got %q", tt.wantID, pkg.ID)
				}
				var containsFile bool
				for _, goFile := range pkg.CompiledGoFiles {
					if f == goFile {
						containsFile = true
						break
					}
				}
				if !containsFile {
					t.Fatalf("expected %s in CompiledGoFiles, got %v", f, pkg.CompiledGoFiles)
				}
				// Check value of d.D.
				D := constant(pkg, "D")
				if D == nil {
					t.Fatalf("%d. D: got nil", i)
				}
				got := D.Val().String()
				if got != tt.want {
					t.Fatalf("%d. D: got %s, want %s", i, got, tt.want)
				}
			}
		})
	}
}

func isTestVariant(libID, testID string) bool {
	variantID := fmt.Sprintf("%[1]s [%[1]s.test]", libID)
	return variantID == testID
}

func TestInvalidXTestInGOPATH(t *testing.T) {
	testAllOrModulesParallel(t, testInvalidXTestInGOPATH)
}
func testInvalidXTestInGOPATH(t *testing.T, exporter packagestest.Exporter) {
	t.Skip("Not fixed yet. See golang.org/issue/40825.")

	exported := packagestest.Export(t, exporter, []packagestest.Module{
		{
			Name: "golang.org/fake",
			Files: map[string]interface{}{
				"x/x.go":      `package x`,
				"x/x_test.go": ``,
			},
		},
	})
	defer exported.Cleanup()

	dir := filepath.Dir(filepath.Dir(exported.File("golang.org/fake", "x/x.go")))

	exported.Config.Mode = everythingMode
	exported.Config.Tests = true

	initial, err := packages.Load(exported.Config, fmt.Sprintf("%s/...", dir))
	if err != nil {
		t.Fatal(err)
	}
	pkg := initial[0]
	if len(pkg.CompiledGoFiles) != 2 {
		t.Fatalf("expected at least 2 CompiledGoFiles for %s, got %v", pkg.PkgPath, len(pkg.CompiledGoFiles))
	}
}

// Reproduces golang/go#40685.
func TestAddImportInOverlay(t *testing.T) {
	testAllOrModulesParallel(t, testAddImportInOverlay)
}
func testAddImportInOverlay(t *testing.T, exporter packagestest.Exporter) {
	exported := packagestest.Export(t, exporter, []packagestest.Module{
		{
			Name: "golang.org/fake",
			Files: map[string]interface{}{
				"a/a.go": `package a

import (
	"fmt"
)

func _() {
	fmt.Println("")
	os.Stat("")
}`,
				"a/a_test.go": `package a

import (
	"os"
	"testing"
)

func TestA(t *testing.T) {
	os.Stat("")
}`,
			},
		},
	})
	defer exported.Cleanup()

	exported.Config.Mode = everythingMode
	exported.Config.Tests = true

	dir := filepath.Dir(exported.File("golang.org/fake", "a/a.go"))
	exported.Config.Overlay = map[string][]byte{
		filepath.Join(dir, "a.go"): []byte(`package a

import (
	"fmt"
	"os"
)

func _() {
	fmt.Println("")
	os.Stat("")
}
`),
	}
	initial, err := packages.Load(exported.Config, "golang.org/fake/a")
	if err != nil {
		t.Fatal(err)
	}
	pkg := initial[0]
	var foundOs bool
	for _, imp := range pkg.Imports {
		if imp.PkgPath == "os" {
			foundOs = true
			break
		}
	}
	if !foundOs {
		t.Fatalf(`expected import "os", found none: %v`, pkg.Imports)
	}
}

// Tests that overlays are applied for different kinds of load patterns.
func TestLoadDifferentPatterns(t *testing.T) {
	testAllOrModulesParallel(t, testLoadDifferentPatterns)
}
func testLoadDifferentPatterns(t *testing.T, exporter packagestest.Exporter) {
	exported := packagestest.Export(t, exporter, []packagestest.Module{
		{
			Name: "golang.org/fake",
			Files: map[string]interface{}{
				"foo.txt": "placeholder",
				"b/b.go": `package b
import "golang.org/fake/a"
func _() {
	a.Hi()
}
`,
			},
		},
	})
	defer exported.Cleanup()

	exported.Config.Mode = everythingMode
	exported.Config.Tests = true

	dir := filepath.Dir(exported.File("golang.org/fake", "foo.txt"))
	exported.Config.Overlay = map[string][]byte{
		filepath.Join(dir, "a", "a.go"): []byte(`package a
import "fmt"
func Hi() {
	fmt.Println("")
}
`),
	}
	for _, tc := range []struct {
		pattern string
	}{
		{"golang.org/fake/a"},
		{"golang.org/fake/..."},
		{fmt.Sprintf("file=%s", filepath.Join(dir, "a", "a.go"))},
	} {
		t.Run(tc.pattern, func(t *testing.T) {
			initial, err := packages.Load(exported.Config, tc.pattern)
			if err != nil {
				t.Fatal(err)
			}
			var match *packages.Package
			for _, pkg := range initial {
				if pkg.PkgPath == "golang.org/fake/a" {
					match = pkg
					break
				}
			}
			if match == nil {
				t.Fatalf(`expected package path "golang.org/fake/a", got none`)
			}
			if match.PkgPath != "golang.org/fake/a" {
				t.Fatalf(`expected package path "golang.org/fake/a", got %q`, match.PkgPath)
			}
			if _, ok := match.Imports["fmt"]; !ok {
				t.Fatalf(`expected import "fmt", got none`)
			}
		})
	}

	// Now, load "golang.org/fake/b" and confirm that "golang.org/fake/a" is
	// not returned as a root.
	initial, err := packages.Load(exported.Config, "golang.org/fake/b")
	if err != nil {
		t.Fatal(err)
	}
	if len(initial) > 1 {
		t.Fatalf("expected 1 package, got %v", initial)
	}
	pkg := initial[0]
	if pkg.PkgPath != "golang.org/fake/b" {
		t.Fatalf(`expected package path "golang.org/fake/b", got %q`, pkg.PkgPath)
	}
	if _, ok := pkg.Imports["golang.org/fake/a"]; !ok {
		t.Fatalf(`expected import "golang.org/fake/a", got none`)
	}
}

// Tests that overlays are applied for a replaced module.
// This does not use go/packagestest because it needs to write a replace
// directive with an absolute path in one of the module's go.mod files.
func TestOverlaysInReplace(t *testing.T) {
	testenv.NeedsGoPackages(t)
	t.Parallel()

	// Create module b.com in a temporary directory. Do not add any Go files
	// on disk.
	tmpPkgs, err := os.MkdirTemp("", "modules")
	if err != nil {
		t.Fatal(err)
	}
	defer os.RemoveAll(tmpPkgs)

	dirB := filepath.Join(tmpPkgs, "b")
	if err := os.Mkdir(dirB, 0775); err != nil {
		t.Fatal(err)
	}
	if err := os.WriteFile(filepath.Join(dirB, "go.mod"), []byte(fmt.Sprintf("module %s.com", dirB)), 0775); err != nil {
		t.Fatal(err)
	}
	if err := os.MkdirAll(filepath.Join(dirB, "inner"), 0775); err != nil {
		t.Fatal(err)
	}

	// Create a separate module that requires and replaces b.com.
	tmpWorkspace, err := os.MkdirTemp("", "workspace")
	if err != nil {
		t.Fatal(err)
	}
	defer os.RemoveAll(tmpWorkspace)
	goModContent := fmt.Sprintf(`module workspace.com

require (
	b.com v0.0.0-00010101000000-000000000000
)

replace (
	b.com => %s
)
`, dirB)
	if err := os.WriteFile(filepath.Join(tmpWorkspace, "go.mod"), []byte(goModContent), 0775); err != nil {
		t.Fatal(err)
	}

	// Add Go files for b.com/inner in an overlay and try loading it from the
	// workspace.com module.
	config := &packages.Config{
		Dir:  tmpWorkspace,
		Mode: packages.LoadAllSyntax,
		Logf: t.Logf,
		Overlay: map[string][]byte{
			filepath.Join(dirB, "inner", "b.go"): []byte(`package inner; import "fmt"; func _() { fmt.Println("");`),
		},
	}
	initial, err := packages.Load(config, "b.com/...")
	if err != nil {
		t.Error(err)
	}
	if len(initial) != 1 {
		t.Fatalf(`expected 1 package, got %v`, len(initial))
	}
	pkg := initial[0]
	if pkg.PkgPath != "b.com/inner" {
		t.Fatalf(`expected package path "b.com/inner", got %q`, pkg.PkgPath)
	}
	if _, ok := pkg.Imports["fmt"]; !ok {
		t.Fatalf(`expected import "fmt", got none`)
	}
}
