Pull to refresh

Comments 10

Монументально. Правда половина статьи про дружбу с Reqnroll.

У меня всё проще, использую тестовый вэб хост, все неуправляемые зависимости перманентно замоканы, чтобы программист не ошибся. Бд на отдельном инстансе, потому до запуска в контейнере так и не добрался.

Стратегию очистки данных выбираю по ситуации.

Если тест происходит в каком-то "скоупе" (пользователь, тенанант и т.д.), то просто создаю новый скоуп. Мусор БД не мешает и даже полезен, т.к. чужие данные мы видеть не должны.
Если тесту нужны "общие" данные, то делают TRUNCATE CASCASE. На прошлом проекте больше 1000 тестов проходили за минуту где-то. Подход с манипуляцией транзакцией считаю пока подозрительным, нужно над этим подумать.

В пирамиду тестирования не верю, видимо пишу слишком простые простые и получается, что интеграционных тестов сильно больше, чем юнитов. Критерий простой: если удобнее через интеграционный тестить, то беру его, если через юнит, то юнит. Главное, что я уверен в том, что написал и могу спокойной спать.

Слой интеграции с неуправляемыми зависимостями пишу 1 раз, тестирую руками. С ними, как правило, проблем в эксплуатации нет.

В пирамиду тестирования не верю, видимо пишу слишком простые простые и получается, что интеграционных тестов сильно больше, чем юнитов.

Kent Dodds, автор Testing Library (ранее известной как React Testing Library), также предпочитает в основном интеграционные тесты: Write tests. Not too many. Mostly integration. Он придумал концепцию Testing Trophy в качестве метафоры для такого подхода.

Также упор на интеграционные тесты иногда называют Testing Diamond (термин более ранний, но я не смог отследить его первоисточник).

А если уходить вглубь истории, есть такой интересный нюанс с появлением термина Пирамида Тестирования:

  • в 2009 году Mike Cohn написал статью The Forgotten Layer of the Test Automation Pyramid, суть которой можно описать так: разработчики пишут unit-тесты, QA пишут сквозные тесты, все забывают про интеграционные тесты (в статье названы Service Tests)

  • в той же статье он в качестве метафоры показал Пирамиду Тестирования (Testing Automation Pyramid)

  • затем в 2010 году в книге "Succeeding with Agile: Software Development Using Scrum" он ещё раз представил метафору Пирамиды Тестирования

Так вот: пирамида тестирования у Mike Cohn была лишь иллюстрацией к статье, а соль статьи именно в рекомендации обратить внимание на интеграционные тесты. Но почему-то в индустрии запомнили термин Пирамида Тестирования, а про интеграционные тесты снова забыли.

Уровни тестов с точки зрения внепроцессных зависимостей

Чёткие критерии разделения уровней тестов есть у Владимира Хорикова в прекрасной книге «Принципы Unit-тестирования»

Вот уж не знаю. Мне кажется, что разумнее делить уровни тестов по границам тестируемого поведения, а не по зависимостям. Тестируете поведение одного юнита - значит, это юнит-тест. Тестируете несколько своих юнитов вместе - интеграционный тест.

То, что в тесте затрагивается внепроцессная зависимость юнита, это всего лишь нюанс с некоторыми последствиями (задержки пуска, шум в результатах если зависимость сбоит; нестабильные тесты если зависимость некорректно сбрасывается и т.д.). Причём тормоза могут быть вполне приемлемы в ряде случаев. В конце концов, поведение это вполне себе атрибут юнита, а процесс это пятью этажами выше. Или вообще на другой улице.

Как вы тестируете сервисы, использующие СУБД?

Поднимаем in-memory базу.

Как изолируете тестовые сценарии, влияющие на базу данных?

Чистим часть таблиц между сценариями.

Работает замечательно.

Зачем тестировать in-memory бд? Это даст скорость, но вы теряете возможность использовать вещи специфичные для бд. Поднять контейнер с бд сейчас не сложно, для CI поднять контейнер с тем же pg не проблема, для локальных тестов есть TestConteiners. Это позволяет использовать и проверять более сложные запросы к бд, проверять миграции, а работает это не сильно медленее, например у нас тестсет из 500+ тестов на бд проходит приблизительно 45-60 секунд.

Изоляцию данных между тестами не делаем, просто в тесте генерируем данные через AutoFixture и проверяем наличие данных данных с конкретными id сгенерированными именно в конкретном тесте

У нас какие-то разные in-memory бд, потому что в моём случае она такая же полноценная, как и на диске. То есть я под этим не подразумевал какую-то куцую базу. Точно так же запускаю на ней любые запросы.

Какая именно in-memory БД используется, если не секрет?

  • та же СУБД, как на проде (будь то PostgreSQL, MS SQL, MySQL)

  • или SQLite в режиме in-memory

  • или Microsoft.EntityFrameworkCore.InMemory

  • или что-то иное

И речь о C# / .NET или о другой платформе?

Я не говорю, что она неполноценная, она просто другая, в ней используется провайдер отличный от того, что используется в приложении. Провайдер может генерировать не совсем такой запрос, как это делает провайдер в приложении. Когда используются стандартный SQL, то проблем как правило нет, но вот когда используется расширенный SQL, например pgSQL, различные блокировки, енумы, работа с json, вот тут могут возникнуть проблемы

И правда, как то ночью проглядеть умудрился.

Sign up to leave a comment.

Articles