// Copyright 2022 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 checker_test

import (
	"flag"
	"io/ioutil"
	"os"
	"os/exec"
	"path"
	"regexp"
	"runtime"
	"testing"

	"golang.org/x/tools/go/analysis"
	"golang.org/x/tools/go/analysis/analysistest"
	"golang.org/x/tools/go/analysis/internal/checker"
	"golang.org/x/tools/internal/testenv"
)

func main() {
	checker.Fix = true
	patterns := flag.Args()

	code := checker.Run(patterns, []*analysis.Analyzer{analyzer, other})
	os.Exit(code)
}

// TestFixes ensures that checker.Run applies fixes correctly.
// This test fork/execs the main function above.
func TestFixes(t *testing.T) {
	oses := map[string]bool{"darwin": true, "linux": true}
	if !oses[runtime.GOOS] {
		t.Skipf("skipping fork/exec test on this platform")
	}

	if os.Getenv("TESTFIXES_CHILD") == "1" {
		// child process

		// replace [progname -test.run=TestFixes -- ...]
		//      by [progname ...]
		os.Args = os.Args[2:]
		os.Args[0] = "vet"
		main()
		panic("unreachable")
	}

	testenv.NeedsTool(t, "go")

	files := map[string]string{
		"rename/foo.go": `package rename

func Foo() {
	bar := 12
	_ = bar
}

// the end
`,
		"rename/intestfile_test.go": `package rename

func InTestFile() {
	bar := 13
	_ = bar
}

// the end
`,
		"rename/foo_test.go": `package rename_test

func Foo() {
	bar := 14
	_ = bar
}

// the end
`,
		"duplicate/dup.go": `package duplicate

func Foo() {
	bar := 14
	_ = bar
}

// the end
`,
	}
	fixed := map[string]string{
		"rename/foo.go": `package rename

func Foo() {
	baz := 12
	_ = baz
}

// the end
`,
		"rename/intestfile_test.go": `package rename

func InTestFile() {
	baz := 13
	_ = baz
}

// the end
`,
		"rename/foo_test.go": `package rename_test

func Foo() {
	baz := 14
	_ = baz
}

// the end
`,
		"duplicate/dup.go": `package duplicate

func Foo() {
	baz := 14
	_ = baz
}

// the end
`,
	}
	dir, cleanup, err := analysistest.WriteFiles(files)
	if err != nil {
		t.Fatalf("Creating test files failed with %s", err)
	}
	defer cleanup()

	args := []string{"-test.run=TestFixes", "--", "rename", "duplicate"}
	cmd := exec.Command(os.Args[0], args...)
	cmd.Env = append(os.Environ(), "TESTFIXES_CHILD=1", "GOPATH="+dir, "GO111MODULE=off", "GOPROXY=off")

	out, err := cmd.CombinedOutput()
	if len(out) > 0 {
		t.Logf("%s: out=<<%s>>", args, out)
	}
	var exitcode int
	if err, ok := err.(*exec.ExitError); ok {
		exitcode = err.ExitCode() // requires go1.12
	}

	const diagnosticsExitCode = 3
	if exitcode != diagnosticsExitCode {
		t.Errorf("%s: exited %d, want %d", args, exitcode, diagnosticsExitCode)
	}

	for name, want := range fixed {
		path := path.Join(dir, "src", name)
		contents, err := ioutil.ReadFile(path)
		if err != nil {
			t.Errorf("error reading %s: %v", path, err)
		}
		if got := string(contents); got != want {
			t.Errorf("contents of %s file did not match expectations. got=%s, want=%s", path, got, want)
		}
	}
}

// TestConflict ensures that checker.Run detects conflicts correctly.
// This test fork/execs the main function above.
func TestConflict(t *testing.T) {
	oses := map[string]bool{"darwin": true, "linux": true}
	if !oses[runtime.GOOS] {
		t.Skipf("skipping fork/exec test on this platform")
	}

	if os.Getenv("TESTCONFLICT_CHILD") == "1" {
		// child process

		// replace [progname -test.run=TestConflict -- ...]
		//      by [progname ...]
		os.Args = os.Args[2:]
		os.Args[0] = "vet"
		main()
		panic("unreachable")
	}

	testenv.NeedsTool(t, "go")

	files := map[string]string{
		"conflict/foo.go": `package conflict

func Foo() {
	bar := 12
	_ = bar
}

// the end
`,
	}
	dir, cleanup, err := analysistest.WriteFiles(files)
	if err != nil {
		t.Fatalf("Creating test files failed with %s", err)
	}
	defer cleanup()

	args := []string{"-test.run=TestConflict", "--", "conflict"}
	cmd := exec.Command(os.Args[0], args...)
	cmd.Env = append(os.Environ(), "TESTCONFLICT_CHILD=1", "GOPATH="+dir, "GO111MODULE=off", "GOPROXY=off")

	out, err := cmd.CombinedOutput()
	var exitcode int
	if err, ok := err.(*exec.ExitError); ok {
		exitcode = err.ExitCode() // requires go1.12
	}
	const errExitCode = 1
	if exitcode != errExitCode {
		t.Errorf("%s: exited %d, want %d", args, exitcode, errExitCode)
	}

	pattern := `conflicting edits from rename and rename on /.*/conflict/foo.go`
	matched, err := regexp.Match(pattern, out)
	if err != nil {
		t.Errorf("error matching pattern %s: %v", pattern, err)
	} else if !matched {
		t.Errorf("%s: output was=<<%s>>. Expected it to match <<%s>>", args, out, pattern)
	}

	// No files updated
	for name, want := range files {
		path := path.Join(dir, "src", name)
		contents, err := ioutil.ReadFile(path)
		if err != nil {
			t.Errorf("error reading %s: %v", path, err)
		}
		if got := string(contents); got != want {
			t.Errorf("contents of %s file updated. got=%s, want=%s", path, got, want)
		}
	}
}

// TestOther ensures that checker.Run reports conflicts from
// distinct actions correctly.
// This test fork/execs the main function above.
func TestOther(t *testing.T) {
	oses := map[string]bool{"darwin": true, "linux": true}
	if !oses[runtime.GOOS] {
		t.Skipf("skipping fork/exec test on this platform")
	}

	if os.Getenv("TESTOTHER_CHILD") == "1" {
		// child process

		// replace [progname -test.run=TestOther -- ...]
		//      by [progname ...]
		os.Args = os.Args[2:]
		os.Args[0] = "vet"
		main()
		panic("unreachable")
	}

	testenv.NeedsTool(t, "go")

	files := map[string]string{
		"other/foo.go": `package other

func Foo() {
	bar := 12
	_ = bar
}

// the end
`,
	}
	dir, cleanup, err := analysistest.WriteFiles(files)
	if err != nil {
		t.Fatalf("Creating test files failed with %s", err)
	}
	defer cleanup()

	args := []string{"-test.run=TestOther", "--", "other"}
	cmd := exec.Command(os.Args[0], args...)
	cmd.Env = append(os.Environ(), "TESTOTHER_CHILD=1", "GOPATH="+dir, "GO111MODULE=off", "GOPROXY=off")

	out, err := cmd.CombinedOutput()
	var exitcode int
	if err, ok := err.(*exec.ExitError); ok {
		exitcode = err.ExitCode() // requires go1.12
	}
	const errExitCode = 1
	if exitcode != errExitCode {
		t.Errorf("%s: exited %d, want %d", args, exitcode, errExitCode)
	}

	pattern := `conflicting edits from other and rename on /.*/other/foo.go`
	matched, err := regexp.Match(pattern, out)
	if err != nil {
		t.Errorf("error matching pattern %s: %v", pattern, err)
	} else if !matched {
		t.Errorf("%s: output was=<<%s>>. Expected it to match <<%s>>", args, out, pattern)
	}

	// No files updated
	for name, want := range files {
		path := path.Join(dir, "src", name)
		contents, err := ioutil.ReadFile(path)
		if err != nil {
			t.Errorf("error reading %s: %v", path, err)
		}
		if got := string(contents); got != want {
			t.Errorf("contents of %s file updated. got=%s, want=%s", path, got, want)
		}
	}
}
