Как настроить selenium webdriver

Начинаем работать с Selenium в Python

Введение

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

Автоматизация взаимодействия пользователя с веб-браузером часто используется как для тестирования в ходе процесса разработки ( development ), так и на стадии завершении работы над проектом ( production ). Также автоматизация управления веб-браузером может использоваться для извлечения данных из открытых источников сети Интернет для последующего анализа и обработки полученных данных.

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

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

Он поддерживает многие языки, такие как C #, Java, Perl, PHP и Ruby. Однако в нашей статье изложены материалы по его использованию с Python в Windows.

Что такое Selenium?

Selenium — отличный инструмент, который позволяет разработчикам эмулировать (имитировать) действия в браузере пользователя с использованием всего лишь нескольких строк кода. Используя инструменты, которые он предлагает, очень легко реализуется загрузка содержимого веб-страниц в браузер, а также имитация взаимодействия пользователя с её элементами и даже с учетом особенностей человеческого поведения.

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

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

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

  • нажатие кнопок;
  • ввод текста;
  • извлечение текста;
  • доступ к данным в cookie файлах;
  • нажатие клавиш.

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

Прежде чем мы начнем, нам необходимо проделать следующие операции:

  • Установка браузер Google Chrome на свой компьютер — далее мы будем имитировать действия пользователя в браузере Google Chrome. Хотя вы конечно же можете использовать Selenium в других браузерах, но в этой статье я буду описывать способы работы с Google Chrome.
  • Загрузите chromedriver.exe , в дальнейшем вам потребуется указать путь к этому исполняемому файлу на вашем компьютере.
  • Установите пакет selenium package запустив в консоли команду pip install selenium .

Основы работы с Selenium

Отлично, теперь мы готовы начать работать с Selenium. Попробуем запустить браузер и перейти по заданному URL:

Запуск этого кода на исполнение откроет Google Chrome и перенаправит его по адресу https://www.google.com . Как видно из листинга кода подключение к веб-странице осуществляется с помощью метода get(URL) объекта driver .

driver — это экземпляр класса WebDriver импортируемого из пакета Selenium , который мы далее будем использовать для управлению действиями браузера, например:

Код выше выведет в консоли исходный HTML код всего содержимого нашей страницы, полученного с помощью метода get(URL) . Поэтому если вам в дальнейшем необходимо будет просмотреть содержимое запрашиваемой страницы, то этот прием вам пригодится.

Положение элементов на странице

Как правило, вам совсем не нужно всё содержимое страницы, а лишь только её отдельных частей (HTML элементов). Поэтому вначале необходимо определить местоположение нужного нам HTML элемента на странице, для этого можно использовать инструмент Inspect Element из состава web developer tools браузера Google Chrome.

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

    Щелкните правой кнопкой мыши на элементе

Выберите в контекстном меню «Просмотреть код»

  • В появившемся новом окне вы увидите выделенный HTML код нужного вам элемента, из которого можно получить нужный вам идентификатор. Это может быть значение атрибута класса class или id элемента.
  • Как ещё можно использовать этот инструмент для поиска элементов на странице, вы можете прочитать на официальном сайте.

    Отметим, что полученный таким способом идентификатор должен однозначно указывать на нужный нам HTML элемент. Если в качестве идентификатор мы указываем его уникальный на целевой странице id , то наш код, обрабатывающий содержимое элемента, будет работать так, как мы хотим. Но в случае если в качестве идентификатора мы будем использовать значение других атрибутов тега, например class , то полученные результаты могут отличаться от ожидаемых.

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

    Получение элементов и их содержимого по id

    Если знаете id нужного вам элемента, то его со всем содержимым, а также вложенными элементами, можно легко получить следующим способом:

    Получение элементов по значению атрибута name

    Аналогично предыдущему примеру:

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

    И снова, аналогично предыдущему примеру кода:

    Получение элементов по имени тега HTML

    Так же вы можете получить элементы страницы по имени тега:

    В этом случае переменная links получает все элементы с тегом a , находящиеся на загруженной странице .

    Получение элементов с использованием синктаксиса XPath

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

    Для решения подобных задач были разработаны другие способы получения содержимого конкретного элемента на странице, например, с использованием синтаксиса XPath (языка запросов к элементам XML документа). С использованием XPath вы сможете находить элементы на странице более быстрым и эффективным способом:

    Переменная tag_list теперь содержит все элементы страницы с тегом tag у которого задан атрибут attr с установленным значением val :

    Теперь вы можете перебирать итерируемый объект tag_list и обрабатывать по отдельности его элементы, имеющие тип WebElement , описанный в пакете Selenium.

    Вы можете больше прочитать об использовании XPath в Selenium по ссылке .

    Selenium WebElement

    Класс WebElement , определенный в Selenium, по сути является представлением обычного HTML элемента. С ним вы можете выполнять все те же операции, как и с обычными HTML элементами на странице, подобно тому, как взаимодействует с ними конечный пользователь.

    Перечислим основные из них:

    • Доступ к простым свойствам элемента, таким как текст внутри: element.text
    • Доступ к родительским элементам, которые также имеют тип WebElement : element.parent
    • Доступ к атрибутам элементов, таким как href тега a : element.get_attribute(‘href’)
    • Поиск в содержимом элемента (так же, как в глобальном корневом объекте driver )
    • Кликать по нему (нажимать на нем левой кнопкой мыши): element.click()
    • Пользовательский ввод в элемент текстовой информации, если это возможно для его типа: element.send_keys(‘Input Text’)
    Читайте также:  Как настроить кодовый навесной замок для чемодана

    Selenium WebDriver

    Объект WebDriver схож с WebElement , однако их основным отличием является контекст его применения. Таким образом, область действия последнего — это сам элемент, а первого — вся страница в целом.

    С помощью объекта WebDriver вы можете осуществлять множество операций, а точнее практически проделывать все действия, что может сделать человек с обычным браузером.

    Вот некоторые полезные его полезные возможности:

    • Запуск на странице произвольных JavaScript скриптов: driver.execute_script(«script»)
    • Сохранять скриншоты страницы: driver.save_screenshot(‘image.png’)
    • Включить режим работы браузера в режиме «headless» ( Как работает Headless Chrome ). Таким образом браузер экономит время, исключая этап рендеринга страницы:

    Обратите внимание на то, что в методе set_window_size указывается размер окна браузера, он устанавливается равным (1440, 900) . Это важно для предотвращения ситуаций, связанных с присутствием на странице элементов, которые могут не загружаются в «headless» режиме (загрузка которых зависит от текущего размера окна браузера, а точнее размера экрана устройства).

    Вы можете изменять разрешение или размер окна браузера на любое другое значение, но вы должны помнить, что в этом случае для текущего экземпляра объекта driver это значение будет установлено по умолчанию.

    Вам может понадобиться добавить или удалить файлы cookie браузера, с заданным содержимым:

    Этот код предписывает браузеру создать файлы cookie с заданными значениями атрибутов some_attr и some_other_attr . Это может быть использовано, в случае если вам необходимо добавить в файлы cookie данные аутентификации или другую информацию. Напомним, что содержимое файла cookie имеет формат схожий с синтаксисом словаря dict .

    Также очень легко получить cookie из текущей сессии браузера:

    Приведенный выше код выведет в консоли содержимое каждого файла cookie из текущей сессии браузера.

    Изменение HTML кода страницы

    Если вам понадобилось изменить свойства определенного HTML элемента страницы, например, добавить или удалить его атрибуты и т. д. То как уже упоминалось ранее, вы можете использовать объект Selenium WebDriver для выполнения произвольного JavaScript кода на загруженной странице. Таким образом с помощью JavaScript можно легко изменять любые свойства элементов страницы:

    Здесь element — это элемент страницы, полученный любым из описанных выше способов. attr соответственно его атрибут, который нужно изменить (или добавить), а value — его значение.

    Загрузка файлов с использованием ссылок на скачивание

    Допустим вам необходимо загрузить какой-либо файл с веб-сайта. Следующий код поможет это осуществить:

    Также вы можете указать путь к папке для сохранения скаченного файла, определив значение свойства download.default_directory , например, так — path\to\directory .

    Нажатие клавиш клавиатуры

    Этот код эмулирует нажатие клавиши «стрелка вниз» ( Keys.ARROW_DOWN ) 3 раза. После каждого нажатия action.send_keys(Keys.ARROW_DOWN) программа ожидает небольшой промежуток времени (0.1 сек.).

    Этот прием рекомендуется использовать для того, чтобы убедиться, что в текущем окне браузера зарегистрированы обработчики событий нажимаемых клавиш. Также этот способ применяется для исключения ситуаций, когда команды нажатия клавиш могут «потеряться» в процессе взаимодействия с браузером (например, страница не успела загрузится и соответствующие обработчики событий элементов не были назначены), то есть они просто не будут зарегистрированы и исполнены в последствии.

    Таким образом, объект Keys позволяет эмулировать нажатия любых клавиш вашей клавиатурой. Что позволяет, например, использовать событие Keys.TAB (нажатие клавиши Tab ) для перемещения фокуса между элементами ввода в формах (касается элементов, способных принимать фокус для ввода с клавиатуры). Или эмулировать нажатие клавиш Keys.RETURN и Keys.SPACE , что облегчает взаимодействие с элементами ввода данных, а также имитирует поведение человека.

    Нажатия на кнопки и другие HTML элементы

    Как уже говорилось выше, вы можете использовать эмуляцию событий нажатия клавиши Tab для перемещения между элементами на странице, клавиши Space (пробел) для заполнения checkbox (флажков), а также клавиш со стрелками для перемещения между пунктами выпадающего меню.

    Но более простым является следующий способ реализации взаимодействия с HTML элементами, такими как button или элементами option выпадающего списка значений select . Способ включает в себя выполнение следующих действий: поиск и получение конкретного элемента на странице с помощью объекта webdriver , а затем инициирование клика по нему:

    Ввод данных в элементы ввода форм

    Вы также можете эмулировать нажатия клавиш внутри HTML элементов ввода в формы текстовой информации:

    Таким способом, например, вы можете поместить текстовую информацию в элемент text или textarea .

    Кстати, код выше использует сочетание клавиш ( CTRL + A ) для выделения всего текста внутри элемента element . А следующая строка заменяет выделенный текст заданным произвольным строковым значением из переменной value .

    И так, для эмуляции нажатия сочетаний клавиш передавайте их через параметры метода send_keys .

    Скроллинг

    Иногда некоторые части страницы загружаются только после ее прокрутки вниз. Например, канал в Instagram или любая другая страница с “бесконечной” прокруткой (с использованием AJAX). C помощью приведенного ниже скрипта JavaScript можно прокрутить страницу браузера вниз:

    Приведенный выше код использует команды языка JavaScript для прокрутки до нижней части страницы, теперь вы можете использовать метод driver.page_source и получить полное содержимое страницы.

    Заключение

    Selenium — один из наиболее широко используемых инструментов для автоматизации работы с веб-браузером, который предлагает множество функций и возможностей для просмотра и сбора информации. В основном он используется для автоматизации тестирования веб-приложений в ходе разработки, хотя его также можно эффективно использовать в качестве инструмента для сбора информации ( web scraping ).

    Соблюдайте законы, если вы осуществляете сбор контента из ресурсов Интернет. Не нарушайте авторские права 😉

    Источник

    Selenium 2.0 — WebDriver. Впечатления, проблемы и советы по использованию

    Введение

    Последние три месяца мне пришлось работать с Selenium 2.0 (WebDriver).
    В данной статье я опишу свои впечатления, мысли и опыт, который я приобрел.
    Так же я опишу основные действия, которые чаще всего вызывают проблемы и покажу наиболее удачные решения, которые я смог реализовать для них. Возможно есть более правильные подходы — буду рад если оставите их в комментариях.

    Коротко о Selenium

    Библиотека Selenium позволяет производить тестирование графических web интерфейсов. Ее принцип — максимально точно симулировать деятельность пользователя. По сути — это написание бота, который бегает по страничкам сайта, производит действия и проверяет ожидаемый результат. Selenium 2.0 реализует сообщения с браузерами посредством специальных драйверов. В отличие от Selenium 1.0 он не использует JavaScript, а сообщается напрямую с API браузеров.

    Что у меня получилось реализовать

    Получилось написать тесты на основе JUnit и Selenium 2.0, объединенные в одно приложение. Данное приложение может выполняться на Selenium Grid — это сеть, во главе с Selenium Hub, который принимает и распределяет поступившие задачи тестирования по своим Selenium Nodes. На различных Selenium Nodes могут быть настроены любые требуемые браузеры. Используемые драйвера — родные драйвера для каждого браузера.

    Часть первая. Впечатления

    Разное поведение в разных браузерах

    Под браузерами я понимаю основные: Firefox, Google Chrome, Opera, Safari, IE8, IE9
    Чтобы один и тот же код срабатывал одинаково успешно в разных браузерах, нужно потратить огромное количество времени. Порой нужна железная воля, чтобы не бросить это гиблое дело. В этом плане самые послушные браузеры — Firefox и Google Chrome. По моему личному опыту — жизненно необходимо, чтобы тест мог менять поведение в нужных местах в зависимости от того, какой браузер в данный момент используется. Т.е. он должен иметь информацию о среде, в которой он проходит.

    Совет:
    Старайся не использовать в тестах объект webDriver напрямую! Создай методы-обертки вокруг основных необходимых тебе методов. Проще менять поведение в одном месте, чем повсеместно в коде всех тестов.

    Читайте также:  Инфолинк телевидение базовые как настроить
    Selenium 2.0 — сырой продукт

    Читая множество постов на Stackoverflow в поисках best practices или просто решения проблемы, постоянно натыкаешься на workaround’ы. Причин несколько: различия в работе драйверов браузеров, не выполнение драйверами контракта требуемого функционала, наличие ошибок в версиях, наличие прямой зависимости версии браузера от версии драйвера. Порой он способен просто ронять тест на голом месте (с точки зрения пользователя API) — элемент есть, но он его не видит. По моему опыту много плавающих ошибок, которые намеренно воспроизводятся только через раз при абсолютно схожих условиях и действиях. С Firefox вообще иногда начинается лихорадка и браузер может просто закрыться с примерно таким сообщением: Error communicating with the remote browser. It may have died. Крайне тяжело найти причину, если она вообще доступна пользователю Selenium. По этому порой ситуация беспомощная — просто не работает функционал.

    Совет:
    Такой прескорбный расклад дел заставляет менять поведение тест-кейса. К счастью, одни и те же вещи в GUI клиентах зачастую можно выполнить либо разной последовательностью, либо разным способом. В случае если ты не смог найти решения погуглив — попытайся подобрать другое поведение, которое будет успешно отработано. Не замыкайся на конкретном действии, если на то нет особой необходимости.

    Тесты Selenium — зависимые тесты

    Это означает, что если дополнительно не позаботиться, действия одного теста могут влиять на результат другого теста. Это вполне очевидно, пользователь в том числе изменяет данные в процессе своей активности. Тестируя подобный функционал, вы вынуждено будете изменять начальные данные. Если от этого зависят другие тесты и вы не вернули данные в исходное состояние — или не смогли этого сделать по причине того, что тест прервался ошибкой — другой тест может тоже сломаться. Этакий принцип домино. Когда впервые осознаешь это, становится очень больно. Руки опускаются…

    Совет:
    Если есть возможность воспроизводить условия теста независимо, т.е. есть прямой доступ к тестируемому приложению и нет преград для разворачивания исходных тестовых данных — вам повезло, изолируйте свои тесты подобным образом — подготавливая данные до теста и очищая их после. К примеру, в восстановлении данных в БД может помочь инструмент Liquibase.
    Скорей всего такой возможности нет. В этом случае выход один — помимо самих тестируемых действий, описывать с помощью Selenium так же и действия по их «откатке». Т.е. если пользователь удалил сущность — в конце теста ее необходимо заново создать или загрузить.
    Это грешный путь. Так как подобные действия тоже уязвимы и тоже могут оборваться ошибкой, не выполнив своего предназначения.

    Тесты Selenium — медленные тесты

    Нужно быть готовым, что последовательный прогон большого набора тестов для всех браузеров может занимать большое количество времени, измеряемое в часах (от 30 минут — до 2-3 часов). Это делает все что я описал выше трагедиями и порой похоже на издевательство. Причина в том, что тесты сильно насыщены различными ожиданиями, поиском элементов и прочими медленными действиями.

    Совет:
    Тестируйте только то, что действительно надо тестировать. Из всех возможных работающих вариантов реализации одного и того же действия — выбирайте наиболее быстрый.

    Selenium IDE — не помощник

    Selenium IDE — специальный плагин для Firefox, который способен записать все выполняемые действия пользователя в виде скриптов. Там же есть возможность экспорта составленных скриптов в различные языки и в два формата: Selenium 1.0 (RC) и Selenium 2.0 (WebDriver).
    В большинстве случаев бесполезная вещь.

    Проблемы:

    • генерируемый код — не читаем
    • генерируемый код — не рабочий, в случае сложного интерфейса, в силу всех вышеописанных особенностей
    • в случае если id элементов (div, table, span, input) автоматически генерируемые — предлагаемые на выбор XPath указатели не подходят
    • большое количество тестов (5 тестов уже достаточно) заставит встать на правильный путь джедая и составить собственную реализацию часто выполняемых действий — и далее использовать их как унаследованный метод. Единожды описанный и отточенный. Как только образуется такой набор методов — польза от IDE резко падает. Ей нельзя указать использовать свои методы — среда разработки будет генерить свои собственные неработающие неидеальные шаблоны. Просматривать потом сгенерированный код и замещать все необходимые места со временем сводится к полному переписыванию этого кода. Эту же мысль можно продолжить единым «справочником»-перечнем всех XPath локаторов ключевых элементов. Как только все подобные локаторы вынесены в константы или в отдельный справочник — проще становится использовать их, чем в очередной раз проверять — что там нагенерила среда разработки

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

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

    Часть вторая. Практические решения возникающих проблем (Java)

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

    Получение элемента (findElement)

    Проблема:
    WebDriver предоставляет механизм для поиска и получения сущности WebElement:

    Теоретически, на поведение этого метода влияет параметр ‘implicit wait’ который можно указать при построении самого webdriver. К примеру, так:

    Опять таки, теоретически, это должно явно заставлять webdriver искать элемент в течении указанного времени и ждать либо пока не появится искомый элемент, либо пока не закончится указанный таймаут. Кстати, данный таймаут судя по всему можно выставлять только единожды.
    На практике, происходит нечто странное. Пауза выдерживается, но есть внутреннее ощущение, что поиск если и идет по DOM модели, то обновления этой DOM модели не происходит. Для некоторых браузеров получается другая ситуация — элемент уже есть в DOM модели, но еще не отрисовался или отрисовался частично (Google Chrome). WebDriver возвращает найденный наполовину отрисованный элемент и событие click попадает в еще неотрисованные координаты. Метод isDisplayed() в таких случаях не помогает. В любом случае, итог у меня всегда один — элемент визуально уже гарантированно появился, а webDriver его по-прежнему не обнаруживает.

    Решение:
    Делать грубую паузу. Для того, чтобы не умножать количество строк кода вдвое, рекомендую сделать собственную реализацию метода findElement();
    Как я писал выше — для более эффективной работы — тест должен знать какой браузер в данный момент запущен. Для Firefox по моим наблюдениям такой задержки не требуется.
    Так же можно воспользоваться инструментом WebDriverWait. Описывать здесь такой вариант не буду, так как я решил остановиться на спячке потока, мне этого достаточно — поэтому проверенного варианта нет. Но там все довольно просто.
    В дальнейшем использовать во всех тестах только этот метод и не использовать webDriver.findElement() напрямую.

    Получение элементов (findElements)

    Проблема и решение аналогичны поиску одного элемента.

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

    Если необходимо проверить, что элемент отсутствует — рекомендуется использовать конструкцию:

    Вот рекомендация из JavaDocs:

    findElement should not be used to look for non-present elements, use findElements(By) and assert zero length response instead.

    Скачивание картинки или файла

    Проблема:
    Есть желание протестировать скачивание файла, что скачанный файл соответствует ожидаемому, а если это картинка — она действительно доступна по указанной ссылке.

    Рассуждения:
    В 99% случаев вам это не нужно. Еще раз задайтесь вопросом, что вы хотите протестировать? Я практически уверен, что вам достаточно знать, что загрузка доступна. Что ссылка активна, кнопка загрузки enabled и статус ответа после начала скачки равен 200. У вас нет задачи тестировать браузер и его процесс скачивания.
    Так же, если тесты проходят на Selenium Grid — то у вас не получится скачать файл и проверить после этого его местонахождение. Файл скачается на Selenium Node, а проверять вы его будете на Selenium Hub. Это разные хосты, по крайней мере в обычной практике.

    Читайте также:  Шкода суперб не работает круиз контроль

    Решение:
    Решение заключается в том, чтобы выполнить обыкновенный HTTP запрос по ссылке ведущей к файлу на сервере, либо по ссылке, по которой сервер должен вернуть такой файл. Если статус полученного от сервера ответа 200 — ссылка верная, файл существует. Все остальные варианты я рассматриваю как недоступность скачивания файла. Так как зачастую запросы должны иметь при себе авторизованные cookies — такие cookies необходимо импортировать из webDriver.
    Если одного статуса недостаточно, ничто не мешает вам считать весь InputStream из HttpEntity и далее сравнить его содержимое с эталонным, будь то MD5 сумма или какой-нибудь другой способ.

    Очистка значения поля input

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

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

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

    Решение:
    Есть несколько основных способов.
    Первый способ — моделировать действие «выделить все» и сразу после этого выслать новое значение:

    Но данное решение у меня работает не на всех браузерах и не всегда.

    Второй способ — выслать количество символов backspace, равное длине старого значения. Данное решение некрасиво, но оно эффективно и работает гарантированно во всех браузерах.
    Ниже я публикую вариант, которым пользуюсь сам. В нем есть отдельное рассмотрение ситуации, когда браузер — IE, а input с типом file.
    Это особенная ситуация. При выполнении команды sendKeys к такому элементу IE заменит старое значение, новым, а не допишет его в конец. Поэтому делать очистку такого поля смысла нет. Более того, подобная попытка приведет к ошибке. Либо по причине несуществующего файла (так как будет попытка найти файл по пустому пути), либо по причине попытки найти файл по пути, строковое значение которого будет равно символу backspace.

    Загрузка файла на сервер

    Проблема:
    Необходимо загрузить файл на сервер, используя стандартные элементы HTML:

    Решение:
    Я рекомендую просто взять и вынести себе это в отдельный универсальный метод и использовать его каждый раз когда нужно что-либо загрузить через такую форму.

    Исключение:
    Safari Driver полностью не поддерживает загрузку файла, т.к. насколько я понял, он javascript-based. Появляющееся окно с выбором файла ставит его в тупиковое положение. Такие сценарии нужно либо избегать, либо добиваться результата другим способом — создавать собственный HTTP запрос или подкладывать данные напрямую на стороне сервера, если такая возможность имеется.

    Действия с элементами внутри iframe

    Проблема:
    Если требуемый элемент находится внутри iframe — он не доступен из дефолтного контекста. Вы не сможете обнаружить его в DOM модели и webDriver будет бросать исключение NoSuchElementException.

    Решение:
    Перед тем как взаимодействовать с этим элементом, необходимо переключить webDriver на контекст iframe элемента. Как я понимаю, это связано с тем, что контекст страницы и контекст iframe на этой странице — это две разных DOM модели.

    IE8. Проблема с XPath

    Проблема:
    IE8, в свойственной ему эксцентричной манере, бывает неверно интерпретирует указатели элементов (By.id, By.xpath и другие).
    У меня возникали ситуации когда он игнорировал уточнение для искомого элемента указывающее на его атрибут class.
    К примеру IEDriver отказывался различать два разных элемента, найденных по таким локаторам и выводил элементы подходящие обоим вариантам:

    Понять в каких ситуациях у него возникают проблемы мне не удалось.
    Абсолютно идентичная ситуация происходила с прямым указанием id элемента. WebDriver делает вид что его не существует.

    Решение:
    Если у IEDriver возникает галлюциногенное заблуждение в поиске элемента (но не у остальных драйверов и браузеров) — лучший выход — изменить XPath. Благо возможных вариантов благодаря гибкости XPath всегда много.

    IE8. элемент недоступен для нажатия

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

    Решение:
    Необходимо выполнить прокрутку. Единственный найденный мной и работающий способ — воспользоваться помощью javascript. На самом деле, WebDriver имеет специальный механизм, призванный помочь с прокруткой до требуемого элемента:

    Но он не сработает в случае с IE8.

    Где container — это id элемента, который необходимо прокрутить. Т.е. в нашем случае — div или table, внутри которого располагается элемент. Как можно понять, данный скрипт выполнит прокрутку по горизонтали.

    Firefox may die

    Проблема:
    Firefox Driver мог быть примером для остальных драйверов, но у него есть один очень неприятный недостаток. Как можно понять по коментариям к разным версиям WebDriver’a — этот недостаток, то исчезает, то вновь появляется от версии к версии.
    Суть в том, что иногда на Firefox находит бес и он вдруг, без каких либо внешних, как это кажется, воздействий и изменений, начинает падать на ровном месте.
    Выглядит это примерно так: вы наблюдаете, как в окне браузера успешно выполняется уже отлаженный до блеска тест. И тут на абсолютно мелочном шаге или действии окно браузера просто исчезает. В логах вы обнаруживаете такую запись: Error communicating with the remote browser. It may have died. Все, больше никакой информации вы не найдете.

    Решение:
    Это регрессивная ошибка и гарантированного лекарства быть не может. Заключается она в том, что между браузером и драйвером возникает непонимание. К примеру по причине того, что ваш браузер обновился, вы не обратили на это внимание и продолжаете использовать старый WebDriver. Между Firefox и его драйвером есть, как я это ощутил, зависимость. Она не абсолютная, т.е. не всякий раз когда Firefox обновился, нужно бежать обновлять вебдрайвер тоже. Но первое что я посоветую сделать — погуглите, какая версия вебдрайвера наиболее подходит под вашу версию Firefox.
    В случае с Firefox 19 мне помогло обновить stand-alone-server селениума до версии 2.30.0.

    Заключение

    Я благодарен за такой опыт и за возможность поработать с этим фреймворком. За последние месяцы XPath для меня стал как родной язык, наверное скоро переписываться на нем смогу. Судя по всему, я получил достаточно много знаний о том, как использовать Selenium и как это делать эффективно.

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

    Поэтому, если вы решите писать серьезные тесты на этой платформе — подготовьтесь психологически.

    Источник

    Оцените статью