Retro68/gcc/libgo/go/testing/example.go

125 lines
2.5 KiB
Go
Raw Normal View History

2012-03-27 23:13:14 +00:00
// Copyright 2009 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 testing
import (
"bytes"
"fmt"
"io"
"os"
"sort"
2012-03-27 23:13:14 +00:00
"strings"
"time"
)
type InternalExample struct {
Name string
F func()
Output string
Unordered bool
2012-03-27 23:13:14 +00:00
}
// An internal function but exported because it is cross-package; part of the implementation
// of the "go test" command.
2012-03-27 23:13:14 +00:00
func RunExamples(matchString func(pat, str string) (bool, error), examples []InternalExample) (ok bool) {
_, ok = runExamples(matchString, examples)
return ok
}
func runExamples(matchString func(pat, str string) (bool, error), examples []InternalExample) (ran, ok bool) {
2012-03-27 23:13:14 +00:00
ok = true
var eg InternalExample
for _, eg = range examples {
matched, err := matchString(*match, eg.Name)
if err != nil {
fmt.Fprintf(os.Stderr, "testing: invalid regexp for -test.run: %s\n", err)
os.Exit(1)
}
if !matched {
continue
}
ran = true
2014-09-21 17:33:12 +00:00
if !runExample(eg) {
ok = false
2012-03-27 23:13:14 +00:00
}
2014-09-21 17:33:12 +00:00
}
return ran, ok
}
func sortLines(output string) string {
lines := strings.Split(output, "\n")
sort.Strings(lines)
return strings.Join(lines, "\n")
2014-09-21 17:33:12 +00:00
}
func runExample(eg InternalExample) (ok bool) {
if *chatty {
2017-04-10 11:32:00 +00:00
fmt.Printf("=== RUN %s\n", eg.Name)
2014-09-21 17:33:12 +00:00
}
2012-03-27 23:13:14 +00:00
2014-09-21 17:33:12 +00:00
// Capture stdout.
stdout := os.Stdout
r, w, err := os.Pipe()
if err != nil {
fmt.Fprintln(os.Stderr, err)
os.Exit(1)
}
os.Stdout = w
outC := make(chan string)
go func() {
2017-04-10 11:32:00 +00:00
var buf bytes.Buffer
_, err := io.Copy(&buf, r)
2014-09-21 17:33:12 +00:00
r.Close()
2012-03-27 23:13:14 +00:00
if err != nil {
2014-09-21 17:33:12 +00:00
fmt.Fprintf(os.Stderr, "testing: copying pipe: %v\n", err)
2012-03-27 23:13:14 +00:00
os.Exit(1)
}
2014-09-21 17:33:12 +00:00
outC <- buf.String()
}()
start := time.Now()
ok = true
2012-03-27 23:13:14 +00:00
2014-09-21 17:33:12 +00:00
// Clean up in a deferred call so we can recover if the example panics.
defer func() {
2015-08-28 15:33:40 +00:00
dstr := fmtDuration(time.Now().Sub(start))
2012-03-27 23:13:14 +00:00
2014-09-21 17:33:12 +00:00
// Close pipe, restore stdout, get output.
2012-03-27 23:13:14 +00:00
w.Close()
2014-09-21 17:33:12 +00:00
os.Stdout = stdout
2012-03-27 23:13:14 +00:00
out := <-outC
2014-09-21 17:33:12 +00:00
var fail string
err := recover()
got := strings.TrimSpace(out)
want := strings.TrimSpace(eg.Output)
if eg.Unordered {
if sortLines(got) != sortLines(want) && err == nil {
fail = fmt.Sprintf("got:\n%s\nwant (unordered):\n%s\n", out, eg.Output)
}
} else {
if got != want && err == nil {
fail = fmt.Sprintf("got:\n%s\nwant:\n%s\n", got, want)
}
2014-09-21 17:33:12 +00:00
}
if fail != "" || err != nil {
2015-08-28 15:33:40 +00:00
fmt.Printf("--- FAIL: %s (%s)\n%s", eg.Name, dstr, fail)
2012-03-27 23:13:14 +00:00
ok = false
} else if *chatty {
2015-08-28 15:33:40 +00:00
fmt.Printf("--- PASS: %s (%s)\n", eg.Name, dstr)
2012-03-27 23:13:14 +00:00
}
2014-09-21 17:33:12 +00:00
if err != nil {
panic(err)
}
}()
2012-03-27 23:13:14 +00:00
2014-09-21 17:33:12 +00:00
// Run example.
eg.F()
2012-03-27 23:13:14 +00:00
return
}