Documentation ¶
Overview ¶
Package qt implements assertions and other helpers wrapped around the standard library's testing types.
Index ¶
- Variables
- func Assert(t testing.TB, checker Checker, comments ...Comment) bool
- func BadCheckf(format string, a ...any) error
- func Check(t testing.TB, checker Checker, comments ...Comment) bool
- func F2[Got, Want any](cf func(got Got, want Want) Checker, want Want) func(got Got) Checker
- func Format(v any) string
- func IsBadCheck(err error) bool
- func Patch[T any](tb testing.TB, dest *T, value T)
- type Arg
- type Checker
- func CmpEquals[T any](got, want T, opts ...cmp.Option) Checker
- func CodecEquals[T []byte | string](got T, want any, marshal func(any) ([]byte, error), ...) Checker
- func ContentEquals[T any](got, want T) Checker
- func DeepEquals[T any](got, want T) Checker
- func Equals[T any](got, want T) Checker
- func ErrorAs[T any](got error, want *T) Checker
- func ErrorIs(got, want error) Checker
- func ErrorMatches[StringOrRegexp string | *regexp.Regexp](got error, want StringOrRegexp) Checker
- func HasLen[T any](got T, n int) Checker
- func Implements[I any](got any) Checker
- func IsFalse[T ~bool](got T) Checker
- func IsNil[T any](got T) Checker
- func IsNotNil[T any](got T) Checker
- func IsTrue[T ~bool](got T) Checker
- func JSONEquals[T []byte | string](got T, want any) Checker
- func MapAll[K comparable, V any](container map[K]V, f func(elem V) Checker) Checker
- func MapAny[K comparable, V any](container map[K]V, f func(elem V) Checker) Checker
- func MapContains[K comparable, V any](container map[K]V, elem V) Checker
- func Matches[StringOrRegexp string | *regexp.Regexp](got string, want StringOrRegexp) Checker
- func Not(c Checker) Checker
- func PanicMatches[StringOrRegexp string | *regexp.Regexp](f func(), want StringOrRegexp) Checker
- func Satisfies[T any](got T, f func(T) bool) Checker
- func SliceAll[T any](container []T, f func(elem T) Checker) Checker
- func SliceAny[T any](container []T, f func(elem T) Checker) Checker
- func SliceContains[T any](container []T, elem T) Checker
- func StringContains[T ~string](got, substr T) Checker
- type Comment
- type SuppressedIfLong
- type Unquoted
Examples ¶
Constants ¶
This section is empty.
Variables ¶
var ErrSilent = fmt.Errorf("silent failure")
ErrSilent is the error used when there is no need to include in the failure output the "error" and "check" keys and all the keys automatically added for args. This helper can be used when implementing checkers.
Functions ¶
func Assert ¶
Assert checks that the provided argument passes the given check and calls tb.Fatal otherwise, including any Comment arguments in the failure.
func BadCheckf ¶
BadCheckf returns an error used to report a problem with the checker invocation or testing execution itself (like wrong number or type of arguments) rather than a real Check or Assert failure. This helper can be used when implementing checkers.
func Check ¶
Check checks that the provided argument passes the given check and calls tb.Error otherwise, including any Comment arguments in the failure.
func F2 ¶
F2 factors a 2-argument checker function into a single argument function suitable for passing to an *Any or *All checker. Whenever the returned function is called, cf is called with arguments (got, want).
func Format ¶
Format formats the given value as a string. It is used to print values in test failures.
func IsBadCheck ¶
IsBadCheck reports whether the given error has been created by BadCheckf. This helper can be used when implementing checkers.
func Patch ¶
Patch sets a variable to a temporary value for the duration of the test.
It sets the value pointed to by the given destination to the given value, which must be assignable to the element type of the destination.
At the end of the test (see "Deferred execution" in the package docs), the destination is set back to its original value.
Types ¶
type Checker ¶
type Checker interface { // Check runs the check for this checker. // On failure, the returned error is printed along with // the checker arguments (obtained by calling Args) // and key-value pairs added by calling the note function. // // If Check returns ErrSilent, neither the checker arguments nor // the error are printed; values with note are still printed. Check(note func(key string, value any)) error // Args returns a slice of all the arguments passed // to the checker. The first argument should always be // the "got" value being checked. Args() []Arg }
Checker is implemented by types used as part of Check/Assert invocations.
func CmpEquals ¶
CmpEquals is like DeepEquals but allows custom compare options to be passed too, to allow unexported fields to be compared.
It can be useful to define your own version that uses a custom set of compare options. See example for details.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" "github.com/google/go-cmp/cmp/cmpopts" ) func main() { runExampleTest(func(t testing.TB) { list := []int{42, 47} qt.Assert(t, qt.CmpEquals(list, []int{47, 42}, cmpopts.SortSlices(func(i, j int) bool { return i < j }))) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
Example (Customfunc) ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" "github.com/google/go-cmp/cmp" ) type myStruct struct { a int } func customDeepEquals[T any](got, want T) qt.Checker { return qt.CmpEquals(got, want, cmp.AllowUnexported(myStruct{})) } func main() { runExampleTest(func(t testing.TB) { got := &myStruct{ a: 1234, } qt.Assert(t, customDeepEquals(got, &myStruct{ a: 1234, })) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func CodecEquals ¶
func CodecEquals[T []byte | string]( got T, want any, marshal func(any) ([]byte, error), unmarshal func([]byte, any) error, opts ...cmp.Option, ) Checker
CodecEquals returns a Checker that checks for codec value equivalence.
It expects two arguments: a byte slice or a string containing some codec-marshaled data, and a Go value.
It uses unmarshal to unmarshal the data into an interface{} value. It marshals the Go value using marshal, then unmarshals the result into an any value.
It then checks that the two interface{} values are deep-equal to one another, using CmpEquals(opts) to perform the check.
See JSONEquals for an example of this in use.
func ContentEquals ¶
ContentEquals is like DeepEquals but any slices in the compared values will be sorted before being compared.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { got := []int{1, 23, 4, 5} qt.Assert(t, qt.ContentEquals(got, []int{1, 4, 5, 23})) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func DeepEquals ¶
DeepEquals returns a Checker checking equality of two values using cmp.DeepEqual.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { list := []int{42, 47} qt.Assert(t, qt.DeepEquals(list, []int{42, 47})) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func Equals ¶
Equals returns a Checker checking equality of two comparable values.
Note that T is not constrained to be comparable because we also allow comparing interface values which currently do not satisfy that constraint.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { answer := int64(42) qt.Assert(t, qt.Equals(answer, 42)) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func ErrorAs ¶
ErrorAs retruns a Checker checking that the error is or wraps a specific error type. If so, it assigns it to the provided pointer. This is analogous to calling errors.As.
Example ¶
package main import ( "errors" "fmt" "os" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { _, err := os.Open("/non-existent-file") // Checking for a specific error type. qt.Assert(t, qt.ErrorAs(err, new(*os.PathError))) qt.Assert(t, qt.ErrorAs[*os.PathError](err, nil)) // Checking fields on a specific error type. var pathError *os.PathError if qt.Check(t, qt.ErrorAs(err, &pathError)) { qt.Assert(t, qt.Equals(pathError.Path, "/non-existent-file")) } }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func ErrorIs ¶
ErrorIs returns a Checker that checks that the error is or wraps a specific error value. This is analogous to calling errors.Is.
Example ¶
package main import ( "errors" "fmt" "os" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { _, err := os.Open("/non-existent-file") qt.Assert(t, qt.ErrorIs(err, os.ErrNotExist)) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func ErrorMatches ¶
ErrorMatches returns a Checker checking that the provided value is an error whose message matches the provided regular expression pattern.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { err := errors.New("bad wolf at the door") qt.Assert(t, qt.ErrorMatches(err, "bad wolf .*")) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func HasLen ¶
HasLen returns a Checker checking that the provided value has the given length. The value may be a slice, array, channel, map or string.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { qt.Assert(t, qt.HasLen([]int{42, 47}, 2)) myMap := map[string]int{ "a": 13, "b": 4, "c": 10, } qt.Assert(t, qt.HasLen(myMap, 3)) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func Implements ¶
Implements returns a Checker checking that the provided value implements the interface specified by the type parameter.
Example ¶
package main import ( "errors" "fmt" "io" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { var myReader struct { io.ReadCloser } qt.Assert(t, qt.Implements[io.ReadCloser](myReader)) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func IsFalse ¶
IsFalse returns a Checker checking that the provided value is false.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { isValid := func() bool { return false } qt.Assert(t, qt.IsFalse(1 == 0)) qt.Assert(t, qt.IsFalse(isValid())) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func IsNil ¶
IsNil returns a Checker checking that the provided value is equal to nil.
Note that an interface value containing a nil concrete type is not considered to be nil.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { got := (*int)(nil) qt.Assert(t, qt.IsNil(got)) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func IsNotNil ¶
IsNotNil returns a Checker checking that the provided value is not nil. IsNotNil(v) is the equivalent of qt.Not(qt.IsNil(v)).
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { got := new(int) qt.Assert(t, qt.IsNotNil(got)) // Note that unlike reflection-based APIs, a nil // value inside an interface still counts as non-nil, // just as if we were comparing the actual interface // value against nil. nilValueInInterface := any((*int)(nil)) qt.Assert(t, qt.IsNotNil(nilValueInInterface)) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func IsTrue ¶
IsTrue returns a Checker checking that the provided value is true.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { isValid := func() bool { return true } qt.Assert(t, qt.IsTrue(1 == 1)) qt.Assert(t, qt.IsTrue(isValid())) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func JSONEquals ¶
JSONEquals returns a Checker that checks whether a string or byte slice is JSON-equivalent to a Go value. See CodecEquals for more information.
It uses DeepEquals to do the comparison. If a more sophisticated comparison is required, use CodecEquals directly.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { data := `[1, 2, 3]` qt.Assert(t, qt.JSONEquals(data, []uint{1, 2, 3})) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func MapAll ¶
func MapAll[K comparable, V any](container map[K]V, f func(elem V) Checker) Checker
MapAll returns a Checker that uses checkers returned by f to check values of a map. It succeeds if f(v) passes the check for all values v in the map.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { qt.Assert(t, qt.MapAll(map[string]int{ "x": 2, "y": 2, }, qt.F2(qt.Equals[int], 2))) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func MapAny ¶
func MapAny[K comparable, V any](container map[K]V, f func(elem V) Checker) Checker
MapAny returns a Checker that uses checkers returned by f to check values of a map. It succeeds if f(v) passes the check for any value v in the map.
See the F2 function for a way to adapt a regular checker function to the type expected for the f argument here.
See also MapAll and MapContains.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { qt.Assert(t, qt.MapAny(map[string]int{"x": 2, "y": 3}, qt.F2(qt.Equals[int], 3))) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func MapContains ¶
func MapContains[K comparable, V any](container map[K]V, elem V) Checker
MapContains returns a Checker that succeeds if the given value is contained in the values of the given map, by comparing for equality.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { qt.Assert(t, qt.MapContains(map[string]int{ "hello": 1234, }, 1234)) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func Matches ¶
Matches returns a Checker checking that the provided string matches the provided regular expression pattern.
Example ¶
package main import ( "errors" "fmt" "net" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { qt.Assert(t, qt.Matches("these are the voyages", "these are .*")) qt.Assert(t, qt.Matches(net.ParseIP("1.2.3.4").String(), "1.*")) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func Not ¶
Not returns a Checker negating the given Checker.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { got := []int{1, 2} qt.Assert(t, qt.Not(qt.IsNil(got))) answer := 13 qt.Assert(t, qt.Not(qt.Equals(answer, 42))) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func PanicMatches ¶
PanicMatches returns a Checker checking that the provided function panics with a message matching the provided regular expression pattern.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { divide := func(a, b int) int { return a / b } qt.Assert(t, qt.PanicMatches(func() { divide(5, 0) }, "runtime error: .*")) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func Satisfies ¶
Satisfies returns a Checker checking that the provided value, when used as argument of the provided predicate function, causes the function to return true.
Example ¶
package main import ( "errors" "fmt" "math" "os" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { // Check that an error from os.Open satisfies os.IsNotExist. _, err := os.Open("/non-existent-file") qt.Assert(t, qt.Satisfies(err, os.IsNotExist)) // Check that a floating point number is a not-a-number. f := math.NaN() qt.Assert(t, qt.Satisfies(f, math.IsNaN)) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func SliceAll ¶
SliceAll returns a Checker that uses checkers returned by f to check elements of a slice. It succeeds if all elements of the slice pass the check. On failure it prints the error from the first index that failed.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { qt.Assert(t, qt.SliceAll([]int{3, 5, 8}, func(e int) qt.Checker { return qt.Not(qt.Equals(e, 0)) })) qt.Assert(t, qt.SliceAll([][]string{{"a", "b"}, {"a", "b"}}, qt.F2(qt.DeepEquals[[]string], []string{"a", "b"}))) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func SliceAny ¶
SliceAny returns a Checker that uses the given checker to check elements of a slice. It succeeds if f(v) passes the check for any v in the slice.
See the F2 function for a way to adapt a regular checker function to the type expected for the f argument here.
See also SliceAll and SliceContains.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { qt.Assert(t, qt.SliceAny([]int{3, 5, 7, 99}, qt.F2(qt.Equals[int], 7))) qt.Assert(t, qt.SliceAny([][]string{{"a", "b"}, {"c", "d"}}, qt.F2(qt.DeepEquals[[]string], []string{"c", "d"}))) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func SliceContains ¶
SliceContains returns a Checker that succeeds if the given slice contains the given element, by comparing for equality.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { qt.Assert(t, qt.SliceContains([]int{3, 5, 7, 99}, 99)) qt.Assert(t, qt.SliceContains([]string{"a", "cd", "e"}, "cd")) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
func StringContains ¶
StringContains returns a Checker checking that the given string contains the given substring.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { qt.Assert(t, qt.StringContains("hello world", "hello")) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
type Comment ¶
type Comment struct {
// contains filtered or unexported fields
}
Comment represents additional information on a check or an assertion which is displayed when the check or assertion fails.
Example ¶
package main import ( "errors" "fmt" "testing" "github.com/go-quicktest/qt" ) func main() { runExampleTest(func(t testing.TB) { a := 42 qt.Assert(t, qt.Equals(a, 42), qt.Commentf("no answer to life, the universe, and everything")) }) } func runExampleTest(f func(t testing.TB)) { defer func() { if err := recover(); err != nil && err != exampleTestFatal { panic(err) } }() var t exampleTestingT f(&t) if t.failed { fmt.Println("FAIL") } else { fmt.Println("PASS") } } type exampleTestingT struct { testing.TB failed bool } var exampleTestFatal = errors.New("example test fatal error") func (t *exampleTestingT) Helper() {} func (t *exampleTestingT) Error(args ...any) { fmt.Printf("ERROR: %s\n", fmt.Sprint(args...)) t.failed = true } func (t *exampleTestingT) Fatal(args ...any) { fmt.Printf("FATAL: %s\n", fmt.Sprint(args...)) t.failed = true panic(exampleTestFatal) }
Output: PASS
type SuppressedIfLong ¶ added in v1.100.0
type SuppressedIfLong struct { // Value holds the original annotated value. Value any }
SuppressedIfLong indicates that the value must be suppressed if verbose testing is off and the pretty printed version of the value is long. This is useful when a checker calls note and does not want the provided value to be printed in non-verbose test runs if the value is too long.