package
1.2.0
Repository: https://github.com/drykit-go/testx.git
Documentation: pkg.go.dev

# README

testx/check

testxtestx/checktestx/checkconv

Package check provides checkers interfaces and implementations for testx test runners.

Table of contents

Checker interfaces

A checker is a type-specific interface composed of 2 funcs Pass and Explain:

// IntChecker provides methods to run checks on type int.
type IntChecker interface {
    IntPasser
    Explainer
}

// IntPasser provides a method Pass(got int) bool to determinate
// whether the got int passes a check.
type IntPasser interface { Pass(got int) bool }


// Explainer provides a method Explain to describe the reason of a failed check.
type Explainer interface { Explain(label string, got interface{}) string }

Provided checkers

Package check provides a collection of basic checkers for common types and kinds:

Covered types
Go typeChecker providerInterface
boolcheck.Bool TypeCheckerProvider
intcheck.Int IntCheckerProvider
float64check.Float64 Float64CheckerProvider
stringcheck.String StringCheckerProvider
[]bytecheck.Bytes BytesCheckerProvider
time.Durationcheck.Duration DurationCheckerProvider
context.Contextcheck.Context ContextCheckerProvider
http.Headercheck.HTTPHeader HTTPHeaderCheckerProvider
*http.Requestcheck.HTTPRequest HTTPRequestCheckerProvider
*http.Responsecheck.HTTPResponse HTTPResponseCheckerProvider
interface{}check.Value ValueCheckerProvider
Go kindChecker provider
slicecheck.Slice SliceCheckerProvider
mapcheck.Map MapCheckerProvider
structcheck.Bool StructCheckerProvider

Custom checkers

This section is about creating custom checkers, either extending the provided ones or full-fledged customs.

Extend provided checkers

There are 2 ways to extend a provided checker.

Using a New function

With every <Type> covered by this package comes a New<Type>Checker function.

It takes a PassFunc for the corresponding type (func(got Type) bool) and an ExplainFunc, then returns a checker for that type.

func Test42IsEven(t *testing.T) {
    checkIsEven := check.NewIntChecker(
        func(got int) bool { return got&1 == 0 },
        func(label string, got interface{}) string {
            return fmt.Sprintf("%s: expect even int, got %v", label, got)
        },
      )

    testx.Value(42).
        Pass(checkconv.FromInt(checkIsEven)).
        Run(t)
}

Related examples:

Using check.Value.Custom

func Test42IsEven(t *testing.T) {
    checkIsEven := check.Value.Custom(
        "even int",
        func(got interface{}) bool {
          gotInt, ok := got.(int)
          return ok && got&1 == 0
        },
      )

    testx.Value(42).
        Pass(checkIsEven).
        Run(t)
}

Custom checkers of any type

At some point you may need a checker for a type that is not (yet?) covered by check, such as float32 or complex128.
You may also want custom checkers for your own local types, like User.

Fortunately, because checkers are interfaces, it is easy to implement a custom checker for any type.

In practice, any type that implements func Pass(got Type) bool and Explainer interface is recognized as a valid checker and can be used for testx runners via checkconv.Cast.

Related examples:

  • CustomChecker: implementation of a custom checker that implements IntChecker
  • CustomCheckerUnknownType: implementation of a custom checker for a local type MyType struct
  • CustomCheckerClosures: advanced implementation of a parameterized custom checker for uncovered type complex128, using closures.

Contribute!

If you believe a particuliar checker should be natively implemented, feel free to contribute!