Каков наилучший способ модульного тестирования такой функции?
Начать с его редизайна?
Частью разработки тестов в первую очередь является утверждение, что тестируемые интерфейсы также «лучше»;более легко потребляемый, более легко обслуживаемыйодин вам нужен для вашего варианта использования.
Две возможности:
Во-первых, код пытается вам сказать, что у вас есть требования к телеметрии;чтобы у вас была возможность запрашивать тестируемую систему и узнать, сколько объектов было сохранено в каждом хранилище, или каким был последний объект, сохраненный в каждом хранилище, или что-то в этом духе.
Тогда вы можете использоватьтелеметрия для написания вашего теста
Given:
telemetry reports that repository B has stored 7 objects
and myBool is true
When:
foo()
Then:
telemetry reports that repository B has stored 7 objects
Это в основном разбивает проблему на две части;набор тестов, которые гарантируют, что телеметрия точно сообщает количество раз, когда хранилище сохранило объект, а затем тест foo()
, который предполагает, что телеметрия работает.
Второй вариант: тест пытаетсясказать вам, что вы хотите, чтобы иметь возможность оценить, какие побочные эффекты происходят в программе.Так что сделайте эти эффекты первоклассным гражданином в вашем дизайне и напишите тесты, которые проверят эффекты.
List<Effect> foo () {
if (myBool) {
return List.of(SaveInRepositoryA);
} else {
return List.of(SaveInRepositoryB);
}
}
Теперь ваше утверждение стало проще - вы просто убедитесь, что в списке есть нужное количество элементов,и правильные элементы.
Важное замечание: эти проекты создают шов между вашей логикой и побочными эффектами.Представьте себе границу, на одной стороне которой находится сложная логика, которую легко проверить, потому что это все манипуляции с данными в памяти;на другой стороне границы находится код, который сложно проверить, но он настолько прост и понятен, что в нем явно нет ошибок.