Ale*_*lex 5 testing error-handling unit-testing go
我想根据预期结果的表测试来测试返回的错误类型,如下所示:
var tabletest = []struct{
instruction string
want string
err error
}{
{"synonym for hi", "hello", nil}, // input, retval, errtype
{"synonym for hig", "", TranslationError{}},
{"sssnymm for hi", "", InstructionError{}},
}
func TestThesaurus(t *Testing) {
for _, testcase := range tabletest {
got, err := Thesaurus(testcase.instruction)
// check error type
// check result type
}
}
Run Code Online (Sandbox Code Playgroud)
在上面的示例中,根据发生的错误类型返回不同的错误子类。您可能会想象,编造的 Thesaurus 函数的调用者会以不同的方式处理每种错误类型。
断言返回的错误类型和预期的错误类型相同的惯用方法是什么?
使用type开关。
func TestThesaurus(t *Testing) {
for _, testcase := range tabletest {
got, err := Thesaurus(testcase.instruction)
// Don't use && because we want to trap all cases where err is nil
if err == nil {
if testcase.err != nil {
// failure
}
continue
}
switch err.(type) {
case TranslationError:
if _,ok := (testcase.err).(TranslationError); !ok {
// failure
}
case InstructionError:
if _,ok := (testcase.err).(InstructionError); !ok {
// failure
}
default:
// Unrecognized error, failure
}
}
Run Code Online (Sandbox Code Playgroud)
它绝对不像reflect这样做的方式那么简洁,但我认为它更 Go-ish 和明确。
Reflect.TypeOf 的工作如下:
import "reflect"
...
func TestThesaurus(t *Testing) {
for _, testcase := range tabletest {
got, err := Thesaurus(testcase.instruction)
// check error type
if goterr, wanterr := reflect.TypeOf(err), reflect.TypeOf(testcase.err);
goterr != wanterr {
t.Errorf("For instruction %q, unexpected error: %q. Wanted %q",
testcase.instruction, goterr, wanterr)
}
// check result type
if want := testcase.want; got != want {
t.Errorf("For instruction %q, got %q, want %q.",
testcase.instruction, got, want)
}
}
}
Run Code Online (Sandbox Code Playgroud)
它是否惯用由社区决定。