Краткий ликбез по локаторам в вебе
"Любишь UI-автотесты писать, люби и локаторы подбирать" (с) Конфуций
Конфуций, конечно, был мудрым человеком, и ещё поговаривал, что знание локаторов пригождется не только тем, кто работает с автоматизацией клиентской части.
Зачем это мне?
🔹 Если вы можете быстро найти локатор элемента, то репортить баги UI-части становится в разы проще. Вместо того, чтобы искать "красную нопку ОК на странице авторизации пользователя в личный кабинет", разработчик вбивает в поиск ".btn.submit" и моментально находит элемент, для которого нужно сделать исправления.
🔹 Если вы знаете, как работают CSS-селекторы, то можете проверять работу визуальной части не только как пользователь, но и как... скажем, продвинутый пользователь. Например, обнаружить, что выполненный пункт в ToDo-листе не перечеркивается, потому что не подтянулся стиль, который отвечает за то, чтобы текст элемента, находящегося в определенном состоянии, был зачеркнут.
🔹 Вообще механика работы веба — того, что мы, собственно, тестируем — становится намного понятнее, а работать с тем, что понимаешь, в разы приятнее. Кроме того, появляются новые идеи для проверок: а что будет, если мы уберем вот этот атрибут и попробуем ввести в поле невалидное значение? А если у кнопки стереть 'disabled' и кликнуть на неё, что-то произойдет?
🔹 Можно открывать новые для себя направления деятельности: например, одна моя коллега не пишет UI-тесты, но редактирует код страниц и добавляет элементам data-test-* атрибуты. Это требует аналитического мышления, системного подхода и внимательности, а ещё позволяет порботать с кодом, но без написания автотестов (если вдруг вам их писать не очень хочется).
Короче, локаторы нужны и важны, а DevTools (F12 в большинстве браузеров) — наш лучший друг.
Что такое локаторы?
По сути — запросы с тем или иным синтаксисом, которые позволяют нам обращаться к элементам страницы по их уникальным (или не очень) характеристикам.
То есть если обычно вы видите кнопку "Login" и знаете, что надо нажать именно на неё, то в случае с автоматизацией браузеру надо дать команду "нажать", а ещё обозначить, что именно жать. Собственно, чтобы взаимодействие браузера происходило с нужным вам элементом, а не соседним или вообще скрытым, и нужно умение писать уникальные локаторы. Ещё хорошо, чтобы локаторы были читабельными — тогда вашим коллегам будет проще понимать, к чему именно вы обращаетесь (и что пошло не так в случае проблемы), но это уже, увы, не всегда зависит от QA.
Какие виды локаторов существуют?
Selenium WebDriver ищет элементы с помощью двух методов:
- Find Element
- Find Elements
Оба получают на вход параметры: объект класса By + тип запроса (по чему будем искать элемент) и сам локатор. Локатор должен соответствовать типу запроса: если ищем по атрибуту, то в локатор кидаем значение атрибута, если по СSS-селектору — то селектор. Если запрос будет вида
find_element(By.XPATH, "#login_form")
, то, разумеется, вместо рабочего теста мы получим ошибку.
Пара других различий, которые важно знать о методах Find Element и Find Elements:
Объект класса By может принимать на вход следующие виды локаторов:
- ID
- Name
- XPath
- Link text
- Partial link text
- Tag name
- Class name
- CSS selector
При этом ID, Name, Tag name и Class name — частные случаи CSS-селекторов. Таким образом, основные виды локаторов, с которыми мы будем сталкиваться — это CSS-селекторы и XPath. О них и поговорим ниже.
CSS Selector
Использует для поиска элемента его части (атрибуты). Изначальная цель использования —поиск элементов HTML-странички и навешивание на них стилей. Так как стилями нужно мочь обвешать все элементы страницы, синтаксис селекторов разработан с ориентиром на максимальную гибкость.
Синтаксис:
- id (#uniqueid)
- tag (H1)
- name ([name="my-element"])
- class (.class1.class2)
- другое значение атрибута ([attribute="value"])
- текст в элементе: псевдокласс из jquery :contains()
- положение потомка: :nth-child(1)
Примеры использования:
#test
— поиск по ID “test”tag
— поиск по тэгу “tag”.my-class
— поиск по классу “my-class”.class1.class2
— поиск по классам “class1 class2” или “class2 class1” (обратите внимание, что порядок классов элемента не имеет значения при написании селектора)[name="my-name"]
— поиск по имени "my-name"[attribute="value"]
— поиск по значению "value" атрибута “attribute”a:contains("test")
— поиск по тексту "test", который содержится в элементе#posts > .item:nth-child(2) > .title
— составной селектор. Ищет элемент с классом title, который является потомком второго потомка элемента с классом item, который, в свою очередь, потомок элемента с ID = posts
XPath
Поиск элемента(ов) с помощью запроса XPath (XML path) — языка разметки в XML-документе. Приятный момент работы с XPath: здесь, в отличие от селекторов, можно производить перемещение как в глубину DOM-иерархии, так и в обратную сторону (например, искать родительский элемент по дочернему).
Синтаксис:
- / — поиск прямого потомка
- // — поиск потомка любой степени
- [ ] — фильтрация
- Функция text() - поиск по тексту элемента
- Функция contains() - поиск полного или частичного совпадения
- Булевы операции and, or, not
- * - выбор всех элементов
Важный момент: XPath регистрозависим. То есть если запрос вида //*[@class=”my-class”]
находит элемент, то запрос вида //*[@Сlass=”my-Сlass”]
тот же элемент не обнаружит.
Возможный вид запроса:
//корень(конкретный или *)/потомок[параметры фильтрации]
Примеры использования:
//*[@class=”my-class”]
— поиск по всем элементам, у которых есть класс ”my-class”//div/p/a[text()=”Пример текста”]
— поиск по всем элементам a, содержащим текст ”Пример текста” и являющимся прямыми потомками элемента p, который прямой потомок элемента div//*[@data-test=”select-button” or contains(@class, “login-button”)]
— поиск по всем элементам, у которых есть data-test-атрибут со значением ”select-button” ИЛИ у которых в имени класса есть “login-button”//div[1]
— выбор первого потомка элемента div
DevTools наш друг
Чтобы искать элементы быстрее и убедиться, что написанный запрос вернет нам нужное количество элементов страницы, можно (и нужно) использовать DevTools. Они открываются по нажатию F12 или комбинации Ctrl+Shift+I. Во вкладке Elements можно посмотреть код страницы и скопировать уникальный локатор того или иного элемента. Ещё пару лет назад таким образом возвращались трудночитабельные монстры, но браузеры умнеют (как и мы), и теперь часто Chrome возвращает отличные лаконичные локаторы.
Как же овладеть искусством поиска красивых локаторов? Практика, практика, практика!
Почитать (и потренироваться) дополнительно можно вот тут:
1. На официальном сайте Selenium: https://www.seleniumhq.org/docs/03_webdriver.jsp#locating-ui-elements-webelements
2. В документации к Selenium для вашего языка программирования. Вот так выглядит вариант для Python: https://selenium-python.readthedocs.io/locating-elements.html
3. В других местах:
- https://software-testing.ru/library/testing/testing-automation/3129-web-element-locators-for-test-automation
- http://barancev.github.io/good-locators/
- https://automated-testing.info/t/selenium-znakomimsya-s-lokatorami-i-vybiraem-pravilnyj/2268
- https://www.w3.org/TR/CSS2/selector.html
4. А вот тут можно найти готовые подсказки по CSS-селекторам, XPath и многому другому интересному ;)
- https://devhints.io/css
- https://devhints.io/xpath
- https://code.tutsplus.com/ru/tutorials/the-30-css-selectors-you-must-memorize--net-16048
Если вы хотите лишний раз попрактиковаться в написании CSS-селекторов — часто используемых локаторов — рекомендуем вам заглянуть на https://www.w3schools.com/css/exercise.asp и https://flukeout.github.io/.
Тем, кому совсем интересно и хочется больше практики из реальной жизни, поможе вот такое нетрудное упражнение:
- Выбрать туториал с любой формой из раздела Forms W3Schools (например, первый — Login Form)
- На странице туториала кликнуть кнопку Try it yourself
- Скопировать код из левой части редактора и сохранить на вашем компьютере в формате HTML
- Открыть сохраненную HTML-страницу и поискать для каждого элемента разного рода атрибуты и тэги.
А ещё очень рекомендуем обратить внимание на шаги 1.4 - 1.6 курса Автоматизация тестирования с помощью Selenium и Python и на модули 5 и 6 курса Веб-разработка для начинающих: HTML и CSS.
Когда вы чувствуете, что готовы попробовать поиск и написание локаторов на реальном веб-сайте, вы можете использовать песочницы из предыдущего поста или что-то из списка ниже:
- http://todomvc.com/
- http://executeautomation.com/demosite/Login.html
- http://eaapp.somee.com/
- http://computer-database.gatling.io/
- http://demo.guru99.com/
- http://automationpractice.com/
- https://phptravels.com/demo/
Надеюсь, этот ликбез оказался вам полезен! Всем интересных задач и красивых локаторов :)