Разбираемся с DevTools в Selenium 4
Один из самых популярных инструментов UI автоматизации — Selenium, готовит к релизу мажорное обновление. На момент написания статьи выпущена вторая бета.
В состав релиза входит API для работы с DevTools через CDP (Chrome DevTools Protocol), который выводит взаимодействие с браузером на новый уровень.
Инструментарий DevTools разделен на блоки (DOM, Debugger, Network etc.), каждый из которых определяет список поддерживаемых команд и генерируемых ивентов.
Selenium позволяет напрямую работать с каждым, что дает возможность:
- работать с кэшем браузера
- перехватывать и модифицировать запросы
- эмулировать состояние сети
- устанавливать геолокацию
- обходить security ограничения
- считывать браузерные метрики
Драйвер, который поддерживает работу с инструментами разработчика, реализует getDevTools()
метод, а выполнять CDP команды можно непосредственно работая с объектом DevTools
.
Для каждого блока команд предусмотрены классы обертки. Чтобы отправить команду достаточно создать сессию и вызвать devTools.send(Command<X> command)
.
DevTools devTools = driver.getDevTools(); devTools.createSession(); List<Cookie> cookies = devTools.send(Network.getAllCookies());
Еще один способ — вызвать метод executeCdpCommand()
, который реализован у наследников ChromiumDriver
и работает не с обертками, а raw командами. Аргументы метода — название операции и перечень параметров.
Map<String, Object> data = driver.executeCdpCommand("Network.getAllCookies", new HashMap<>()); List<Cookie> cookies = (List<Cookie>) data.get("cookies");
Используем новые возможности на практике
Переопределение UserAgent
До Selenium 4 UserAgent устанавливался только через capabilities, до создания объекта драйвера.
Network.setUserAgentOverride задает новое значение UserAgent на лету.
devTools.send(Network.setUserAgentOverride("aqa-agent", Optional.empty(), Optional.empty(), Optional.empty()));
Предоставление прав
Для некоторых операций, браузер запрашивает разрешение пользователя, например, для доступа к буферу обмена или микрофону. Предоставить права можно при помощи Browser.grantPermissions передавая перечень необходимых PermissionType.
Для примера разрешим браузеру захват звука.
driver.executeCdpCommand("Browser.grantPermissions", Map.of("permissions", asList("audioCapture")));
Добавление заголовков в запросы
Network.setExtraHTTPHeaders позволяет добавить кастомные заголовки к запросам.
devTools.send(Network.enable(empty(),empty(),empty())); devTools.send(Network.setExtraHTTPHeaders(new Headers(Map.of("aqa-header", "John Wick"))));
Перехват и модификация запросов
Fetch.enable включает перехват, каждый запрос будет остановлен пока клиент не вызовет failRequest, fulfillRequest или continueRequest.
Перехватывать можно все запросы и модифицировать по условию, либо работать только с целевыми, указав для этого RequestPattern
, ниже приведены оба варианта.
Модифицируем URL, например перенаправим запросы /v1/users
на новую версию бэкенда /v2/users
.
devTools.send(Fetch.enable(empty(), empty())); devTools.addListener(Fetch.requestPaused(), request -> { String url = request.getRequest().getUrl().contains("/v1/users") ? request.getRequest().getUrl().replace("/v1/users", "/v2/users") : request.getRequest().getUrl(); devTools.send(Fetch.continueRequest( request.getRequestId(), Optional.of(url), Optional.of(request.getRequest().getMethod()), request.getRequest().getPostData(), request.getResponseHeaders())); });
Аналогичным способом эмулируется неудачный запрос. Например для тестирования работы приложения с отвалившейся интеграцией.
Optional<List<RequestPattern>> patterns = Optional.of(asList(new RequestPattern(of("*.dropbox.*"), empty(), empty()))); devTools.send(Fetch.enable(patterns, empty())); devTools.addListener(Fetch.requestPaused(), r -> devTools.send(Fetch.failRequest(r.getRequestId(), FAILED)));
Эмуляция интернет соединения
Network.emulateNetworkConditions позволяет задавать параметры соединения, например для тестирования поведения при слабом 3G или отсутствии сети.
devTools.send(Network.enable(empty(), empty(), empty())); devTools.send(Network.emulateNetworkConditions(false, 100, 1000, 1000, of(ConnectionType.CELLULAR3G)));
Очистка кэша
Network.clearBrowserCache очистит кэш браузера.
devTools.send(Network.clearBrowserCache());
Блокировка загрузки ресурсов
Через Network.setBlockedURLs можно ограничишь загрузку ресурсов по паттерну. Например, заблокируем скачивание .svg
devTools.send(Network.enable(empty(), empty(), empty())); devTools.send(Network.setBlockedURLs(List.of("*.svg")));
Установка TimeZone и Geolocation Position
Emulation.setTimezoneOverride переопределяет TimeZone браузера, а Emulation.setGeolocationOverride геопозицию.
devTools.send(Emulation.setTimezoneOverride("America/New_York")); devTools.send(Emulation.setGeolocationOverride(Optional.of(40.730610), Optional.of(-73.935242), Optional.of(1)));
Обход ограничений безопасности
Security.setIgnoreCertificateErrors позволит обойти проблемы с SSL сертификатом. Отмечу, что не призываю к таким действиям, а показываю наличие возможности.
devTools.send(Security.enable()); devTools.send(Security.setIgnoreCertificateErrors(true));
Метрики
Performance.enable включает сбор метрик (Resources, Documents, JSHeapUsedSize etc.), а Performance.getMetrics возвращает текущие значения.
devTools.send(Performance.enable(empty())); List<Metric> send = devTools.send(Performance.getMetrics());
Итоги
В статье разобраны лишь некоторые из возможностей использования DevTools для написания тестов, применение ограничивается только фантазией и перечнем команд.
API для работы с инструментами разработчика делает Selenium еще мощнее, открывая возможности настроек, кастомизации, эмуляции, перехвата трафика, отслеживания ивентов и метрик.
Функционал DevTools добавит в тесты гибкости, сделает прекондишены проще, а репортинг и причины падений информативнее.
Ожидаем выхода официального релиза.
4 коментарі
Додати коментар Підписатись на коментаріВідписатись від коментарів