1package analysistest_test 2 3import ( 4 "fmt" 5 "log" 6 "os" 7 "reflect" 8 "strings" 9 "testing" 10 11 "golang.org/x/tools/go/analysis/analysistest" 12 "golang.org/x/tools/go/analysis/passes/findcall" 13 "golang.org/x/tools/internal/testenv" 14) 15 16func init() { 17 // This test currently requires GOPATH mode. 18 // Explicitly disabling module mode should suffice, but 19 // we'll also turn off GOPROXY just for good measure. 20 if err := os.Setenv("GO111MODULE", "off"); err != nil { 21 log.Fatal(err) 22 } 23 if err := os.Setenv("GOPROXY", "off"); err != nil { 24 log.Fatal(err) 25 } 26} 27 28// TestTheTest tests the analysistest testing infrastructure. 29func TestTheTest(t *testing.T) { 30 testenv.NeedsTool(t, "go") 31 32 // We'll simulate a partly failing test of the findcall analysis, 33 // which (by default) reports calls to functions named 'println'. 34 findcall.Analyzer.Flags.Set("name", "println") 35 36 filemap := map[string]string{"a/b.go": `package main // want package:"found" 37 38func main() { 39 // The expectation is ill-formed: 40 print() // want: "diagnostic" 41 print() // want foo"fact" 42 print() // want foo: 43 print() // want "\xZZ scan error" 44 45 // A diagnostic is reported at this line, but the expectation doesn't match: 46 println("hello, world") // want "wrong expectation text" 47 48 // An unexpected diagnostic is reported at this line: 49 println() // trigger an unexpected diagnostic 50 51 // No diagnostic is reported at this line: 52 print() // want "unsatisfied expectation" 53 54 // OK 55 println("hello, world") // want "call of println" 56 57 // OK (multiple expectations on same line) 58 println(); println() // want "call of println(...)" "call of println(...)" 59} 60 61// OK (facts and diagnostics on same line) 62func println(...interface{}) { println() } // want println:"found" "call of println(...)" 63 64`} 65 dir, cleanup, err := analysistest.WriteFiles(filemap) 66 if err != nil { 67 t.Fatal(err) 68 } 69 defer cleanup() 70 71 var got []string 72 t2 := errorfunc(func(s string) { got = append(got, s) }) // a fake *testing.T 73 analysistest.Run(t2, dir, findcall.Analyzer, "a") 74 75 want := []string{ 76 `a/b.go:5: in 'want' comment: unexpected ":"`, 77 `a/b.go:6: in 'want' comment: got String after foo, want ':'`, 78 `a/b.go:7: in 'want' comment: got EOF, want regular expression`, 79 `a/b.go:8: in 'want' comment: invalid char escape`, 80 `a/b.go:11:9: diagnostic "call of println(...)" does not match pattern "wrong expectation text"`, 81 `a/b.go:14:9: unexpected diagnostic: call of println(...)`, 82 `a/b.go:11: no diagnostic was reported matching "wrong expectation text"`, 83 `a/b.go:17: no diagnostic was reported matching "unsatisfied expectation"`, 84 } 85 // Go 1.13's scanner error messages uses the word invalid where Go 1.12 used illegal. Convert them 86 // to keep tests compatible with both. 87 // TODO(matloob): Remove this once Go 1.13 is released. 88 for i := range got { 89 got[i] = strings.Replace(got[i], "illegal", "invalid", -1) 90 } // 91 if !reflect.DeepEqual(got, want) { 92 t.Errorf("got:\n%s\nwant:\n%s", 93 strings.Join(got, "\n"), 94 strings.Join(want, "\n")) 95 } 96} 97 98type errorfunc func(string) 99 100func (f errorfunc) Errorf(format string, args ...interface{}) { 101 f(fmt.Sprintf(format, args...)) 102} 103