Comments 2
Не совсем понятно какую проблему решали и как-то слиплись Unit тесты и интеграционные.
В случае Unit тестов все-таки не так сложно инициализировать SUT (system/service under test) в отдельном методе/конструкторе и тп. Следуя правилу 1 класс и 1 набор тестов, но даже в случае если не так то можно разделить на папки и рядом положить хэлпер с инициализацией.
В случае с интеграционными тестами все-таки есть TestHost из которого можно получать ServiceProvider, но в целом звучит тоже довольно странно, потому что уместнее тут тестировать через endpoint'ы (web api/consumer/cron job и тд), тогда и контейнер брать из хоста не надо.
И в заключении, сейчас кажется нет проблем запускать окружение для полноценных тестов, в том же gitlab делается не так сложно (спасибо контейнерам), почти для всех внешних зависимостей есть легкие контейнеры чисто для тестирования, а для мока внешних вызовов можно использовать mountebank
Удивительно, про AutoMocker не знал. Использовал подобный самописный «велосипед».
А по поводу использования контейнера зависимостей в unit-тестах – всегда был противником такого решения. DI-контейнер – это инфраструктурная вещь, которая реализуется на уровне платформы/framework-а приложения, но не бизнес-логики. В тесте сервиса стоит четко описать требуемые зависимости. Если зависимостей много, то стоит задуматься над рефакторингом для разделения ответственности. Использование контейнера и костыля в виде вызова RegisterEverything() делает тест хрупким.
Из-за попытки прокинуть контейнер зависимостей в тесты возникает и проблема, которая описана в разделе «Тестирование уровня проекта». Если уйти от этого, то будет достаточно сделать unit-тесты для реализации конкретных сервисов + единственный тест на проект для статического метода ContainerConfig.RegisterDomainServices(), проверяющий, что все реализуемые проектом интерфейсы добавлены в контейнер.
Тестирование дерева зависимостей