Обзор Примеров Кода для Автоматизированного Тестирования с Selenium WebDriver на Python: От Базы до Продвинутых Техник

Автоматизированное тестирование стало неотъемлемой частью современной разработки программного обеспечения. Selenium WebDriver, в сочетании с Python, предоставляет мощный и гибкий инструмент для создания надежных автотестов selenium. В этой статье мы сосредоточимся на практических примерах selenium код для тестов, охватывающих широкий спектр задач — от базовых операций до сложных сценариев тестирования.

В этом обзоре вы найдете:

Примеры selenium webdriver примеры python для инициализации браузера и навигации.

Фрагменты кода для эффективного поиска элементов с использованием различных selenium locators examples, включая CSS-селекторы и XPath.

Инструкции по взаимодействию с элементами: ввод текста, клики, выбор опций.

Рекомендации по использованию стратегий ожидания (selenium wait examples) для обработки динамического контента.

Примеры использования Selenium Actions Class для эмуляции сложных действий пользователя.

Интеграцию с pytest для структурирования и организации ваших автотестов selenium.

Основы масштабирования тестирования с использованием Selenium Grid (примеры seleniun grid).

Наша цель — предоставить вам готовые к использованию примеры selenium автоматизации, которые помогут вам быстро освоить Selenium WebDriver и начать создавать эффективные selenium код для тестирования. Независимо от вашего уровня опыта, вы найдете полезные и практичные примеры selenium код для автоматизированного тестирования с использованием selenium, которые можно адаптировать под свои нужды.

Основы Selenium WebDriver с Python

Selenium WebDriver – мощный инструмент для автоматизации тестирования веб-приложений. Python, благодаря своему лаконичному синтаксису и широкому набору библиотек, является отличным выбором для работы с Selenium. Рассмотрим основные шаги и примеры кода для начала работы.

Установка и настройка Selenium WebDriver

Установка Selenium: Используйте pip для установки библиотеки Selenium: pip install selenium

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

Ваш первый тест: запуск браузера и навигация

from selenium import webdriver
from selenium.webdriver.chrome.service import Service

# Укажите путь к драйверу Chrome
webdriver_service = Service(executable_path='/путь/к/chromedriver')

# Создаем экземпляр драйвера Chrome
driver = webdriver.Chrome(service=webdriver_service)

# Открываем веб-страницу
driver.get("https://www.example.com")

# Закрываем браузер
driver.quit()

Этот код открывает браузер Chrome, переходит на сайт example.com и затем закрывает браузер. Обязательно замените /путь/к/chromedriver на актуальный путь к вашему драйверу.

Поиск элементов: базовые локаторы (ID, Name, Class Name)

Для взаимодействия с элементами на странице, необходимо их найти. Selenium предоставляет различные локаторы:

ID: driver.find_element(By.ID, "element_id")

Name: driver.find_element(By.NAME, "element_name")

Class Name: driver.find_element(By.CLASS_NAME, "element_class")

Пример:

from selenium.webdriver.common.by import By

# Поиск элемента по ID
element = driver.find_element(By.ID, "search_input")

# Ввод текста в элемент
element.send_keys("Selenium Python")

В этом примере мы находим текстовое поле с ID search_input и вводим в него текст "Selenium Python".

Установка и настройка Selenium WebDriver

После установки selenium (через pip install selenium), необходимо настроить драйверы для тех браузеров, которые вы планируете автоматизировать. Selenium WebDriver использует отдельные исполняемые файлы (драйверы) для взаимодействия с каждым браузером.

Скачайте драйвер:

ChromeDriver для Google Chrome: https://chromedriver.chromium.org/downloads

GeckoDriver для Mozilla Firefox: https://github.com/mozilla/geckodriver/releases

EdgeDriver для Microsoft Edge: https://developer.microsoft.com/en-us/microsoft-edge/tools/webdriver/

Разместите драйвер: Рекомендуется поместить исполняемый файл драйвера в каталог, который добавлен в системную переменную PATH. Это позволит Selenium находить драйвер автоматически. Альтернативно, можно указать путь к драйверу непосредственно при создании экземпляра webdriver.

from selenium import webdriver

# Пример указания пути к драйверу (не рекомендуется, если драйвер в PATH)
# driver = webdriver.Chrome(executable_path='/path/to/chromedriver')

# Если драйвер находится в PATH, достаточно:
driver = webdriver.Chrome()
driver.get('https://www.example.com')
driver.quit()

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

Ваш первый тест: запуск браузера и навигация

После успешной установки и настройки Selenium WebDriver, давайте напишем наш первый автотест selenium на Python. Этот простой пример покажет, как запустить браузер, перейти по URL и закрыть его.

from selenium import webdriver
from selenium.webdriver.chrome.service import Service

# Укажите путь к исполняемому файлу ChromeDriver
webdriver_path = '/путь/к/chromedriver'

# Создаем экземпляр Chrome WebDriver с указанием пути к драйверу
service = Service(executable_path=webdriver_path)
driver = webdriver.Chrome(service=service)

# Переходим по указанному URL
driver.get("https://www.example.com")

# Закрываем браузер
driver.quit()

Замените /путь/к/chromedriver на фактический путь к исполняемому файлу ChromeDriver на вашей системе.

Строка driver.get("https://www.example.com") открывает указанный сайт в браузере.

Метод driver.quit() закрывает все окна браузера и завершает сессию WebDriver. Использование driver.close() закроет текущее окно, оставив сессию WebDriver активной, что может быть полезно при работе с несколькими окнами.

Этот простой selenium код для тестов демонстрирует базовый workflow автоматизации. В следующих разделах мы рассмотрим, как искать элементы на странице и взаимодействовать с ними.

Поиск элементов: базовые локаторы (ID, Name, Class Name)

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

ID: Самый предпочтительный способ, если у элемента есть уникальный ID. Пример кода:

element = driver.find_element(By.ID, "login_button")

Name: Используется, когда у элемента есть атрибут name. Часто применяется для полей ввода:

element = driver.find_element(By.NAME, "username")
element.send_keys("your_username")

Class Name: Применяется, когда нужно найти элементы с определенным классом CSS. Стоит учитывать, что class name не всегда уникален:

elements = driver.find_elements(By.CLASS_NAME, "error_message")
for element in elements:
    print(element.text)

Важно: find_element возвращает первый найденный элемент, а find_elements возвращает список всех подходящих элементов.

Для использования этих локаторов, необходимо импортировать By из selenium.webdriver.common.by:

from selenium.webdriver.common.by import By

Пример комбинированного использования:

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

from selenium import webdriver
from selenium.webdriver.common.by import By

driver = webdriver.Chrome() # Или другой предпочитаемый браузер
driver.get("ваша_страница_с_формой")

username_field = driver.find_element(By.NAME, "username")
username_field.send_keys("test_user")

password_field = driver.find_element(By.NAME, "password")
password_field.send_keys("password123")

login_button = driver.find_element(By.ID, "login_button")
login_button.click()

# driver.quit()

Продвинутые Локаторы и Взаимодействие с Элементами

CSS-селекторы и XPath для сложных элементов

Когда базовых локаторов недостаточно, на помощь приходят CSS-селекторы и XPath. Они позволяют находить элементы, опираясь на их атрибуты, структуру DOM или взаимоотношения с другими элементами.

CSS-селекторы: Ориентированы на стилизацию, но отлично подходят для поиска элементов по классам, атрибутам и их значениям.

element = driver.find_element(By.CSS_SELECTOR, "input[type='text'][name='username']")

Этот код найдет элемент <input> с типом text и именем username.

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

element = driver.find_element(By.XPATH, "//div[@id='login-form']/input[@name='password']")

Этот код найдет элемент <input> с именем password внутри элемента <div> с идентификатором login-form.

Кликаем, вводим текст, выбираем опции: основные методы взаимодействия

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

click(): Кликает на элемент.

element.click()

send_keys(): Вводит текст в элемент.

element.send_keys("my_username")

clear(): Очищает содержимое элемента (например, текстового поля).

element.clear()

Работа с выпадающими списками и чекбоксами

Выпадающие списки и чекбоксы требуют особого подхода.

Выпадающие списки: Используйте класс Select из selenium.webdriver.support.ui для выбора опций.

from selenium.webdriver.support.ui import Select

dropdown = Select(driver.find_element(By.ID, "my_dropdown"))
dropdown.select_by_value("option1") # Выбор по значению
dropdown.select_by_visible_text("Option 2") # Выбор по видимому тексту
dropdown.select_by_index(3) # Выбор по индексу

Чекбоксы: Для установки или снятия отметки используйте метод click().

checkbox = driver.find_element(By.ID, "my_checkbox")
if not checkbox.is_selected():
    checkbox.click()

CSS-селекторы и XPath для сложных элементов

XPath и CSS-селекторы предоставляют мощные инструменты для поиска элементов, особенно когда ID, Name или Class Name не подходят. Они позволяют точно определять элементы на странице, основываясь на их атрибутах, иерархии и взаимосвязях.

CSS-селекторы: Отлично подходят для выбора элементов по классам, атрибутам и псевдоклассам. Например, element.find_element(By.CSS_SELECTOR, "input[type='submit']") найдет кнопку отправки формы.

XPath: Предоставляет гибкий язык запросов для навигации по DOM-дереву. element.find_element(By.XPATH, "//div[@class='myClass']/a") найдет ссылку внутри div с классом myClass.

Пример использования XPath для поиска элемента по тексту:

element = driver.find_element(By.XPATH, "//*[contains(text(), 'Текст элемента')] ")

В этом примере contains(text(), 'Текст элемента') позволяет найти элементы, содержащие определенный текст. Это может быть полезно, когда текст элемента динамически меняется, но содержит постоянную часть.

Пример использования CSS-селектора для поиска элемента по атрибуту и значению:

element = driver.find_element(By.CSS_SELECTOR, "a[href='https://example.com']")

Этот селектор найдет все ссылки (теги <a>) с атрибутом href, равным "https://example.com".

Кликаем, вводим текст, выбираем опции: основные методы взаимодействия

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

Клик по элементу: Используйте метод click() для нажатия на кнопки, ссылки и другие интерактивные элементы.

element = driver.find_element(By.ID, "submit_button")
element.click()

Ввод текста: Для заполнения текстовых полей используйте метод send_keys().

element = driver.find_element(By.NAME, "username")
element.send_keys("your_username")

Выбор опций в выпадающем списке: Для взаимодействия с <select> элементами используйте класс Select из selenium.webdriver.support.ui.

from selenium.webdriver.support.ui import Select

select = Select(driver.find_element(By.ID, "dropdown"))
select.select_by_visible_text("Option 1") # Выбор по видимому тексту
select.select_by_value("1") # Выбор по значению атрибута value
select.select_by_index(1) # Выбор по индексу (начиная с 0)

Работа с чекбоксами и радиокнопками: Клик по элементу input с типом checkbox или radio позволяет установить или снять выделение.

checkbox = driver.find_element(By.ID, "agree_checkbox")
checkbox.click()

Чтобы проверить, выбран ли чекбокс, используйте атрибут is_selected():

is_checked = checkbox.is_selected()
print(f"Чекбокс выбран: {is_checked}")

Работа с выпадающими списками и чекбоксами

Для работы с выпадающими списками (select) в Selenium, используется класс Select из модуля selenium.webdriver.support.ui. Он предоставляет удобные методы для выбора опций по тексту, индексу или значению атрибута value.

Пример:

from selenium.webdriver.support.ui import Select

select_element = Select(driver.find_element(By.ID, "dropdown"))
select_element.select_by_visible_text("Option 1")
select_element.select_by_index(2)
select_element.select_by_value("value3")

Для работы с чекбоксами, достаточно определить их состояние (checked) и, при необходимости, изменить его.

Пример:

checkbox = driver.find_element(By.ID, "checkbox1")
if not checkbox.is_selected():
    checkbox.click()

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

Стратегии Ожидания в Selenium

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

Неявные и явные ожидания: когда и как использовать

Неявные ожидания (Implicit Waits) устанавливаются один раз для всего драйвера и заставляют его ждать определенное время при каждом поиске элемента. Это глобальная настройка. Пример:

driver.implicitly_wait(10) # ожидание до 10 секунд
element = driver.find_element(By.ID, "myElement")

Явные ожидания (Explicit Waits) позволяют задать конкретные условия, при которых нужно ждать элемент. Это более гибкий и рекомендуемый подход. Пример:

from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC

try:
    element = WebDriverWait(driver, 10).until(
        EC.presence_of_element_located((By.ID, "myElement"))
    )
finally:
    pass

В этом примере мы ждем, пока элемент с ID "myElement" не появится в DOM.

Примеры кода для ожидания видимости, кликабельности и присутствия элемента

expected_conditions предоставляет множество предустановленных условий. Вот некоторые примеры:

Ожидание видимости элемента:

element = WebDriverWait(driver, 10).until(
    EC.visibility_of_element_located((By.ID, "myElement"))
)

Ожидание кликабельности элемента:

element = WebDriverWait(driver, 10).until(
    EC.element_to_be_clickable((By.ID, "myButton"))
)

Ожидание присутствия элемента (не обязательно видимого):

element = WebDriverWait(driver, 10).until(
    EC.presence_of_element_located((By.ID, "myElement"))
)

Ожидание изменений в DOM и URL

Ожидание изменения текста элемента:

WebDriverWait(driver, 10).until(
    EC.text_to_be_present_in_element((By.ID, 'myElement'), 'Expected Text')
)

Ожидание изменения URL:

WebDriverWait(driver, 10).until(
    EC.url_contains('expected_url_part')
)

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

Неявные и явные ожидания: когда и как использовать

Selenium предлагает два основных типа ожиданий: неявные (implicit waits) и явные (explicit waits). Понимание различий между ними критически важно для написания стабильных автотестов selenium.

Неявные ожидания (Implicit Waits): Устанавливаются глобально для всего драйвера. Когда вы пытаетесь найти элемент, драйвер будет ждать определенное время, прежде чем выбросить исключение NoSuchElementException.

from selenium import webdriver

driver = webdriver.Chrome()
driver.implicitly_wait(10)  # Ожидание в течение 10 секунд
driver.get("https://example.com")
element = driver.find_element("id", "myElement")
# ...

Использовать неявные ожидания не рекомендуется, так как они могут замедлить выполнение тестов и усложнить отладку. Лучше отдать предпочтение явным ожиданиям.

Явные ожидания (Explicit Waits): Применяются к конкретным элементам или условиям. Они позволяют задать максимальное время ожидания и условие, которое должно быть выполнено (например, элемент должен стать видимым или кликабельным).

from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC

driver = webdriver.Chrome()
driver.get("https://example.com")

try:
    element = WebDriverWait(driver, 10).until(
        EC.presence_of_element_located((By.ID, "myElement"))
    )
finally:
    pass
    #driver.quit()

В этом примере, WebDriverWait будет ждать до 10 секунд, пока элемент с id="myElement" не появится в DOM. EC.presence_of_element_located — это одно из множества предопределенных условий, доступных в модуле expected_conditions. Другие полезные условия включают visibility_of_element_located, element_to_be_clickable и другие.

Когда что использовать:

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

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

Примеры кода для ожидания видимости, кликабельности и присутствия элемента

Для иллюстрации различных стратегий ожидания, рассмотрим примеры кода, демонстрирующие ожидание видимости, кликабельности и присутствия элемента на странице, используя WebDriverWait и expected_conditions.

Ожидание видимости элемента:

from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC

driver.get("https://example.com")
element = WebDriverWait(driver, 10).until(
    EC.visibility_of_element_located((By.ID, "myDynamicElement"))
)
print(element.text)

Этот код ожидает, пока элемент с ID "myDynamicElement" не станет видимым в течение 10 секунд. Если элемент не появится, будет выброшено исключение TimeoutException.

Ожидание кликабельности элемента:

from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC

driver.get("https://example.com")
button = WebDriverWait(driver, 10).until(
    EC.element_to_be_clickable((By.ID, "submitButton"))
)
button.click()
Реклама

Здесь мы ожидаем, что кнопка с ID "submitButton" станет кликабельной, прежде чем выполнить клик. Это полезно для элементов, которые могут быть временно недоступны из-за анимации или других процессов.

Ожидание присутствия элемента в DOM:

from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC

driver.get("https://example.com")
WebDriverWait(driver, 10).until(
    EC.presence_of_element_located((By.ID, "myElement"))
)
element = driver.find_element(By.ID, "myElement")
print(element.text)

Этот пример ожидает, пока элемент с ID "myElement" не будет добавлен в DOM (Document Object Model), но не обязательно должен быть видимым. Это полезно, когда элемент добавляется асинхронно, но еще не отображается.

Ожидание изменений в DOM и URL

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

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

from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.support.ui import WebDriverWait

element = driver.find_element(By.ID, "myDynamicElement")
WebDriverWait(driver, 10).until(EC.staleness_of(element))
print("Element больше не в DOM")

Ожидание изменения URL: url_contains, url_matches, url_to_be позволяют дождаться, пока URL страницы не будет соответствовать определенному условию.

from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.support.ui import WebDriverWait

# Ожидание, пока URL не будет содержать строку 'success'
WebDriverWait(driver, 10).until(EC.url_contains('success'))
print("URL содержит 'success'")

# Ожидание полного совпадения URL
WebDriverWait(driver, 10).until(EC.url_to_be('https://example.com/success'))
print("URL соответствует 'https://example.com/success'")

#Ожидание соответствия URL регулярному выражению
 WebDriverWait(driver, 10).until(EC.url_matches(r'\/page\d+'))
print("URL соответствует регулярному выражению")

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

Расширенные Возможности и Интеграция

В этом разделе мы рассмотрим расширенные возможности Selenium WebDriver и его интеграцию с другими инструментами.

Использование Selenium Actions Class для сложных действий (drag-and-drop, hover)

Selenium Actions позволяет моделировать сложные действия пользователя, такие как перетаскивание элементов или наведение курсора мыши. Вот пример перетаскивания элемента:

from selenium.webdriver import ActionChains

source_element = driver.find_element(By.ID, "draggable")
target_element = driver.find_element(By.ID, "droppable")

action_chains = ActionChains(driver)
action_chains.drag_and_drop(source_element, target_element).perform()

Для наведения курсора используйте move_to_element():

element = driver.find_element(By.ID, "hoverable")
action_chains = ActionChains(driver)
action_chains.move_to_element(element).perform()

Переключение между окнами, фреймами и алертами

Для переключения между окнами используйте driver.switch_to.window(window_name) или driver.window_handles для получения списка доступных окон.

original_window = driver.current_window_handle
# Открываем новое окно
driver.execute_script("window.open('https://example.com', '_blank');")

for window_handle in driver.window_handles:
    if window_handle != original_window:
        driver.switch_to.window(window_handle)
        break

Для переключения во фрейм используйте driver.switch_to.frame(frame_reference), где frame_reference может быть индексом, именем или WebElement.

driver.switch_to.frame("frameName") # или driver.switch_to.frame(1) или driver.switch_to.frame(frame_element)

Для работы с алертами:

alert = driver.switch_to.alert
print(alert.text)
alert.accept() # или alert.dismiss()

Интеграция с pytest для структурирования тестов

Pytest – популярный фреймворк для тестирования в Python. Интеграция с Selenium упрощает создание и запуск тестов.

Пример простого теста:

import pytest
from selenium import webdriver
from selenium.webdriver.common.by import By

@pytest.fixture(scope="module")
def driver():
    driver = webdriver.Chrome() # Или другой браузер
    yield driver
    driver.quit()


def test_title(driver):
    driver.get("https://www.example.com")
    assert "Example Domain" in driver.title

В этом примере, фикстура driver создает экземпляр WebDriver и закрывает его после завершения всех тестов в модуле. Функция test_title выполняет проверку заголовка страницы.

Использование Selenium Actions Class для сложных действий (drag-and-drop, hover)

Selenium Actions Class предоставляет мощный инструмент для эмуляции сложных взаимодействий пользователя, таких как перетаскивание элементов (drag-and-drop) и наведение курсора мыши (hover). Это особенно полезно, когда стандартные методы click() или send_keys() не подходят.

Пример: Drag-and-Drop

from selenium import webdriver
from selenium.webdriver import ActionChains

driver = webdriver.Chrome() # Или другой браузер
driver.get("https://example.com/drag_and_drop") # Замените на URL с drag-and-drop

source_element = driver.find_element("id", "draggable")
target_element = driver.find_element("id", "droppable")

actions = ActionChains(driver)
actions.drag_and_drop(source_element, target_element).perform()

# Альтернативный вариант (более детализированный):
# actions.click_and_hold(source_element).move_to_element(target_element).release().perform()

В этом примере drag_and_drop() перетаскивает элемент source_element на target_element. perform() выполняет цепочку действий.

Пример: Hover (наведение курсора)

from selenium import webdriver
from selenium.webdriver import ActionChains

driver = webdriver.Chrome()
driver.get("https://example.com/hover") # Замените на URL с hover-элементом

menu_element = driver.find_element("id", "menu")

actions = ActionChains(driver)
actions.move_to_element(menu_element).perform()

# Теперь можно взаимодействовать с элементами, которые появляются при наведении курсора.
submenu_item = driver.find_element("id", "submenu_item")
submenu_item.click()

Здесь move_to_element() наводит курсор на menu_element, после чего можно взаимодействовать с появившимися элементами подменю. Важно помнить, что Action Chains позволяют создавать сложные последовательности действий, которые затем выполняются все вместе.

Переключение между окнами, фреймами и алертами

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

Переключение между окнами:

При открытии нового окна, Selenium создает новый window handle. Чтобы переключиться на него, нужно знать этот handle.

original_window = driver.current_window_handle
# Открываем новое окно
driver.execute_script("window.open('https://www.example.com', '_blank');")

# Перебираем все window handles и переключаемся на новое окно
for window_handle in driver.window_handles:
    if window_handle != original_window:
        driver.switch_to.window(window_handle)
        break

# Теперь мы работаем в новом окне
print(driver.title)
driver.close()
driver.switch_to.window(original_window) # Возвращаемся к исходному окну

Переключение между фреймами:

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

# Переключение на фрейм по ID или имени
driver.switch_to.frame("frame_name")

# Переключение на фрейм по индексу
driver.switch_to.frame(0)

# Переключение на фрейм по элементу
frame_element = driver.find_element(By.ID, "frame_id")
driver.switch_to.frame(frame_element)

# Работаем с элементами внутри фрейма
element = driver.find_element(By.ID, "element_inside_frame")
element.send_keys("Текст внутри фрейма")

# Возвращаемся к основному контенту страницы
driver.switch_to.default_content()

Работа с алертами:

Selenium позволяет принимать, отклонять и читать текст из всплывающих окон (alerts).

# Переключаемся на алерт
alert = driver.switch_to.alert

# Получаем текст алерта
alert_text = alert.text
print(alert_text)

# Принимаем алерт (нажимаем OK)
alert.accept()

# Отклоняем алерт (нажимаем Cancel), если доступно
# alert.dismiss()

# Ввод текста в алерт (если это prompt)
# alert.send_keys("Текст для ввода")

Интеграция с pytest для структурирования тестов

Pytest – мощный и удобный фреймворк для тестирования в Python, который отлично интегрируется с Selenium WebDriver. Он предоставляет возможности для структурирования тестов, параметризации, использования фикстур и генерации отчетов.

Организация тестов: Pytest автоматически обнаруживает тестовые функции в файлах, начинающихся с test_ или заканчивающихся на _test.py. Функции, имена которых также начинаются с test_, считаются тестовыми.

Фикстуры: Фикстуры позволяют задавать предварительные условия и уборку после тестов. Например, можно создать фикстуру для инициализации WebDriver.

import pytest
from selenium import webdriver

@pytest.fixture(scope="function")
def driver():
    driver = webdriver.Chrome()  # Или другой браузер
    yield driver
    driver.quit()

def test_example(driver):
    driver.get("https://www.example.com")
    assert "Example Domain" in driver.title

Параметризация: Pytest позволяет запускать один и тот же тест с разными наборами данных.

import pytest
from selenium import webdriver

@pytest.mark.parametrize("url, expected_title", [
    ("https://www.example.com", "Example Domain"),
    ("https://www.python.org", "Welcome to Python.org")
])
def test_url(driver, url, expected_title):
    driver.get(url)
    assert expected_title in driver.title

Assert-ы: Pytest использует стандартные assert-ы Python для проверки результатов тестов. При возникновении ошибки, он предоставляет подробную информацию.

Запуск тестов: Тесты запускаются командой pytest в терминале. Можно указывать конкретные файлы, директории или использовать различные опции, например, -v для более подробного вывода.

Использование pytest позволяет создавать более структурированные, читаемые и поддерживаемые selenium код для тестов.

Масштабирование Тестирования и Лучшие Практики

Масштабирование автотестов selenium и поддержание их в актуальном состоянии – важные задачи при развитии проекта. Рассмотрим ключевые аспекты и примеры.

Основы Selenium Grid для параллельного выполнения тестов

Selenium Grid позволяет запускать автотесты selenium параллельно на разных машинах и в разных браузерах. Это значительно сокращает время выполнения всего набора тестов.

Настройка Hub и Node. Необходимо настроить центральный Hub и Node-ы, на которых будут выполняться тесты. Это включает запуск Selenium Server с соответствующими параметрами.

Указание capabilities. При создании экземпляра webdriver нужно указать DesiredCapabilities, чтобы направить тест на нужный Node с нужным браузером.

Пример:

from selenium import webdriver

capabilities = {
    "browserName": "chrome",
    "platform": "WINDOWS"
}

driver = webdriver.Remote(command_executor='http://192.168.1.10:4444/wd/hub', desired_capabilities=capabilities)
driver.get("http://www.example.com")
print(driver.title)
driver.quit()

Примеры кода для типовых сценариев (вход, формы, таблицы)

Вход в систему:

driver.find_element("id", "username").send_keys("your_username")
driver.find_element("id", "password").send_keys("your_password")
driver.find_element("id", "login_button").click()

Заполнение формы:

driver.find_element("id", "name").send_keys("John Doe")
driver.find_element("id", "email").send_keys("john.doe@example.com")
driver.find_element("id", "submit_button").click()

Работа с таблицами:

table = driver.find_element("id", "my_table")
rows = table.find_elements("tag name", "tr")
for row in rows:
    cells = row.find_elements("tag name", "td")
    for cell in cells:
        print(cell.text)

Лучшие практики написания читаемых и поддерживаемых автотестов

Используйте Page Object Model (POM). POM улучшает структуру тестов и упрощает их поддержку.

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

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

Регулярно обновляйте selenium код для тестов. Поддерживайте актуальность тестов при изменениях в приложении.

Основы Selenium Grid для параллельного выполнения тестов

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

Основные компоненты Selenium Grid:

Hub (Центр): Центральная точка, куда отправляются запросы на выполнение тестов. Он распределяет тесты между доступными Node.

Node (Узел): Рабочая станция, на которой фактически запускается браузер и выполняются selenium код для тестов. Каждый Node регистрируется в Hub и сообщает о своих возможностях (тип браузера, версия и т.д.).

Пример конфигурации (упрощенный):

Запуск Hub: java -jar selenium-server-standalone-<version>.jar -role hub

Запуск Node: java -Dwebdriver.chrome.driver=/path/to/chromedriver -jar selenium-server-standalone-<version>.jar -role node -hub http://<hub_ip>:<hub_port>/grid/register -browser browserName=chrome

Код для запуска теста на Grid:

from selenium import webdriver
from selenium.webdriver.common.desired_capabilities import DesiredCapabilities

# Конфигурация для Chrome
capabilities = DesiredCapabilities.CHROME.copy()
# Или для Firefox: capabilities = DesiredCapabilities.FIREFOX.copy()

driver = webdriver.Remote(
    command_executor='http://:/wd/hub',
    desired_capabilities=capabilities
)

driver.get("http://www.example.com")
print(driver.title)
driver.quit()

Важно: Для корректной работы необходимо, чтобы драйверы браузеров (chromedriver, geckodriver) были доступны на всех Node. Рекомендуется использовать Docker для управления конфигурацией Selenium Grid и Node, чтобы обеспечить воспроизводимость и упростить масштабирование.

Selenium Grid значительно повышает эффективность автоматизированного тестирования за счет параллельного запуска тестов на разных конфигурациях.

Примеры кода для типовых сценариев (вход, формы, таблицы)

Рассмотрим примеры selenium код для тестов для типовых сценариев, которые часто встречаются при автоматизации тестирования веб-приложений.

1. Вход в систему:

from selenium import webdriver
from selenium.webdriver.common.by import By

# Предполагаем, что драйвер уже настроен
driver = webdriver.Chrome()

# Открываем страницу входа
driver.get("https://example.com/login")

# Вводим логин и пароль
login_field = driver.find_element(By.ID, "username")
password_field = driver.find_element(By.ID, "password")
login_field.send_keys("your_username")
password_field.send_keys("your_password")

# Нажимаем кнопку "Войти"
login_button = driver.find_element(By.ID, "login_button")
login_button.click()

# Проверяем, что вход выполнен успешно (например, по наличию элемента с именем пользователя)
assert driver.find_element(By.ID, "user_profile").is_displayed()

2. Заполнение формы:

# После успешного входа переходим на страницу с формой
driver.get("https://example.com/profile")

# Заполняем поля формы
name_field = driver.find_element(By.ID, "name")
email_field = driver.find_element(By.ID, "email")

name_field.send_keys("John Doe")
email_field.send_keys("john.doe@example.com")

# Выбираем опцию из выпадающего списка (используя Select)
from selenium.webdriver.support.ui import Select

country_dropdown = Select(driver.find_element(By.ID, "country"))
country_dropdown.select_by_value("USA")

# Отправляем форму
submit_button = driver.find_element(By.ID, "submit_button")
submit_button.click()

# Проверяем, что данные успешно отправлены (например, по появлению сообщения об успехе)
assert driver.find_element(By.CLASS_NAME, "success_message").is_displayed()

3. Работа с таблицами:

# Переходим на страницу с таблицей
driver.get("https://example.com/table")

# Получаем все строки таблицы (за исключением заголовка)
table_rows = driver.find_elements(By.XPATH, "//table/tbody/tr")

# Итерируемся по строкам и выводим данные из каждого столбца
for row in table_rows:
    cells = row.find_elements(By.TAG_NAME, "td")
    row_data = [cell.text for cell in cells]
    print(row_data)

# Пример: поиск конкретной строки по значению в столбце
for row in table_rows:
    cells = row.find_elements(By.TAG_NAME, "td")
    if cells[0].text == "Specific Value": #Проверяем значение первого столбца
        print("Found row:", [cell.text for cell in cells])
        break

Эти примеры демонстрируют базовые приемы работы с Selenium для автоматизации веб-приложений. Для более сложных сценариев может потребоваться использование Selenium Actions Class, явных ожиданий, и других продвинутых техник, рассмотренных в предыдущих разделах.

Лучшие практики написания читаемых и поддерживаемых автотестов

Принцип DRY (Don’t Repeat Yourself). Избегайте дублирования кода. Выносите повторяющиеся действия (например, запуск браузера, авторизация) в отдельные функции или классы.

Используйте Page Object Model (POM). POM помогает организовать тесты, представляя веб-страницы как объекты. Это улучшает читаемость и упрощает поддержку автотестов selenium.

Осмысленные имена. Дайте тестам, функциям и переменным понятные имена, отражающие их назначение. Например, вместо test1, используйте test_login_with_valid_credentials.

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

Явные ожидания. Используйте явные ожидания вместо time.sleep(). Это сделает selenium код для тестов более стабильным и эффективным, так как тесты не будут ждать дольше, чем необходимо.

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

Логирование. Добавьте логирование важных событий и действий в тестах. Это поможет понять, что происходило во время выполнения теста, и быстрее выявить причины ошибок.

Используйте параметризацию. Применяйте параметризацию для запуска одного и того же теста с разными наборами данных. Это сократит количество дублирующегося selenium python код и упростит тестирование различных сценариев.

Конфигурация. Храните параметры конфигурации (URL, логины, пароли) в отдельных файлах или переменных окружения. Это облегчит изменение конфигурации без изменения кода тестов.

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

Заключение

В заключение, мы рассмотрели ключевые аспекты автоматизированного тестирования с использованием Selenium WebDriver и Python, начиная с базовой настройки и заканчивая продвинутыми техниками. Мы изучили различные стратегии локаторов, методы взаимодействия с элементами, способы реализации ожиданий и интеграцию с pytest.

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

Автоматизация тестирования — это непрерывный процесс, требующий постоянного обучения и адаптации. Желаем вам успехов в ваших проектах автоматизации!


Добавить комментарий