Автотесты для сайта на Java с нуля

Что такое UI автотесты

UI (user interface, «пользовательский интерфейс») - это то, что мы видим глазами, когда заходим на сайт: иконки, кнопки, картинки и т.д.

Чтобы проверить, что все работает корректно - открываются нужные страницы, кнопки на странице нажимаются, необходимая информация отображается, поля ввода заполняются - проводят UI тесты (тестирование пользовательского интерфейса).

Конечно, некоторые сайты не так уж сложны, но когда речь идет, например, об интернет-магазинах/маркетплейсах/сайтах-агрегаторах - тут интерфейс выходит на первое место. Ведь пользователь просто ничего не купит, если не сможет выбрать товар, прочитать его описание и поместить товар в корзину.

Казалось бы, что сложного - можно тестировать интерфейс вручную - заходить на сайт, нажимать кнопки, заполнять поля и смотреть, что все элементы отображаются и работают корректно. Но когда раз за разом после каждого обновления нужно проверять одни и те же страницы и формы, это, мягко говоря, начинает утомлять. Кроме того, на это уходит неоправданно много времени!

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

С чего начать. Тест-дизайн

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

В общем случае базовая структура автотеста будет выглядеть следующим образом:

  1. Подготовка окружения
  2. Поиск нужных элементов на странице
  3. Совершение действия/ий с элементами
  4. Проверка результата
  5. Освобождение ресурсов

Давайте рассмотрим на примере, чем тест-кейс для автоматизированного тестирования отличается от тест-кейса для ручного тестирования.

Для примера, будем использовать простую формочку с нашего сайта -> https://softwarecats.dev

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

Кейс для ручного тестирования этой формы будет выглядеть так:

Предусловия:

Открыта форма “Обсудить проект”.
Есть кнопка “Отправить заявку”.

Шаги:

  1. Заполнить форму.
  2. Нажать кнопку “отправить заявку”

Ожидаемый результат:

Показано сообщение об успешной отправке заявки.

Для полной уверенности нам следовало бы еще убедиться в том, что
  • от сервера получен ответ 200 ОК,
  • данные из формы занесены в соответствующие таблицы в БД,
  • на email администратора пришло письмо с данными формы.
Но поскольку мы тестируем UI, то считаем, что появление сообщения об успешной отправке заявки является гарантом того, что сообщение действительно отправлено (и доставлено). По этой же причине мы пренебрежем постусловиями т.е. освобождением ресурсов - в идеале нам следовало бы удалить тестовые данные, которые мы вводили в форму, из базы данных.

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

Давайте перепишем этот тест так, как мы будем “говорить” программе, что нужно делать.

Предусловия:

  1. Открыть сайт https://softwarecats.dev в браузере Chrome (можно указать любой другой браузер, если проверка именно в нем важна)
  2. Найти на странице кнопку “Обсудить проект”
  3. Нажать на кнопку “Обсудить проект”

Шаги теста:

  1. Найти на странице поле “Как вас зовут?”
  2. Поставить курсор на поле “Как вас зовут?”
  3. В поле “Как вас зовут?” ввести значение. Ограничения на количество символов нет, только кириллица и латиница, строчные и заглавные буквы.
  4. Найти на странице поле “Любой удобный контакт”
  5. Поставить курсор на поле “Любой удобный контакт”
  6. В поле “Любой удобный контакт” ввести значение. Ограничения: на количество символов нет, кириллица и латиница, строчные и заглавные буквы, цифры, спецсимволы.
  7. Найти на странице поле “Что вы хотите обсудить?”
  8. Поставить курсор на поле “Что вы хотите обсудить?”
  9. В поле “Что вы хотите обсудить?” ввести значение. Ограничения на количество символов нет, ограничения на значение поля нет.
  10. Найти на странице кнопку “Отправить заявку”
  11. Нажать на кнопку “Отправить заявку”

Ожидаемый результат (проверить что):

Показано всплывающее окно с текстом “Спасибо! Данные успешно отправлены.”

Дальше дело техники - нужно правильно написать на Java шаги теста и проверку ожидаемого результата.

Настройка окружения

Код тестов мы будем писать на Java в среде разработки IntelliJ IDEA. Для этого необходимо установить все нужные компоненты.

Установка JAVA

Если у вас еще не установлена Java, то нужно скачать и установить JDK (это бесплатно) со старого доброго сайта Oracle -> https://www.oracle.com/java/technologies/downloads/#jdk19-windows


JDK (Java Development Kit) - это набор инструментов для разработки на Java. В него входят все необходимые компоненты, которые в том числе позволяют компилировать и запускать написанный код.

Для этого нужно:

  1. Убедится, что ваша система 64-разрядная:
  2. Пуск -> Параметры -> О системе.
  3. Убедиться, что Java еще не установлена (или уже установлена): открыть консоль/терминал Windows (Поиск -> cmd), набрать java -version и нажать Enter. Если Java установлена, то отобразится версия Java, если нет, то отобразится соответствующее сообщение.
  4. Перейти по ссылке на сайт Oracle и скачать Java.
  5. Инсталлировать Java, следуя инструкциям установщика.
  6. Прописать путь к JDK в системные переменные JAVA_HOME и Path. Поиск: изменение системных переменных среды. В открывшемся окне перейти в “Переменные среды”, нажать “Изменить” и прописать путь до JDK в системные переменные JAVA_HOME и Path.
  7. После этого шага понадобится перезагрузка.
8. Убедится, что Java установлена.

Еще один способ установить Java - это скачать готовый пакет Amazon Corretto -> https://aws.amazon.com/ru/corretto/ В этом случае системные переменные пропишутся автоматически.

Установка IntelliJ IDEA

IntelliJ IDEA - это среда разработки программного обеспечения, в которой разработчики и автотестировщики пишут код. В ней есть умный редактор, навигация, подсказки, в нее интегрированы все необходимые инструменты для сборки и публикации.

Бесплатную версию Community Edition можно скачать с официального сайта JetBrains -> https://www.jetbrains.com/ru-ru/idea/download/#section=windows

Запустить установку и следовать инструкциям, на шаге Installation Options отметить все пункты в разделе Create Associations: это расширения файлов, которые по умолчанию будут открываться в IDEA.

Установка Maven

Maven - это система управления проектом, которая используется для загрузки всех необходимых компонентов, установки параметров тестирования, запуска тестов, сбора базовой информации о результатах тестирования.

Скачать Maven можно с официального сайта https://maven.apache.org/download.cgi
Нужно скачать и распаковать zip-архив, путь до папки bin распакованного архива нужно добавить в переменную окружения Path по аналогий с JDK.

Проверить, что Maven устанавлем можно консольной командой mvn -v. Если все верно - отобразится версия Maven.

Установка Git

Скачать и установить Git с официального сайта -> https://git-scm.com/download/

Запустить установщик, при установке обязательно отметить галочку для установки GitBash - это приложение, эмулирующее работу командной строки Git, оно необходимо для полноценной работы с Git. Также необходимо поставить галочку “Использовать Git из командной строки”.

Чтобы убедиться, что Git установлен, запроси информацию о программе:
В терминале Winows ввести git --version (по аналогии с проверкой установки Java).

Чтобы при совместной работе над проектом коллеги смогли понять какие из изменений твои, необходимо в конфиге Git указать информацию о себе.

Для этого в терминале Windows нужно ввести свои данные - имя и email, используя команду git config --global:

git config --global user.name "My Name"
git config --global user.email me@email.mail
Теперь нужно проверить, что всё получилось: в терминале Windows выполнить команду git config --list

Среди прочих свойств будут и заданные данные: user.name и user.email.

Подготовка проекта

Чтобы создать проект, нужно запустить IDEA, перейти в меню File -> New -> Project.

В открывшемся окне нужно ввести название проекта, выбрать язык (Language), на котором будем писать код - Java, а также выбрать систему сборки (Build system) и указать какой JDK будем использовать (JDK). После этого нажать кнопку Create. Проект создан.
Теперь развернем в левом меню IDEA дерево файлов проекта, и развернем папку src. Это именно та папка, где будут хранится файлы проекта (в папке main -> java) и файлы тестов (test -> java).
Вот и все! Теперь мы готовы к написанию автотестов!

Краткая справка по Git. Коммиты, ветвление, мерж

Чаще всего над программным продуктом работает не один человек: кто-то пишет один модуль, еще кто-то другой, тесты могут писать совсем другие люди, не те, кто пишет основной код и т.д.. Чтобы хранить код удаленно и совместно работать над ним используются специальные сервисы, например GitHub или GitLab.

Одна из главных функций в этих сервисах - отслеживать изменения в файлах.

"Под капотом" у них - специальная утилита - Git - для отслеживания истории изменения файлов. С помощью Git вы можете откатить проект до более старой версии, сравнивать изменения в версиях проекта, объединить все изменения и тд.

Репозитории

Хранилище вашего кода/файлов (и истории его изменений) называют репозиторием.

Репозитории могут быть локальными - по сути, любая папка на жестком диске может быть репозиторием, и удаленными (внешними) - это версии вашего проекта, сохраненные на удаленном сервере.

Создадим локальный и удаленный репозитории и свяжем их между собой.

Папка, в которой хранится наш проект, автоматически не станет репозиторием. Нужно инициализировать репозиторий т.е. сообщить Git’у, что изменения в файлах, которые хранятся в этой папке, нужно отслеживать.

Для этого нужно перейти в папку проекта, правой кнопкой мыши открыть меню и запустить Git.
Откроется командная строка в которой нужно ввести и запустить команду git init. После чего Git сообщит, что репозиторий инициализирован.
Теперь git будет отслеживать изменения в файлах этого репозитория, но чтобы это произошло git’у нужно сообщить, какие именно файлы нужно отслеживать.

Статусы файлов, коммит

В Git есть несколько статусов файлов:

Untracked - файл, который Git пока не “видит” т.е. не отслеживает.
Unmodified - файл, который Git уже видит, но файл еще не изменялся.
Modified - это файл, в который вносились изменения (сам файл отслеживается Git’ом, но изменения пока не зафиксированы).
Staged - это файл, добавленный в индекс т.е. готовый к коммиту (сохранению) .
Как только файл будет закоммичен т.е. все изменения зафиксированы Git’ом, он снова переходит в статус unmodified.

Когда в инициализированном репозитории появляется новый файл, он автоматически попадает в состояние untracked, файл можно изменять, но Git не будет учитывать изменения. Чтобы Git “увидел” файл, его нужно добавить в индекс и тогда файл перейдет в состояние Staged.

Чтобы узнать какие файлы в каком состоянии находятся используется команда git status.
Видим, что Git показывает список не закоммиченых файлов и предлагает добавить файлы в индекс, с помощью команды git add название_файла. Можно добавить все файлы сразу, с помощью команды git add --all.

Выполняем команду. Теперь видно, что все файлы в репозитории готовы к коммиту.
Чтобы сохранить изменения в файле т.е. закоммитить файл, нужно дать Git команду git commit c ключом -m (англ. message), после ключа обычно указывают комментарий, в котором указывают, что именно изменилось в файле: git commit -m "My first commit".
Чтобы посмотреть список коммитов используется команда git log.

Как найти нужный коммит в истории, как посмотреть его, как откатить проект до определенной версии и многое другое можно изучить, воспользовавшись официальной документацией Git https://git-scm.com/doc.

Ветвление

Еще одна важная функция git, которая нам понадобится - это ветвление. Ветвление - это параллельная разработка по нескольким линиям т.е. разделение версий проекта и работа над ними по отдельности.

Когда репозиторий инициализируется командой git init, автоматически создается основная ветка. Обычно она автоматически называется master (иногда main) и в ней находится основная стабильная версия проекта.

Командой git branch можно посмотреть в какой ветке ты сейчас находишься.
Чтобы не испортить в процессе разработки тестов основную ветку, создают вторую ветку и работают уже с ней, назвать ее можно как угодно. Чтобы создать ветку используют команду git branch название_ветки.
Однако, после создания новой ветки, мы все еще находимся в основной ветке проекта. Чтобы переключится на вновь созданную ветку (или на любую другую) используется команда git checkout название_ветки. Либо используют ключ -b, чтобы переключится на ветку сразу после ее создания git checkout -b название_ветки.

Мерж

Чтобы слить (мёрджить, от англ merge - слияние) ветки между собой используется команда git merge [название ветки, которую присоединяют к текущей].

В разных компаниях по разному принято мержить в основную (master) ветку в удаленном репозитории проекта. Кто-то делает это самостоятельно, а где-то этим занимается ведущий тестировщик/разработчик только после ревью написанного кода. Но про это немного позже. А подробнее про merge, а так же про разрешение конфликтов, которые могут возникать в процессе слияния веток, можно почитать в документации git.

GitHub

Локальный и удаленный репозитории

Мы научились работать с git в локальном репозитории. Удаленные репозитории хранят в Интернете и используют для этого сервисы GitHub или GitLab.

Давайте взглянем на GitHub - это сервис для совместной разработки, в нем можно завести аккаунт и разместить свой код, а также совместно работать над любыми проектами.

Для этого нужно завести аккаунт и авторизоваться GitHub - тут все предельно просто.

Теперь нужно создать удаленный репозиторий. Для этого нужно перейти во вкладку Repositories и нажать New.
В открывшемся окне создания нового репозитория необходимо ввести его имя, а также пометить репозиторий как Public, если хотите, чтобы любой пользователь GitHub мог увидеть репозиторий. Так же отметим чек бокс для автоматического создания файла README.md - это инструкция к проекту, в котором с помощью специальной разметки, описывается, как пользоваться проектом. Подробнее можно посмотреть в документации.
Осталось нажать Create repository. Готово! Удаленный репозиторий создан и он пока пуст.

Чтобы связать локальный репозиторий с удаленным нам понадобится ссылка на удаленный репозиторий, она находится во вкладке Code.
Перейдем в папку проекта и запустим git. Ранее мы уже инициализировали локальный репозиторий, сделали первый коммит и создали отдельную ветку для разработки наших тестов. Но пока это все хранится только локально на компьютере. Чтобы проект был доступен удаленно и все изменения поступали в удаленный репозиторий, нужно связать репозитории между собой. Для этого используется команда git remote add origin URL_удаленного_репозитория.
Чтобы проверить, что репозитории связались, используется команда git remote -v
Теперь нужно передать файлы из локального репозитория в удаленный, для этого нужна команда git push.
Теперь мы видим в удаленном репозитории файлы и ветки нашего проекта.
Откроем проект в IDEA и перейдем во вкладку git, если нажать Share Project on GitHub,то IDEA выдаст предупреждение, что проект уже связан с удаленным репозиторием на GitHub.
Также в IDEA мы можем отслеживать состояние проекта, а так же использовать все основные команды git прямо из IDE.
Другой способ создания локального репозитория - сначала создать удаленный репозиторий с помощью GitHub/GitLab, а потом командой git clone скопировать его с сервера - подробнее в документации.

Pull Request

Нельзя просто так взять и залить свой код в master (стабильную версию проекта). Код должен пройти проверку. Для этого и создается pull request - это запрос на то, чтобы код объединили с основным. Чтобы создать пул-реквест нужно перейти в удаленный репозиторий, в ту ветку, в которую был последний пуш и которую необходимо залить в мастер.

Нажать кнопку Compare & pull request, заполнить название и описание, нажать кнопку Create pull request. Этот пул-реквест получит владелец репозитория для проверки. Здесь же, во вкладке Conversation можно обсудить изменения и необходимые правки. После ревью пул-реквеста код либо мержат в master, если предлагаемые изменения приняты, либо пул-реквест закрывается, если изменения не приняты.

Подключение библиотек

Откроем в IDEA ранее созданный проект и вспомним его структуру.
Обратим внимание на файл pom.xml (POM – Project Object Model) - это специальный XML-файл, который хранится в базовой директории проекта и содержит информацию о проекте, различных деталях конфигурации, библиотеках, плагинах и тд, которые используются Maven для создания проекта.

Для начала заполним данные о проекте <groupId>имя_пакета</groupId>
<artifactId>название_программы</artifactId>
<version>версия_программы</version>

Теперь подключим библиотеки.
Библиотека - это готовое решение, которое мы можем использовать при написании наших программ.

Как правило, большинство популярных библиотек находятся в центральном репозитории Maven, где можно найти нужную библиотеку и посмотреть как она подключается. Кстати в Maven библиотеки называются зависимостями.
Чтобы добавить зависимость, в файле pom нужно: создать блок
<dependencies></dependencies>, в котором будут хранится все зависимости; каждая зависимость объявляется внутри блока <dependencies> в тэге <dependency></dependency>.

Для написания UI тестов нам понадобятся зависимости JUnit и Selenium, Selenide
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.13.2</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.seleniumhq.selenium</groupId>
<artifactId>selenium-java</artifactId>
<version>3.141.59</version>
</dependency>
<dependency>
<groupId>com.codeborne</groupId>
<artifactId>selenide</artifactId>
<version>5.23.2</version>
</dependency>
</dependencies>
После того, как добавили зависимости в файл pom в IDEA нужно загрузить изменения в Maven.
После добавления нужных библиотек, лучше перезапустить IDEA и Maven.

Способы поиска элементов на странице

Прежде чем перейти к написанию кода, давайте вспомним с чего мы начинали написание автотеста, а именно тест-дизайн.

В шагах итогового сценария присутствуют шаги, начинающиеся со слов “Найти на странице поле/кнопку”. То есть, прежде чем совершать какие-то действия с элементом на странице (заполнять поле, нажимать кнопку и тд) нужно этот элемент на странице найти.

Для этого используются локаторы - это запросы, которые ищут элементы страницы по их характеристикам (например, по тексту, по классу или по id).

Локаторы могут находить один элемент, например, кнопку “Войти” или несколько, например, все ссылки на странице.

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

Один из наиболее популярных способов поиска элементов на странице это XPath. Именно его мы будем в дальнейшем использовать в наших автотестах.

XPath — это язык, на котором можно написать запрос, который поможет найти любой элемент на странице путем описания пути до него.

Путь до элемента можно задавать по разному.

Абсолютный путь до элемента

Абсолютный путь до элемента - это полный путь от корневого элемента до целевого. Например, путь до логотипа компании в хедере страницы будет выглядеть так: html/body/div/header/div[3]/div[2]/div/div/a/img
Этот способ не является оптимальным, поскольку любое изменение верстки страницы приведет к тому, что элементы по таким локаторам не будут найдены. Поэтому используется другой способ.

Поиск элементов по атрибутам

Можно искать элемент по любому из его атрибутов, но лучше выбрать какой-то уникальный атрибут - атрибут значение которого единственное на странице, например, только на одной кнопке на странице написано “Обсудить проект”. Но чаще всего такой атрибут - это id.

Синтаксис поиска элемента по id будет такой $xpath("html/body/div[@id='1']").

Часто испрользуется поиск элементов с использованием относитьельного пути и атрибутов. Весь путь до корневого элемента заменяется символами .//. Например, для ссылки пункта меню “О компании” запрос получится таким: $xpath(".//a[contains(text(),'О компании')]").

Более подробно про xpath можно почитать тут.

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

—note—
Кроме xpath, другим популярным методом поиска элементов на странице является поиск по css. В данном случае применяют CSS-селекторы - это специальные выражения, которые указывают на тот или иной элемент на странице. Например, [class='logo'] - найти элемент, у которого значение атрибута class = logo. Более подробно тут.


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

Потренироваться искать элементы страницы с помощью xpath или css можно используя инструменты разработчика браузера.
Например, чтобы найти кнопку “Оставить заявку” на главной странице сайта Softwarecats нам понадобится такой xpath-локатор: $xpath(".//a[contains(text(),'Оставить заявку')]").

Нужно ввести его в строку поиска в консоли браузера и если локатор составлен правильно, элемент будет найден.

Так.
Или так.
Часто приходится работать со сложными случаями: найти несколько элементов, выбрать только определенные элементы из списка, найти скрытые элементы и т.д. Главное не боятся и использовать все возможности xpath для составления локторов.

Google и немного упорства, и я уверена - все получится. А вот здесь можно посмотреть несколько примеров.


Вот и все! Теперь мы готовы к написанию непосредственно кода тестов. Как правильно написать шаги и проверки на языке Java, а так же о том какие подходы и паттерны использовать я напишу в следующей части.
Руководитель отдела тестирования Software Cats