QA The Other WayОбеспечение качества в эпоху тестов, написанных искусственным интеллектом. QA The Other Way.
Тестовый дизайн

Локатор - это контракт, а не координата

CSS и XPath часто описывают положение кнопки, а не её назначение. Роли, подписи и тестовые идентификаторы дают локаторам Playwright более устойчивый контракт.

7 мин. чтенияQA The Other Way
Панель управления, иллюстрирующая элементы управления, определенные по их назначению.
Редакционная иллюстрация, созданная искусственным интеллектом.
Иллюстративное видео к этой статье. английский экранный текст; выберите субтитры для этого языка.

Переведенное издание. Технические идентификаторы остаются в своей первоначальной форме.

page.locator('.panel > div:nth-child(3) > button.primary') сегодня работает. Это работает завтра. Он продолжает работать до тех пор, пока дизайнер не переместит кнопку на один слот влево, и тогда ваш пакет выйдет из строя из-за функции, которую никто не сломал. Вы не написали тест. Вы написали фотографию DOM.

Что на самом деле рекомендует драматург

В документации драматурга об этом говорится необычайно прямо. В руководстве по локаторам рекомендуется расставлять приоритеты атрибутов, ориентированных на пользователя, и явных контрактов: getByRole, getByLabel, getByText, getByPlaceholder, getByTestId. Локаторы ролей отражают то, как пользователи и вспомогательные технологии воспринимают страницу. Идентификаторы тестов создают отдельный явный контракт ценой невидимости для пользователей. Они останутся стабильными только в том случае, если разработчики сохранят этот контракт. Селекторы CSS и XPath документированы как хрупкие, поскольку они привязаны к структуре DOM, а структура DOM - это то, что меняется.

Два свойства структуры вознаграждают за хорошую привычку. Локаторы повторно разрешаются перед каждым действием, поэтому повторный рендеринг между двумя шагами не оставляет вам устаревший элемент. А локаторы строгие: если ваш селектор соответствует двум элементам, действие выбрасывает вместо того, чтобы молча щелкнуть первый. Строгий сбой в CI раздражает полдня. Неправильный щелчок в неправильном диалоговом окне - это отчет об ошибке с вашим именем.

Почему генераторы в первую очередь обращаются к вредной привычке

Сгенерированный набор может использовать селектор, который разрешается на текущей странице, без учета того, что изменится при редизайне. Это риск проверки, а не свидетельство данных обучения какой-либо конкретной модели. Тесты, связанные с макетом, могут пройти в первый же день и провалиться после изменения внешнего интерфейса по причинам, не связанным с поведением продукта.

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

Пятнадцатиминутный аудит любого пакета

Создайте тесты для page.locator со строками CSS или XPath, а также для getByText, используемого в интерактивных элементах. Для каждого попадания задайте один вопрос: называет ли этот селектор, что это за элемент или где он находится? Замените координаты контрактами:

  • Кнопки и ссылки: getByRole с доступным названием.
  • Поля формы: getByLabel или getByPlaceholder в качестве запасного варианта.
  • Повторяющийся или динамический контент: data-testid согласован с разработчиками.
  • getByText: полезно для текстового контента; предпочитайте роль и доступное имя при нажатии на элемент управления.

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

Ловушка строгости, и когда first() - это признание

Локаторы драматурга строгие: действие над селектором, который соответствует двум элементам, вызывает нарушение, а не угадывание. Рассматривайте каждую ошибку строгого режима как вопрос проектирования. Если вам нужен .first() для прохождения пакета, верно одно из двух: страница отображает дубликаты элементов управления, которые должны иметь разные доступные имена, или ваш селектор слишком широк. И то, и другое - выводы, а не неудобства. Исправление состоит в том, чтобы сузить список с помощью именованного контракта, отфильтровать по стабильному родительскому элементу или запросить идентификатор теста. Достижение .nth(1), потому что второе совпадение на этой неделе оказалось правильным, - это то, как пакеты учатся щелкать неправильный диалог после следующего выпуска.

Есть один законный аварийный люк. locator.or() существует для тех случаев, когда страница честно отображает одно из двух состояний, например форму входа или баннер уже выполненного входа. Используйте его сознательно, указав обе альтернативы, и он читается как ветвь. Используйте его, чтобы скрыть двусмысленность, и это будет восприниматься как пожимание плечами.

Где подходят агенты

Позвольте агенту исследовать и составлять проекты; локаторы - это место, где живет ваш отзыв. Сгенерированный тест с помощью getByRole('button', { name: 'Save' }) расскажет вам, что, по его мнению, делает страница. Сгенерированный тест с помощью div:nth-child(3) ничего вам не скажет, кроме того, что DOM когда-то выглядел так. Держите первый вид. Перепишите секунду, прежде чем она достигнет CI, потому что каждый хрупкий локатор, который вы принимаете, - это будущая ложная тревога, за которую вы уже заплатили.

Общие вопросы

Какая стратегия поиска в Playwright самая надежная?

Playwright рекомендует атрибуты, ориентированные на пользователя, и явные контракты: атрибуты getByRole, getByLabel, getByText и data-testid. Селекторы CSS и XPath документированы как хрупкие, поскольку они связывают тесты со структурой DOM.

Атрибуты data-testid лучше, чем локаторы ролей?

Они решают разные проблемы. Идентификаторы тестов выдерживают любые визуальные или структурные изменения, но ничего не говорят о том, что видит пользователь. Локаторы ролей выполняют функцию облегченной проверки доступности. Большинство зрелых пакетов сначала используют роли и метки, а также проверяют идентификаторы на наличие повторяющегося или сгенерированного контента.

Почему инструменты искусственного интеллекта так часто генерируют CSS-селекторы?

Генератор может выбрать селектор, который работает на текущей странице, не проверяя его стабильность при редизайне. Причина зависит от инструмента; проверяйте его выходные данные, а не предполагайте что-либо относительно обучающих данных.

Источники