Тестирование

Тесты в Go встроены в инструментарий: пакет testing и команда go test, без фреймворков.

Тестирование в Go — часть языка и тулчейна. Не нужны сторонние фреймворки: пакет testing и команда go test уже всё умеют.

Соглашения, на которых всё держится

Go-тесты построены на соглашениях об именах:

  • Файл с тестами называется имя_test.go.
  • Тестовая функция начинается с Test и принимает *testing.T.
  • Об ошибке сообщают через t.Errorf (тест продолжается) или t.Fatalf (тест останавливается).

Пусть есть функция, которую тестируем:

// файл mathx.go
package mathx

func Add(a, b int) int {
    return a + b
}
// файл mathx_test.go
package mathx

import "testing"

func TestAdd(t *testing.T) {
    got := Add(2, 3)
    want := 5
    if got != want {
        t.Errorf("Add(2, 3) = %d; хотим %d", got, want)
    }
}
go test
# подробный вывод:
go test -v

Вывод:

ok      example.com/myapp/mathx    0.002s

Табличные тесты — идиома Go

Любимый паттерн Go-тестирования — табличные тесты: набор случаев описывают срезом структур и прогоняют в цикле. Так легко добавлять новые случаи и видеть, какой именно упал, через t.Run с подтестами.

func TestAddTable(t *testing.T) {
    cases := []struct {
        name    string
        a, b    int
        want    int
    }{
        {"положительные", 2, 3, 5},
        {"с нулём", 0, 7, 7},
        {"отрицательные", -1, -1, -2},
    }

    for _, c := range cases {
        t.Run(c.name, func(t *testing.T) {
            if got := Add(c.a, c.b); got != c.want {
                t.Errorf("Add(%d, %d) = %d; хотим %d", c.a, c.b, got, c.want)
            }
        })
    }
}

Один цикл проверяет все случаи, а имена подтестов делают отчёт читаемым. Это канонический способ писать тесты в Go.

Покрытие и бенчмарки

Тулчейн умеет больше: go test -cover показывает покрытие, а функции BenchmarkXxx(b *testing.B) измеряют производительность через go test -bench.

go test -cover
go test -bench .
КомандаЧто делает
go testзапустить тесты пакета
go test -vс подробным выводом
go test -coverпоказать покрытие кода
go test -bench .запустить бенчмарки

Итог

  • Тесты лежат в файлах *_test.go, функции начинаются с Test и берут *testing.T.
  • Запуск — go test; никаких внешних фреймворков не нужно.
  • Идиома Go — табличные тесты со срезом случаев и подтестами через t.Run.
Проверьте себя
1. Как должен называться файл с тестами?
Atest_имя.go
Bимя_test.go
Cимя.test.go
Dtests/имя.go
2. Что принимает тестовая функция?
A*testing.T
Bcontext.Context
Cerror
Dничего
3. Что такое табличные тесты?
AТесты, выводящие таблицу
BНабор случаев в срезе структур, прогоняемый в цикле
CТесты только для баз данных
DТесты без проверок
Поддержать проект