136 lines
4.1 KiB
Go
136 lines
4.1 KiB
Go
// Copyright 2018 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 expect_test
|
||
|
||
import (
|
||
"bytes"
|
||
"go/token"
|
||
"io/ioutil"
|
||
"testing"
|
||
|
||
"golang.org/x/tools/go/expect"
|
||
)
|
||
|
||
func TestMarker(t *testing.T) {
|
||
const filename = "testdata/test.go"
|
||
content, err := ioutil.ReadFile(filename)
|
||
if err != nil {
|
||
t.Fatal(err)
|
||
}
|
||
|
||
const expectNotes = 11
|
||
expectMarkers := map[string]string{
|
||
"αSimpleMarker": "α",
|
||
"OffsetMarker": "β",
|
||
"RegexMarker": "γ",
|
||
"εMultiple": "ε",
|
||
"ζMarkers": "ζ",
|
||
"ηBlockMarker": "η",
|
||
"Declared": "η",
|
||
"Comment": "ι",
|
||
"NonIdentifier": "+",
|
||
}
|
||
expectChecks := map[string][]interface{}{
|
||
"αSimpleMarker": nil,
|
||
"StringAndInt": []interface{}{"Number %d", int64(12)},
|
||
"Bool": []interface{}{true},
|
||
}
|
||
|
||
readFile := func(string) ([]byte, error) { return content, nil }
|
||
markers := make(map[string]token.Pos)
|
||
for name, tok := range expectMarkers {
|
||
offset := bytes.Index(content, []byte(tok))
|
||
markers[name] = token.Pos(offset + 1)
|
||
end := bytes.Index(content[offset+1:], []byte(tok))
|
||
if end > 0 {
|
||
markers[name+"@"] = token.Pos(offset + end + 2)
|
||
}
|
||
}
|
||
|
||
fset := token.NewFileSet()
|
||
notes, err := expect.Parse(fset, filename, nil)
|
||
if err != nil {
|
||
t.Fatalf("Failed to extract notes: %v", err)
|
||
}
|
||
if len(notes) != expectNotes {
|
||
t.Errorf("Expected %v notes, got %v", expectNotes, len(notes))
|
||
}
|
||
for _, n := range notes {
|
||
switch {
|
||
case n.Args == nil:
|
||
// A //@foo note associates the name foo with the position of the
|
||
// first match of "foo" on the current line.
|
||
checkMarker(t, fset, readFile, markers, n.Pos, n.Name, n.Name)
|
||
case n.Name == "mark":
|
||
// A //@mark(name, "pattern") note associates the specified name
|
||
// with the position on the first match of pattern on the current line.
|
||
if len(n.Args) != 2 {
|
||
t.Errorf("%v: expected 2 args to mark, got %v", fset.Position(n.Pos), len(n.Args))
|
||
continue
|
||
}
|
||
ident, ok := n.Args[0].(expect.Identifier)
|
||
if !ok {
|
||
t.Errorf("%v: identifier, got %T", fset.Position(n.Pos), n.Args[0])
|
||
continue
|
||
}
|
||
checkMarker(t, fset, readFile, markers, n.Pos, string(ident), n.Args[1])
|
||
|
||
case n.Name == "check":
|
||
// A //@check(args, ...) note specifies some hypothetical action to
|
||
// be taken by the test driver and its expected outcome.
|
||
// In this test, the action is to compare the arguments
|
||
// against expectChecks.
|
||
if len(n.Args) < 1 {
|
||
t.Errorf("%v: expected 1 args to check, got %v", fset.Position(n.Pos), len(n.Args))
|
||
continue
|
||
}
|
||
ident, ok := n.Args[0].(expect.Identifier)
|
||
if !ok {
|
||
t.Errorf("%v: identifier, got %T", fset.Position(n.Pos), n.Args[0])
|
||
continue
|
||
}
|
||
args, ok := expectChecks[string(ident)]
|
||
if !ok {
|
||
t.Errorf("%v: unexpected check %v", fset.Position(n.Pos), ident)
|
||
continue
|
||
}
|
||
if len(n.Args) != len(args)+1 {
|
||
t.Errorf("%v: expected %v args to check, got %v", fset.Position(n.Pos), len(args)+1, len(n.Args))
|
||
continue
|
||
}
|
||
for i, got := range n.Args[1:] {
|
||
if args[i] != got {
|
||
t.Errorf("%v: arg %d expected %v, got %v", fset.Position(n.Pos), i, args[i], got)
|
||
}
|
||
}
|
||
default:
|
||
t.Errorf("Unexpected note %v at %v", n.Name, fset.Position(n.Pos))
|
||
}
|
||
}
|
||
}
|
||
|
||
func checkMarker(t *testing.T, fset *token.FileSet, readFile expect.ReadFile, markers map[string]token.Pos, pos token.Pos, name string, pattern interface{}) {
|
||
start, end, err := expect.MatchBefore(fset, readFile, pos, pattern)
|
||
if err != nil {
|
||
t.Errorf("%v: MatchBefore failed: %v", fset.Position(pos), err)
|
||
return
|
||
}
|
||
if start == token.NoPos {
|
||
t.Errorf("%v: Pattern %v did not match", fset.Position(pos), pattern)
|
||
return
|
||
}
|
||
expectStart, ok := markers[name]
|
||
if !ok {
|
||
t.Errorf("%v: unexpected marker %v", fset.Position(pos), name)
|
||
return
|
||
}
|
||
if start != expectStart {
|
||
t.Errorf("%v: Expected %v got %v", fset.Position(pos), fset.Position(expectStart), fset.Position(start))
|
||
}
|
||
if expectEnd, ok := markers[name+"@"]; ok && end != expectEnd {
|
||
t.Errorf("%v: Expected end %v got %v", fset.Position(pos), fset.Position(expectEnd), fset.Position(end))
|
||
}
|
||
}
|