Недавно на работе у меня была задача автоматизировать процесс выполнения действия в одном домене и проверки результата в другом домене.
Оказывается, это было сложнее, чем я думал раньше.
У меня не так много опыта работы с Cypress, поэтому это дало мне прекрасную возможность погрузиться и узнать о нем больше.
Поэтому в этой статье я хотел поделиться тем, что узнал о Cypress за этот месяц.
Уступка с «тогда»
Итак, вот интересное для начала. Как описано выше, мне нужно было проверить действие, выполненное на одном домене (X), на другом (Y). Для этого мне нужно было войти на веб-сайт Y, используя значение в файле cookie с веб-сайта X. Как оказалось, это был хороший опыт для понимания ограничений и компромиссов использования Cypress.
Мой первоначальный план состоял в том, чтобы просто использовать команду получить cookie, получить значение из заголовка и присвоить его переменной, чтобы я мог использовать его в команде посещения. Должно быть прямо, верно?
Не так много по нескольким причинам. Одним из них является то, что Cypress API является асинхронным. Вы не можете использовать возвращаемые значения команд Cypress или присваивать их переменной.
Поначалу это раздражает и немного сбивает с толку. Но если подумать, современные веб-приложения не синхронны.
Чтобы обойти это, я решил взглянуть на получение команд Cypress с оператором «then», например:
cy.getCookies().then((cookies) => { cy.log(cookies[0]['thing'] cy.visit('www.whatever.com/' + cookies[0]['thing'] })
Теоретически это должно получить доступ к значению, хранящемуся в файле cookie, и объединить его с концом команды посещения.
Но это привело к другой проблеме, из-за которой я и мой коллега немного почесали затылки…
Тайна перезапуска
Всякий раз, когда Cypress доходил до команды посещения внутри оператора «тогда», Cypress перезапускался. В консоли браузера не будет напечатана ошибка, что немного затруднит определение того, что происходит.
Он не перезапустит тест весь, а только текущий оператор it. Звучит безумно, но уверяю вас, это правда! Один из моих коллег тоже видел, как это произошло. Поэтому мы решили провести расследование.
Сначала мы рассмотрели возможность того, что значение cookie должно быть правильно закодировано для использования в URL-адресе. Поэтому мы решили использовать функцию JavaScript encodeURI, чтобы увидеть, имеет ли это значение. К сожалению, этого не произошло, Cypress все равно перезапустился бы.
Мой коллега нашел ошибку GitHub о таком же поведении при перезапуске Cypress. Это было открыто в 2019 году, а последний комментарий был год назад, поэтому эта проблема все еще затрагивает Cypress сегодня.
Поэтому мы решили все переосмыслить и смогли добиться некоторого прогресса, но вскоре столкнулись с другой проблемой; Cypress не поддерживает переход к разным доменам в рамках одного теста.
В документации Cypress это описано как компромисс. Поэтому, если у вас был тест, посещающий abc.com
, вы не можете изменить его на xyz.com
.
В конце концов, тест был разделен на два разных теста, чтобы обойти его. Теперь мы знаем в следующий раз!
Переключатели среды DIY
Одна вещь, которую я узнал, — это создание собственных переключателей, влияющих на ваши тесты в Cypress.
Я видел, что консоль печатала тонну запросов XHR в тесте, и это затрудняло чтение того, что происходило в тесте. Поэтому я решил провести небольшое исследование того, как я могу отключить регистрацию этой информации.
Выполнив быстрый поиск, вы можете! Но если вы хотите снова включить это ведение журнала, вам придется удалить код, который я считаю не очень хорошим. Я решил взглянуть на то, как превратить это в какой-то переключатель.
Оказывается можно! Это привело меня к переменным окружения в Cypress. Имея это в виду, я решил создать переменную окружения для сокрытия XHR-запросов.
Итак, вот код, который находится в файле index.js
(в папке поддержки):
if (Cypress.config('hideXHR')) { const app = window.top; if (!app.document.head.querySelector('[data-hide-command-log-request]')) { const style = app.document.createElement('style'); style.innerHTML = '.command-name-request, .command-name-xhr { display: none }'; style.setAttribute('data-hide-command-log-request', ''); app.document.head.appendChild(style); } }
А вот код файла cypress.json
:
{ "hideXHR": true }
Теперь вы можете просто переключить его на true или false в зависимости от того, хотите ли вы видеть ведение журнала XHR или нет! (И оказывается, у кого-то была такая же мысль, как и у меня!)
Я также решил создать переменную среды для игнорирования неперехваченных исключений (поскольку приложение, с которым я работал, выдавало неперехваченное исключение и не предоставляло трассировку стека).
Это было сделано путем взятия кода из документации Cypress, включения его в оператор if и обновления файла cypress.json
.
Борьба с ожиданием (и тайм-аутами)
Cypress довольно умен, он будет ждать, пока DOM не будет загружен, прежде чем искать элементы. Это часть возможности повторных попыток Cypress.
Однако в приложении, с которым я работал, Cypress предположил, что DOM полностью загружен. Таким образом, в некоторых случаях тест завершался неудачно, потому что элемента пока не существовало.
Сначала я бы использовал подождать, но мой коллега показал мне другое, изменив значение таймаута.
Изначально Cypress имеет тайм-аут по умолчанию, равный 4 секундам, но это значение можно изменить, например:
cy.get('.css-class', { timeout: 10000 })
Эта команда теперь имеет тайм-аут 10 секунд. Я считаю, что это лучше, чем использование команд ожидания.
Cypress Studio удобна для захвата сложных элементов.
У меня были проблемы с доступом к элементу, который мог исчезнуть, если вы щелкнете от него. Поэтому попытка получить доступ к элементу с помощью инструментов разработки или самого Cypress была невозможна.
Поэтому я обратился в Cypress Studio, чтобы записать этапы захвата именно этого элемента.
И Cypress Studio поймала точно то, что мне было нужно. Это довольно мощный способ записи шагов того, что было записано в ваш файл JavaScript, чтобы вы могли посмотреть, что было сделано.
Хотя это экспериментальная функция, ее все же стоит попробовать, если вы боретесь с элементом, поведение которого работает против вас.
Вы можете включить его, обновив файл cypress.json
следующим образом:
{ "experimentalStudio": true }
Иметь терпение с Дженкинсом
Проблема, с которой я не думал, что столкнусь, связана с Дженкинсом. Мои кипарисовые тесты отлично работали локально, но не работали, когда их запускал Jenkins job.
Любопытно, я посмотрел на сделанные снимки экрана и обнаружил, что причина сбоя теста в том, что он не смог найти элемент, и казалось, что часть страницы все еще загружается (об этом упоминалось ранее, поскольку Cypress думал, что DOM загрузился)
В качестве эксперимента я решил увеличить значение таймаута до 50 секунд, и, конечно же, это прошло. Поэтому мне пришлось расширить все существующие тайм-ауты до гораздо больших значений.
Возможно, причиной этого было то, что виртуальная машина, которую использует Дженкинс, значительно медленнее, чем моя рабочая машина.
Обзоры кода помогают найти области, в которых можно улучшить
Раньше я никогда не участвовал в обзорах кода, так как раньше работал ручным тестировщиком программного обеспечения. Так что для меня это был хороший способ поучиться у других и обрести уверенность в том, что в следующий раз я напишу лучшие тесты.
До скорого…
Надеюсь, вам понравилось читать этот пост о Cypress! Кто знает, может быть, в следующем месяце я напишу дополнительный пост о том, что еще узнал о Cypress.
Первоначально опубликовано на https://joshblewitt.dev.
Это моя первая публикация как на Medium, так и на моем личном веб-сайте