Vitest
Я крайне редко взаимодействую с продуктовым кодом и тестами, а вот другие ребята почаще. И взаимодействие это им не очень нравилось: watch режим лагает, перзапуск тестов медленный.
Для меня главной проблемой являлась настройка, в частности с несчастным ESM. Ишью Meta: Native support for ES Modules больше трёх лет, transformIgnorePatterns всегда как-то странно работал (либо я не очень умный). Но в целом я справлялся с возникающими проблемами.
Хотя, я вспомнил что во времена работы в Альфа-Банке джест просто вырубал мой бедный макбук на интеле.
В общем, мы решили попробовать Vitest и начали переводить тесты на него. Мне не очень хотелось вписываться в эту историю, не измерив на сколько оно быстрее работает, но я полагался на отзывы коллег, которые пишут тесты много и часто.
И вот, внезапно, мы полностью мигрировали с джеста на витест и… получилось медленее))
Если локально взаимодействие с витестом действительно более отзывчивое и приятное, то на CI он показал себя на 2 с лишним минуты медленнее. Наши масштабы: 637 тест-файлов и 4239 теста, 12 воркеров.
Сперва я подумал, что проблема в Babel — мы не можем от него отказаться из-за пары плагинов. И если в джесте мы транспайлили файлы только бабелем, то в витесте это бабель + esbuild. Но на самом деле бабель занимает 20-30 секунд. Т.е. не самое узкое место.
А ещё получилось и не очень стабильно)))
Витест использует worker_threads для параллелизации и иногда эти треды не закрываются. Например, если используется fetch.
Таким образом тесты зависают и пайплайн падает по таймауту.
Самое неприятное: зависает оно иногда (я бы сказал в трети случаев). И лишь пару недель назад появился патч, который хотя бы показывает какой тест-файл залип. Вот ишью про это зависание.
Джест же, в свою очередь, использует child_process. По идее, этот способ более дорогой как с точки зрения создания процессов, так и общения между ними. Так же джест может использовать треды через workerThreads и, возможно, это может сделать джест более отзывчивым, но приведёт к таким же залипаниям.
Т.е. получается, что джест, используя медленный child_process, быстрее, чем vitest c worker_threads. Как-то странно выходит.
Так же витест может использовать child_process, но это просто катастрофа (минуты на 4-5 дольше, чем джест). Но при этом витесту можно указать что только некоторые тесты нужно запускать в child_process через через poolMatchGlobs. Таким образом мы заткнули залипающие тесты.
В общем, у меня впечатления от миграции смешанные. Местами стало лучше, а местами хуже. Решили, что локальный DX для нас важнее и остаёмся на витесте.
Ещё мне кажется, что стало менее контролируемо: теперь у нас есть и esbuild, в котором никто из нашей команды разобраться не сможет.
Утешает только то, что сама миграция занимает пару-тройку часов т.к. API почти 1 в 1 совпадает, и, если что, всегда можно вернуться на джест.
А что делать с производительностью пока не очень понятно, но попробовали пару вещей:
1. используем happy-dom вместо jsdom
2. инициализируем testing-library/jest-dom (он инициализируется где-то 500мс на каждый тест-файл) только в DOM окружениях
И всё равно получается медленнее, блин.
Так же мы пытались закидать проблему ресурсами, но, например, увеличение количества воркеров с 12 до 24 не приводит к видимым изменениям. Возможно может помочь шардирование, но я не фанат этой техники, т.к. сложно склеивать отчёты из нескольких запусков.
P.S. Вот дискуссия со сравнением производительности child_process и worker_threads
Я крайне редко взаимодействую с продуктовым кодом и тестами, а вот другие ребята почаще. И взаимодействие это им не очень нравилось: watch режим лагает, перзапуск тестов медленный.
Для меня главной проблемой являлась настройка, в частности с несчастным ESM. Ишью Meta: Native support for ES Modules больше трёх лет, transformIgnorePatterns всегда как-то странно работал (либо я не очень умный). Но в целом я справлялся с возникающими проблемами.
Хотя, я вспомнил что во времена работы в Альфа-Банке джест просто вырубал мой бедный макбук на интеле.
В общем, мы решили попробовать Vitest и начали переводить тесты на него. Мне не очень хотелось вписываться в эту историю, не измерив на сколько оно быстрее работает, но я полагался на отзывы коллег, которые пишут тесты много и часто.
И вот, внезапно, мы полностью мигрировали с джеста на витест и… получилось медленее))
Если локально взаимодействие с витестом действительно более отзывчивое и приятное, то на CI он показал себя на 2 с лишним минуты медленнее. Наши масштабы: 637 тест-файлов и 4239 теста, 12 воркеров.
Сперва я подумал, что проблема в Babel — мы не можем от него отказаться из-за пары плагинов. И если в джесте мы транспайлили файлы только бабелем, то в витесте это бабель + esbuild. Но на самом деле бабель занимает 20-30 секунд. Т.е. не самое узкое место.
А ещё получилось и не очень стабильно)))
Витест использует worker_threads для параллелизации и иногда эти треды не закрываются. Например, если используется fetch.
Таким образом тесты зависают и пайплайн падает по таймауту.
Самое неприятное: зависает оно иногда (я бы сказал в трети случаев). И лишь пару недель назад появился патч, который хотя бы показывает какой тест-файл залип. Вот ишью про это зависание.
Джест же, в свою очередь, использует child_process. По идее, этот способ более дорогой как с точки зрения создания процессов, так и общения между ними. Так же джест может использовать треды через workerThreads и, возможно, это может сделать джест более отзывчивым, но приведёт к таким же залипаниям.
Т.е. получается, что джест, используя медленный child_process, быстрее, чем vitest c worker_threads. Как-то странно выходит.
Так же витест может использовать child_process, но это просто катастрофа (минуты на 4-5 дольше, чем джест). Но при этом витесту можно указать что только некоторые тесты нужно запускать в child_process через через poolMatchGlobs. Таким образом мы заткнули залипающие тесты.
В общем, у меня впечатления от миграции смешанные. Местами стало лучше, а местами хуже. Решили, что локальный DX для нас важнее и остаёмся на витесте.
Ещё мне кажется, что стало менее контролируемо: теперь у нас есть и esbuild, в котором никто из нашей команды разобраться не сможет.
Утешает только то, что сама миграция занимает пару-тройку часов т.к. API почти 1 в 1 совпадает, и, если что, всегда можно вернуться на джест.
А что делать с производительностью пока не очень понятно, но попробовали пару вещей:
1. используем happy-dom вместо jsdom
2. инициализируем testing-library/jest-dom (он инициализируется где-то 500мс на каждый тест-файл) только в DOM окружениях
И всё равно получается медленнее, блин.
Так же мы пытались закидать проблему ресурсами, но, например, увеличение количества воркеров с 12 до 24 не приводит к видимым изменениям. Возможно может помочь шардирование, но я не фанат этой техники, т.к. сложно склеивать отчёты из нескольких запусков.
P.S. Вот дискуссия со сравнением производительности child_process и worker_threads