Skip to content

Commit

Permalink
feat: add IsError and NotIsError helpers
Browse files Browse the repository at this point in the history
As Go's error wrapping has become more and more common, these types of
tests are becoming ubiquitous.
  • Loading branch information
alecthomas committed Jun 8, 2023
1 parent dedb7c8 commit fed5290
Show file tree
Hide file tree
Showing 9 changed files with 59 additions and 8 deletions.
7 changes: 7 additions & 0 deletions .golangci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,13 @@ linters:
- gomoddirectives
- thelper
- varnamelen
- depguard
- exhaustruct
- nonamedreturns
- varcheck
- structcheck
- deadcode
- nosnakecase

linters-settings:
govet:
Expand Down
6 changes: 6 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,12 @@ func Error(t testing.TB, err error, msgAndArgs ...interface{})
// NoError asserts that an error is nil.
func NoError(t testing.TB, err error, msgAndArgs ...interface{})

// IsError asserts than any error in "err"'s tree matches "target".
func IsError(t testing.TB, err, target error, msgAndArgs ...interface{})

// NotIsError asserts than no error in "err"'s tree matches "target".
func NotIsError(t testing.TB, err, target error, msgAndArgs ...interface{})

// Panics asserts that the given function panics.
func Panics(t testing.TB, fn func(), msgAndArgs ...interface{})

Expand Down
29 changes: 24 additions & 5 deletions assert.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package assert

import (
"bytes"
"errors"
"fmt"
"reflect"
"strconv"
Expand Down Expand Up @@ -124,6 +125,24 @@ func EqualError(t testing.TB, err error, errString string, msgAndArgs ...interfa
}
}

// IsError asserts than any error in "err"'s tree matches "target".
func IsError(t testing.TB, err, target error, msgAndArgs ...interface{}) {
if errors.Is(err, target) {
return
}
t.Helper()
t.Fatal(formatMsgAndArgs(fmt.Sprintf("Error tree %q should contain error %q", err, target), msgAndArgs...))
}

// NotIsError asserts than no error in "err"'s tree matches "target".
func NotIsError(t testing.TB, err, target error, msgAndArgs ...interface{}) {
if !errors.Is(err, target) {
return
}
t.Helper()
t.Fatal(formatMsgAndArgs(fmt.Sprintf("Error tree %q should NOT contain error %q", err, target), msgAndArgs...))
}

// Error asserts that an error is not nil.
func Error(t testing.TB, err error, msgAndArgs ...interface{}) {
if err != nil {
Expand Down Expand Up @@ -185,15 +204,15 @@ func NotPanics(t testing.TB, fn func(), msgAndArgs ...interface{}) {
fn()
}

func diff[T any](lhs, rhs T) string {
func diff[T any](before, after T) string {
var lhss, rhss string
// Special case strings so we get nice diffs.
if l, ok := any(lhs).(string); ok {
if l, ok := any(before).(string); ok {
lhss = l
rhss = any(rhs).(string)
rhss = any(after).(string)
} else {
lhss = repr.String(lhs, repr.Indent(" ")) + "\n"
rhss = repr.String(rhs, repr.Indent(" ")) + "\n"
lhss = repr.String(before, repr.Indent(" ")) + "\n"
rhss = repr.String(after, repr.Indent(" ")) + "\n"
}
edits := myers.ComputeEdits("a.txt", lhss, rhss)
lines := strings.Split(fmt.Sprint(gotextdiff.ToUnified("expected.txt", "actual.txt", lhss, edits)), "\n")
Expand Down
19 changes: 19 additions & 0 deletions assert_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package assert

import (
"fmt"
"os"
"testing"
)

Expand Down Expand Up @@ -123,6 +124,24 @@ func TestNotZero(t *testing.T) {
})
}

func TestIsError(t *testing.T) {
assertOk(t, "SameError", func(t testing.TB) {
IsError(t, fmt.Errorf("os error: %w", os.ErrClosed), os.ErrClosed)
})
assertFail(t, "DifferentError", func(t testing.TB) {
IsError(t, fmt.Errorf("not an os error"), os.ErrClosed)
})
}

func TestNotIsError(t *testing.T) {
assertFail(t, "SameError", func(t testing.TB) {
NotIsError(t, fmt.Errorf("os error: %w", os.ErrClosed), os.ErrClosed)
})
assertOk(t, "DifferentError", func(t testing.TB) {
NotIsError(t, fmt.Errorf("not an os error"), os.ErrClosed)
})
}

type testTester struct {
*testing.T
failed string
Expand Down
File renamed without changes.
File renamed without changes.
2 changes: 1 addition & 1 deletion bin/go
2 changes: 1 addition & 1 deletion bin/gofmt
2 changes: 1 addition & 1 deletion bin/golangci-lint

0 comments on commit fed5290

Please sign in to comment.