5. Проблема 1: Составные элементы
@FindBy(css=".colors-dropdown .caret")
WebElement arrow;
@FindBy (css=".colors-dropdown . dd-menu")
List<WebElement> list;
@FindBy (css=".colors-dropdown [type='text']")
WebElement value;
public void selectColor (String color){
arrow.click();
for (WebElement el : list)
if (el.getText.equals(color)) {
el.click();
break;
}
arrow.click();
}
public String getSelectedColor(){
return value.getAttribute(“value”);
}
5
6. Составные элементы - Selenium
@FindBy(css=".color-dropdown .caret")
WebElement arrow;
@FindBy (css=".color-dropdown. dd-menu")
List<WebElement> list;
@FindBy (css=".color-dropdown [type='text']")
WebElement value;
@FindBy(css=".color-dropdown .caret")
WebElement arrow;
@FindBy (css=".color-dropdown. dd-menu")
List<WebElement> list;
@FindBy (css=".color-dropdown [type='text']")
WebElement value;
@FindBy(css=".color-dropdown .caret")
WebElement arrow;
@FindBy (css=".color-dropdown. dd-menu")
List<WebElement> list;
@FindBy (css=".color-dropdown [type='text']")
WebElement value;
public void selectColor (String color){
arrow.click();
for (WebElement el : list)
if (el.getText.equals(color)) {
el.click();
break;
}
arrow.click();
}
public String getSelectedColor(){
return value.getAttribute(“value”);
}
public void selectColor (String color){
arrow.click();
for (WebElement el : list)
if (el.getText.equals(color)) {
el.click();
break;
}
arrow.click();
}
public String getSelectedColor(){
return value.getAttribute(“value”);
}
public void selectColor (String color){
arrow.click();
for (WebElement el : list)
if (el.getText.equals(color)) {
el.click();
break;
}
arrow.click();
}
public String getSelectedColor(){
return value.getAttribute(“value”);
} 6
7. Составные элементы - JDI
class MyPage extends WebPage {
@FindBy(class = "colors-dropdown")
public IDropDown<Colors> colors = new Dropdown<>(
By.className("сarret"),
By.cssSelector("li span"),
By.cssSelector("[type=‘text’]"));
@FindBy(class = " sizes-dropdown")
public MyDropdown<Sizes> sizes;
}
7
8. Составные элементы - JDI
myPage.colors.select("Blue");
myPage.colors.setValue(Colors.BLUE);
*А еще можно работать с Enum
String value = myPage.colors.getValue();
8
10. Таблицы - Selenium
@FindBy(css=".root .table")
WebElement table;
@FindBy (css=".root .li .row")
List<WebElement> row;
@FindBy (css=".root .li .column")
List<WebElement> column;
public int getColumnsCount(){//TODO};
public int getRowdCount(){//TODO};
public String getRowValue (int index){//TODO};
public String getCellvalue (int index){//TODO};
public int searchRowContain(){//TODO};
public int searchRowMatch(){//TODO};
public String myGetRowValue (int index){//TODO};
public String myGetCellvalue (int index){//TODO};
public int myGetColumnCount(){//TODO};
public int myGetRowCount(){//TODO};
public String myGetRowValue (int index){//TODO};
public String myGetCellvalue (int index){//TODO};
public int myGetColumnCount(){//TODO};
public int myGetRowCount(){//TODO};
…
public String myGetCellvalue (int index){//TODO};
public void cellClick (int x, int y) {
driver.findElement(By.xpath(format("/tr[%s]/td[%s]"),x, y)).click();
}
10
13. Проблема 3: сложные ячейки
myPage.table.cell(1, 2).get(MyCell.class)
.seeMore.click(); 13
14. Итоги
• Существенное уменьшение количество кода
• Экономия времени тест инженера
• Тесты пишутся быстро
• Меньше вероятность ошибки
• Проще поддержка тестов
Типизированные элементы
14
33. Не только Web – Интерфейсы - JDI
Интерфейсы – взгляд на элементы с точки зрения
пользователя
myButton.click();
myButton.getText();
public interface IButton {
void click();
String getText();
}
33
34. Не только Web
@Test
public void addContactTest() {
ContactDetails contacts =
new ContactDetails(
"Irina",
"222-22-22");
startPage.addContact.click();
addContactForm.save(contacts);
}
34
36. UI Objects
+ Типизированные элементы
+ Типизированные Объекты (Секции)
+ Элементы-интерфейсы
UI Objects = PageObject
36
37. Выводы
• Меньше кода
• Экономия времени
• Увеличение производительности
• Меньше вероятность ошибки
• Проще поддержка тестов
• Легко адаптировать под свой проект
• Мультиплатформенность
• Логирование
37
Для оптимизации затрат на разработку и тестирования в компании Epam мы разрабатываем различные инструменты, которые помогают нам ускорить процесс разработки и существенно сэкономить деньги и время на внедрение автоматизации.
Мы также стараемся делится нашими наработками с сообществом, об одном из таких инструментов и пойдет речь.
Фреймворк, который мы используем для UI тестирования в компании называется JDI.
JDI имплементирует паттерн UI Objects, который расширяет всем известный паттерн Page Objects и позволяет легко адаптировать его под разные проекты отличающиеся не только версткой веб страницы, но и даже платформой (поддерживаются и мобильные устройства и Desktop)
Подробнее информацию об его использовании можно поcмотреть в презентациях по ссылочкам или почитать на нашем сайте.
Если вас больше интересует реализация или есть идеи по улучшению фреймворка, то welcome на Github.
4
5
В этом случае мы получим Page Object с большим количеством элементов и методов соотнести которые друг с другом будет крайне не просто
В JDI же мы смотрим на элементы с точки зрения пользователя. Для пользователя это 1 элемент dropdown. Так и запишем.
Все необходимые локаторы указываются вместе.
Также если вы обратили внимание у элемента можно указать общую часть локатора. Это позволяет сделать используемые локаторы существенно короче и нагляднее/
В случае если дропдауны в вашем проекте реализованы достаточно стандартно, то можно создать свой элемент и запись станет гораздо короче
8
9
10
В JDI же таблица описывается очень просто, так же как и любой другой элемент. JDI умеет работать с «локаторами шаблонами», в которые потом подставляются значения, что сохраняет концепцию PageObjects и делает сами классы наглядными и легко поддерживаемыми
У Таблиц также есть возможности для более детальной ее преднастройки, ну а в случае если таблица у вас реализована с использование стандартного подхода (тег table), вам достаточно просто указать локатор на него
JDI мы предлагает взгялнуть на таблицу, как на отдельны элемент – создаем один элемент вместо трех
В качестве входных параметров в конструктор передаем только локаторы для сторок и колонок таблицы, причем локаторы относительно ТАБЛИЦЫ ВЦЕЛОМ
Если у нас таблицы посложнее и содержит еще и хедеры и футоры – локаторы для них также можно указывать в конструкторе – конструкторов для построения таблицы много.
Реализованы Локаторы с шаблонами, куда будет подставлен индеск колоки или строки
А если таблица реализована стандартным образом – еще проще – просто создаем элемент через аннотицию FindBy
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
К счастью нет! Благодаря Интерфейсам используемым в JDI вам достаточно лишь подключить другой пакет (к примеру mobile) и все ваши тесты смогут работать с мобильными устройствами. Поменять придется лишь то что действительно отличается.
Вот к примеру Кнопка. Кнопки бывают и в Web приложениях и в Мобильных и на Desktop. Есть ли какая-то разница между ними? С точки зрения реализации конечно да, но с точки зрения пользователя никакой. На кнопку просто можно нажать. Ну возможно у нее еще есть название.
JDI смотрит на все элементы с точки зрения пользовательских действий именно по этому мы используем интерфейсы. Где же конкретно используются наши элементы это уже вопрос их реализации. Можно использовать Selenium, а можно Appium, можно даже написать имплементацию на JavaScript
концептуально это неверно
JDI предоставляет набор интерфейсов для работы с каждым UIObjects
Для кнопки есть только click () и getText(), реализация которых зависит уже от типа прилжения и драйвера.
Соответственно, интерфейсы помогают нам взглянуть на элементы с точки зрения пользователя, чего мы и добаваемся при написаниее тестов
но есть проблемы и посложнее