Go предоставляет встроенный пакет testing
для написания тестов. Вот как им пользоваться:
// math.go
package math
func Add(a, b int) int {
return a + b
}
// math_test.go
package math
import "testing"
func TestAdd(t *testing.T) {
result := Add(2, 3)
if result != 5 {
t.Errorf("Add(2, 3) = %d; want 5", result)
}
}
Идеальный подход для большинства случаев:
func TestAdd_TDD(t *testing.T) {
tests := []struct {
name string
a, b int
want int
}{
{"positive", 2, 3, 5},
{"negative", -1, -1, -2},
{"zero", 0, 0, 0},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
if got := Add(tt.a, tt.b); got != tt.want {
t.Errorf("Add() = %v, want %v", got, tt.want)
}
})
}
}
t.Error()
/ t.Errorf()
- сообщение об ошибке без остановки тестаt.Fatal()
/ t.Fatalf()
- критическая ошибка, прерывающая тестt.Log()
- вывод дополнительной информацииt.Helper()
- пометка функции как вспомогательнойt.Parallel()
- запуск теста параллельноНаиболее популярный набор инструментов:
import (
"testing"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
"github.com/stretchr/testify/suite"
)
// Простые assertions
func TestAdd_Testify(t *testing.T) {
result := Add(2, 3)
assert.Equal(t, 5, result, "they should be equal")
require.NotNil(t, result, "result should not be nil")
}
// Test suites
type MathTestSuite struct {
suite.Suite
}
func (s *MathTestSuite) TestAdd() {
s.Equal(5, Add(2, 3))
}
func TestMathSuite(t *testing.T) {
suite.Run(t, new(MathTestSuite))
}
Преимущества Testify:
mock
)Генерация моков на основе интерфейсов:
go install github.com/golang/mock/mockgen@latest
mockgen -source=repository.go -destination=repository_mock.go -package=mocks
ctrl := gomock.NewController(t)
defer ctrl.Finish()
mockRepo := mocks.NewMockRepository(ctrl)
mockRepo.EXPECT().
FindByID(123).
Return(&User{Name: "John"}, nil)
Именование:
*_test.go
Test[Функция]_[Сценарий]
или Test[Функция]
tt
(test case), want
(ожидаемое значение)Организация:
internal/testutils
для вспомогательных функцийПокрытие:
go test -cover
go test -coverprofile=coverage.out && go tool cover -html=coverage.out
Параллелизация:
func TestParallel(t *testing.T) {
t.Parallel()
// тестовый код
}
Go предлагает:
testing
для unit-тестовВыбор инструментов зависит от проекта: