Блог
Автотесты/Playwright

Мобильная эмуляция устройств в Playwright

Мобильная эмуляция в Playwright — это запуск теста в обычном браузере (Chromium, WebKit) с подставленными параметрами конкретного мобильного устройства: размером экрана, user-agent, поддержкой touch-событий и плотностью пикселей. Playwright поставляется с готовым каталогом пресетов devices (iPhone, Pixel, Galaxy и другие) — эмуляция не запускает настоящую мобильную операционную систему или реальный мобильный браузер, а имитирует его окружение внутри десктопного движка браузера.

Как включить эмуляцию конкретного устройства в Playwright?

import { test, devices } from '@playwright/test';

test.use({ ...devices['iPhone 13'] });

test('мобильная версия сайта открывается', async ({ page }) => {
await page.goto('https://example.com');
await expect(page.getByRole('button', { name: 'Меню' })).toBeVisible();
});

Объект devices['iPhone 13'] — это готовый набор параметров контекста браузера: viewport, userAgent, deviceScaleFactor, isMobile, hasTouch и (для WebKit-пресетов) defaultBrowserType. test.use({ ...devices[...] }) применяет весь набор сразу через spread-оператор ко всем тестам файла или describe-блока, без необходимости прописывать каждый параметр вручную.

Как настроить мобильную эмуляцию сразу для целого проекта в конфиге?

// playwright.config.ts
import { defineConfig, devices } from '@playwright/test';

export default defineConfig({
projects: [
{ name: 'Desktop Chrome', use: { ...devices['Desktop Chrome'] } },
{ name: 'Mobile Safari', use: { ...devices['iPhone 13'] } },
{ name: 'Mobile Chrome', use: { ...devices['Pixel 7'] } },
],
});

Через projects в конфиге один и тот же набор тестов запускается несколько раз — под десктопным Chrome и под эмуляцией двух мобильных устройств, каждый раз с собственными параметрами viewport и userAgent. Команда npx playwright test без флагов прогонит тесты сразу во всех перечисленных проектах; флаг --project="Mobile Safari" ограничит прогон одним из них.

Какие параметры реально меняет пресет устройства?

— `viewport` — размер видимой области страницы в пикселях (например, { width: 390, height: 664 } у iPhone 13 — это размер видимой веб-страницы, меньше физического экрана из-за системного UI Safari), определяет, какая версия адаптивной вёрстки сработает.
— `userAgent` — строка User-Agent, которую видит сервер и JavaScript-код страницы (navigator.userAgent) — сайты, которые отдают разный HTML по User-Agent, среагируют на неё.
— `deviceScaleFactor` — плотность пикселей экрана (например, 3 у iPhone), влияет на то, как рендерятся изображения с разной плотностью (srcset, image-set) и на скриншоты.
— `isMobile` — булев флаг, который в Chromium дополнительно включает мобильный режим движка рендеринга (влияет на то, как страница интерпретирует медиа-запросы @media (hover: none) и подобные).
— `hasTouch` — включает поддержку touch-событий (touchstart, touchend) в контексте браузера, без него tap() и симуляция жестов работать не будут.
— `defaultBrowserType` — для части iOS-пресетов указывает WebKit, потому что реальный мобильный Safari на iOS основан на движке WebKit, а не на Chromium.

Чем эмуляция устройства отличается от настоящего мобильного браузера?

Эмуляция подставляет метаданные (viewport, user-agent, touch-флаги) в десктопный движок браузера, но не меняет сам движок рендеринга и не воспроизводит специфику мобильной ОС — реальные ограничения памяти, поведение мобильной клавиатуры, системные диалоги (пуш-уведомления, разрешения камеры на уровне ОС), особенности рендеринга шрифтов конкретной прошивки. Даже пресет devices['iPhone 13'] с defaultBrowserType: 'webkit' запускает WebKit на десктопной ОС (macOS/Linux), а не настоящий мобильный Safari на iOS — большая часть поведения совпадает, потому что движок общий, но не гарантированно всё. Для проверок, для которых критична именно реальная мобильная ОС и прошивка (например, специфичные баги мобильного Safari, доступные только на реальном iPhone), эмуляции Playwright недостаточно — нужны облачные фермы реальных устройств (BrowserStack, Sauce Labs) или Appium с реальными эмуляторами Android/iOS.

Как эмулировать жест тапа (tap) вместо клика?

test.use({ ...devices['Pixel 7'] });

test('тап по кнопке в мобильной эмуляции', async ({ page }) => {
await page.goto('https://example.com');
await page.getByRole('button', { name: 'Добавить в корзину' }).tap();
});

Метод .tap() отправляет реальные touch-события (touchstart, touchend), а не эмулирует клик мышью — он доступен только если у контекста браузера включён hasTouch: true, что уже включено во всех мобильных пресетах devices. Для большинства сценариев .click() тоже сработает на элементе, даже в мобильной эмуляции, потому что современные сайты обрабатывают клик как универсальное событие — .tap() нужен именно тогда, когда логика страницы завязана конкретно на touch-события (свайпы, долгое нажатие, специфичные touch-обработчики).

Как проверить геолокацию и разрешения в мобильной эмуляции?

const context = await browser.newContext({
...devices['iPhone 13'],
geolocation: { latitude: 55.7558, longitude: 37.6173 },
permissions: ['geolocation'],
});

Геолокация и разрешения (камера, микрофон, уведомления) — это параметры контекста браузера, не привязанные конкретно к мобильной эмуляции, но особенно часто нужны именно в мобильных сценариях (карты, доставка, локальный поиск). geolocation задаёт координаты, которые вернёт navigator.geolocation.getCurrentPosition() внутри страницы, а permissions: ['geolocation'] заранее выдаёт разрешение на использование геолокации — без него запрос геолокации не покажет диалог, с которым тест мог бы взаимодействовать, а автоматически и молча завершится ошибкой PERMISSION_DENIED в error-колбэке.

Какие параметры мобильных пресетов стоит запомнить?

Все параметры пресета devices['iPhone 13'] для быстрой сверки:
— `viewport` — размер видимой области страницы в пикселях, определяет, какая адаптивная вёрстка сработает. У iPhone 13: { width: 390, height: 664 }.
— `userAgent` — строка User-Agent, которую видят сервер и navigator.userAgent в JS-коде страницы. У iPhone 13: UA-строка мобильного Safari на iOS.
— `deviceScaleFactor` — плотность пикселей экрана, влияет на srcset/image-set и скриншоты. У iPhone 13: 3.
— `isMobile` — мобильный режим движка рендеринга в Chromium, влияет на медиа-запросы вида (hover: none). У iPhone 13: true.
— `hasTouch` — поддержка touch-событий (touchstart, touchend), без неё .tap() не сработает. У iPhone 13: true.
— `defaultBrowserType` — движок браузера по умолчанию для пресета, у части iOS-пресетов это WebKit, приближение к мобильному Safari. У iPhone 13: webkit.

Какие вопросы про мобильную эмуляцию в Playwright задают чаще всего?

Можно ли протестировать нативное мобильное приложение через Playwright? Нет, Playwright эмулирует мобильный веб-браузер, но не запускает нативные приложения iOS/Android — для этого нужны отдельные инструменты, например Appium, которые работают с реальной или эмулируемой мобильной ОС на уровне системного UI, а не браузерного движка.
Список пресетов devices можно расширять своими значениями? Да, devices['iPhone 13'] — это обычный JS-объект, который можно переопределить частично: { ...devices['iPhone 13'], geolocation: {...} } добавит нужные поля поверх пресета, не трогая остальные параметры устройства.
Эмуляция мобильного устройства делает тест медленнее? Незначительно и не из-за самой эмуляции — количество тестов кратно растёт, если один и тот же набор тестов запускается на нескольких проектах (desktop + несколько мобильных пресетов) параллельно в CI, но каждый отдельный тест выполняется примерно с той же скоростью, что и в десктопном режиме.
Нужно ли отдельно проверять ориентацию экрана (portrait/landscape)? Да, если это важно для продукта — viewport в пресете задаёт портретную ориентацию по умолчанию, автоматического поворота «устройства» при эмуляции нет. Прежде чем вручную менять местами ширину и высоту через page.setViewportSize(), стоит проверить, нет ли готового пресета — для части устройств в каталоге devices уже есть landscape-вариант, например devices['iPhone 13 landscape'], с уже подготовленными значениями viewport.
Достаточно ли задать только `viewport`, чтобы получить полноценную мобильную эмуляцию? Нет — это частая ловушка на собеседовании. Уменьшенный viewport меняет только адаптивную вёрстку, но не трогает userAgent, isMobile и hasTouch: сайт, который проверяет тип устройства по одному из этих параметров, продолжит вести себя как в десктопной версии. Для достоверной мобильной эмуляции нужен полный набор параметров пресета devices[...] или явно заданная комбинация всех этих полей вручную.
Чем мобильная эмуляция в Playwright отличается от эмуляции устройств в Chrome DevTools? DevTools меняет viewport и user-agent только внутри открытой вкладки браузера для ручной отладки одним разработчиком за раз. Эмуляция в Playwright — это параметры программного контекста браузера внутри автоматизированного теста: она воспроизводима, работает не только в Chromium, но и в WebKit (приближение к мобильному Safari), и запускается в CI без участия человека.

Закрепить мобильную эмуляцию на практике

Настроить projects в конфиге под несколько устройств — это одна строчка синтаксиса, а вот понять, какая комбинация isMobile/hasTouch/userAgent реально нужна под конкретный сценарий (и не словить на собесе ловушку с «одним только viewport»), проще на практике. Потренироваться на бесплатном тренажёре Playwright Arena от Quality Academy — 30 задач в трёх модулях, без оплаты и ограничения попыток. А для разбора конфигурации, CI и полноценного проекта с ментором — курс «Автотестирование JS/TS + Playwright»: 12 спринтов, 24 лекции, собственный проект за 4 месяца.

-------

Полезные ссылки школы

Сайт Quality Academy:
/main
Telegram-канал:
https://t.me/quality_academy
YouTube-канал:
https://www.youtube.com/@quality_academy
ВКонтакте:
https://vk.com/quality_academy
Канал отзывов учеников (58+ отзывов):
https://t.me/quality_academy_reviews
Задать вопрос менеджеру:
https://t.me/quality_academy_bot
Тест «Подойдёт ли вам тестирование»:
https://quiz.quality-academy.ru
5000+ вопросов с собесов тестировщика — бот-тренажёр:
https://t.me/quality_academy_interview_bot
3 практические задачи и дорожная карта:
https://t.me/quality_academy_tasks_bot
Бесплатные тренажёры — SQL Arena, Playwright Arena, Python Arena:
SQL Arena · Playwright Arena · Python Arena