#
Тестирование на языке Zig: подробное руководство с примерами
Тестирование играет важнейшую роль в разработке качественного программного обеспечения. Хорошо настроенные тесты позволяют обнаружить ошибки и предотвратить появление дефектов до их выхода в продакшн. В данном руководстве мы пошагово рассмотрим организацию тестов на языке Zig, начав с простых примеров и постепенно переходя к более сложным случаям.
#
Основы тестирования на Zig
Первым делом начнём с простого примера. Допустим, у нас есть простая программа, складывающая числа:
#
Файл src/main.zig
const std = @import("std");
pub fn add(a: i32, b: i32) i32 {
return a + b;
}
pub fn main() void {
std.debug.print("Результат равен {d}\n", .{add(2, 3)});
}
Программа выводит сумму чисел, но наша задача — убедиться, что функция add работает корректно. Для этого напишем тесты.
#
Организация тестов
Создадим файл с тестами. Предположим, мы хотим хранить тесты отдельно от основного кода, поместив их в директорию tests:
mkdir tests
touch tests/test_main.zig
#
Написание первого теста
В нашем тестовом файле напишем первый тест, проверяющий функцию add:
// tests/test_main.zig
const std = @import("std");
const main = @import("main"); // Подключение основного модуля
const expect = std.testing.expect;
test "Проверка функции add" {
const result = main.add(2, 3);
try expect(result == 5);
}
Обратите внимание, что мы использовали импорт @import("main"), чтобы обратиться к нашему главному модулю.
#
Сборка и выполнение тестов
Чтобы наши тесты заработали, необходимо правильно настроить сборку. Сделаем это с помощью инструмента build.zig:
// build.zig
const std = @import("std");
pub fn build(b: *std.Build) void {
const target = b.standardTargetOptions(.{});
const optimize = b.standardOptimizeOption(.{});
// Создаём модуль для исполняемого файла
const exe_module = b.createModule(.{
.root_source_file = b.path("src/main.zig"),
.target = target,
.optimize = optimize,
});
// Основное приложение
const exe = b.addExecutable(.{
.name = "my_project",
.root_module = exe_module,
});
// Устанавливаем исполняемый файл
b.installArtifact(exe);
// Тесты
const test_step = b.step("test", "Выполнить все тесты");
const lib = b.addTest(.{
.root_module = b.createModule(.{
.root_source_file = b.path("tests/test_main.zig"),
.target = target,
.optimize = optimize,
}),
});
// Добавляем зависимость на основной модуль
lib.root_module.addImport("main", exe_module);
const run_exe_unit_tests = b.addRunArtifact(lib);
// Включаем тесты в шаг сборки
test_step.dependOn(&run_exe_unit_tests.step);
// Установим тестовую процедуру как шаг по умолчанию
b.default_step.dependOn(&exe.step);
}
#
Выполнение тестов
Собрать и запустить тесты можно командой:
zig build test
Если тесты проходят успешно, вы не увидите сообщений. Если же были ошибки, то информация о них будет в консоли.
#
Дополнительные приёмы тестирования
Помимо простого вызова функций, Zig предоставляет широкие возможности для организации тестов:
- Параметризированные тесты. Их удобно использовать для многократной проверки функций с различными значениями.
- Тестирование ошибок. Функции, возвращающие значение типа
error, требуют особого внимания при проверке результатов. - Модульное тестирование. Возможно раздельное тестирование отдельных компонентов приложения.
#
Полезные советы
- Всегда делайте тесты общедоступными (pub), иначе они не будут доступны при запуске.
- Старайтесь делать тесты небольшими и изолированными. Чем меньше взаимосвязанных элементов, тем легче локализовать причину сбоя.
- Названия тестов должны быть информативными и однозначно отражающими их назначение.
#
Заключение
Организация тестирования на языке Zig — важная составляющая процесса разработки. Грамотно выстроенные тесты гарантируют устойчивость и работоспособность приложения, помогая избегать повторных регрессий и непредвиденных сбоев. Следуйте рекомендациям из этого руководства, и вы сможете качественно протестировать своё приложение на Zig.