Playwright — найпотужніший фреймворк для браузерної автоматизації у 2026 році. Але без правильно налаштованих мобільних проксі ваш скрейпер буде заблокований протягом кількох хвилин на будь-якому серйозному цільовому сайті.
IP-адреси дата-центрів визначаються за ASN ще до відправки першого запиту. Резидентські проксі допомагають, але швидко «згорають» під навантаженням скрейпінгу. Мобільні проксі від реальних операторів 4G/5G — єдиний клас IP-адрес, який витримує тривалу браузерну автоматизацію.
Цей посібник охоплює повну бойову конфігурацію: інтеграцію SOCKS5, автоматичну ротацію IP через API ProxyGrow та патерни, які утримають ваш скрейпер живим навіть на найзахищеніших ресурсах.
Спробуйте справжні мобільні проксі
Україна · Румунія · Латвія — IP-адреси операторів 4G/5G, миттєва активація.
Навіщо Playwright потрібні мобільні проксі
Playwright керує реальним рушієм Chromium, Firefox або WebKit. Браузер надсилає справжні TLS-відбитки, реальні HTTP/2-заголовки, справжні значення navigator — і реальну IP-адресу.
Якщо ця IP належить дата-центровому ASN, жодне підміна браузерного відбитка вас не врятує. Платформа все знає ще до завантаження сторінки.
Мобільні проксі вирішують проблему на мережевому рівні:
- Тип ASN: Kyivstar (AS15895), Orange Romania (AS8708), LMT Latvia (AS12578) — це ASN мобільних операторів, а не діапазони дата-центрів
- Репутація CGNAT: мобільні IP розподіляються між тисячами реальних користувачів, тому масові блокування зачіпають живий трафік — і сайти їх уникають
- Історія IP: операторські IP не потрапляють до комерційних чорних списків так, як дата-центрові
Попередні вимоги
npm init -y
npm install playwright axios
npx playwright install chromium
Вам знадобляться:
- SOCKS5-проксі ProxyGrow (хост, порт, логін, пароль)
- URL ротації IP (вказаний у ваших облікових даних ProxyGrow)
Базове налаштування Playwright + SOCKS5
Playwright приймає параметр proxy безпосередньо в chromium.launch() або browser.newContext().
const { chromium } = require('playwright');
const PROXY_HOST = 'your-proxy-host.proxygrow.net';
const PROXY_PORT = 10500;
const PROXY_USER = 'your-username';
const PROXY_PASS = 'your-password';
(async () => {
const browser = await chromium.launch({
proxy: {
server: `socks5://${PROXY_HOST}:${PROXY_PORT}`,
username: PROXY_USER,
password: PROXY_PASS,
},
});
const context = await browser.newContext();
const page = await context.newPage();
await page.goto('https://httpbin.org/ip');
const body = await page.textContent('body');
console.log('Current IP:', JSON.parse(body).origin);
await browser.close();
})();
Запустіть цей код — і ви побачите українську, румунську або латвійську мобільну IP оператора, а не вашу реальну адресу чи адресу дата-центру.
Ротація IP через API між запитами
ProxyGrow надає ендпоінт ротації. Його виклик ініціює зміну IP на модемі (нове CGNAT-призначення від оператора). Саме так правильно виконувати ротацію — а не перемикатися між різними проксі-серверами.
const { chromium } = require('playwright');
const axios = require('axios');
const PROXY_HOST = 'your-proxy-host.proxygrow.net';
const PROXY_PORT = 10500;
const PROXY_USER = 'your-username';
const PROXY_PASS = 'your-password';
const ROTATION_URL = 'https://your-proxy-host.proxygrow.net/rotate?token=YOUR_TOKEN';
async function rotateIP() {
try {
const response = await axios.get(ROTATION_URL, { timeout: 10000 });
console.log('IP rotated:', response.data);
// Wait for the new IP to stabilize
await new Promise(resolve => setTimeout(resolve, 3000));
} catch (err) {
console.error('Rotation failed:', err.message);
}
}
async function scrapeWithRotation(urls) {
const browser = await chromium.launch({
proxy: {
server: `socks5://${PROXY_HOST}:${PROXY_PORT}`,
username: PROXY_USER,
password: PROXY_PASS,
},
});
for (const url of urls) {
// Rotate IP before each target
await rotateIP();
const context = await browser.newContext({
userAgent: 'Mozilla/5.0 (Linux; Android 13; Pixel 7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/124.0.0.0 Mobile Safari/537.36',
viewport: { width: 390, height: 844 },
locale: 'en-US',
});
const page = await context.newPage();
try {
await page.goto(url, { waitUntil: 'domcontentloaded', timeout: 30000 });
const title = await page.title();
console.log(`[${url}] Title: ${title}`);
} catch (err) {
console.error(`[${url}] Failed: ${err.message}`);
} finally {
await context.close();
}
}
await browser.close();
}
const targets = [
'https://example.com/product/1',
'https://example.com/product/2',
'https://example.com/product/3',
];
scrapeWithRotation(targets);
Ключові архітектурні рішення:
- Для кожного запиту створюється новий
context, щоб куки та сховище не переходили між сесіями - User agent встановлено як реальний Android Mobile UA — відповідає IP мобільного оператора
- Viewport задано у мобільних розмірах — знову ж узгоджується з типом оператора
- Ротація IP відбувається перед кожним контекстом, надаючи кожному запиту свіжу IP
Обхід антибот-захисту
Сучасні антибот-системи (Cloudflare, DataDome, PerimeterX, Akamai) аналізують десятки сигналів окрім IP-адреси. Ось патерни, які мають найбільше значення.
Відповідність User Agent типу IP
Якщо ваша IP належить мобільному оператору, а UA каже HeadlessChrome/124 — ви негайно потрапляєте під підозру. Реальні мобільні користувачі не запускають headless-браузери.
Використовуйте реалістичний Android або iOS user agent:
const mobileUA = 'Mozilla/5.0 (Linux; Android 14; SM-S928B) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/124.0.6367.82 Mobile Safari/537.36';
Правильне вимкнення режиму headless
У Playwright є режим --headless=new, що знижує ймовірність виявлення, але деякі сайти перевіряють рядок Headless у властивостях navigator. Використовуйте headless: false для максимально стійкої конфігурації або придушіть специфічні для ботів властивості navigator:
const context = await browser.newContext();
await context.addInitScript(() => {
Object.defineProperty(navigator, 'webdriver', { get: () => undefined });
Object.defineProperty(navigator, 'plugins', { get: () => [1, 2, 3] });
Object.defineProperty(navigator, 'languages', { get: () => ['en-US', 'en'] });
});
Додавання затримок, що імітують поведінку людини
Боти скрейпять на машинній швидкості. Реальні користувачі роблять паузи, прокручують сторінку і клікають непослідовно. Додайте випадкові затримки:
function randomDelay(min = 800, max = 3000) {
const ms = Math.floor(Math.random() * (max - min + 1)) + min;
return new Promise(resolve => setTimeout(resolve, ms));
}
await page.goto(url);
await randomDelay();
await page.mouse.move(200, 300);
await randomDelay(200, 600);
await page.mouse.move(400, 500);
await randomDelay();
Проходження Cloudflare-перевірок
Turnstile та JS-челенджі від Cloudflare вимагають виконання JavaScript і браузера, що проходить перевірку середовища. З Playwright + мобільний проксі:
- Встановіть
headless: falseабо використовуйтеheadless: 'new' - Дочекайтеся вирішення челенджу перед продовженням роботи
- Ротуйте IP лише між сесіями, а не посередині сесії
await page.goto(url);
// Wait for CF to resolve — up to 15s
await page.waitForFunction(
() => !document.title.includes('Just a moment'),
{ timeout: 15000 }
).catch(() => console.log('CF challenge may still be active'));
Бойовий патерн: пул проксі з чергою
Для великомасштабного скрейпінгу з кількома проксі:
const { chromium } = require('playwright');
const axios = require('axios');
const PROXIES = [
{ host: 'proxy1.proxygrow.net', port: 10500, user: 'user1', pass: 'pass1', rotateUrl: 'https://...' },
{ host: 'proxy2.proxygrow.net', port: 10501, user: 'user2', pass: 'pass2', rotateUrl: 'https://...' },
{ host: 'proxy3.proxygrow.net', port: 10502, user: 'user3', pass: 'pass3', rotateUrl: 'https://...' },
];
let proxyIndex = 0;
function getNextProxy() {
const proxy = PROXIES[proxyIndex % PROXIES.length];
proxyIndex++;
return proxy;
}
async function scrapeURL(url) {
const proxy = getNextProxy();
// Rotate IP on the selected proxy
await axios.get(proxy.rotateUrl, { timeout: 10000 }).catch(() => {});
await new Promise(r => setTimeout(r, 2500));
const browser = await chromium.launch({
proxy: {
server: `socks5://${proxy.host}:${proxy.port}`,
username: proxy.user,
password: proxy.pass,
},
});
const context = await browser.newContext({
userAgent: 'Mozilla/5.0 (Linux; Android 14; Pixel 8) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/124.0.0.0 Mobile Safari/537.36',
viewport: { width: 393, height: 852 },
});
const page = await context.newPage();
await page.goto(url, { waitUntil: 'networkidle', timeout: 45000 });
const html = await page.content();
await browser.close();
return html;
}
Найкращі ГЕО для скрейпінгу з Playwright
| Цільовий сайт за ГЕО | Рекомендоване ГЕО ProxyGrow | Оператор |
|---|---|---|
| США/Глобальний | Румунія | Orange Romania (AS8708) |
| Специфіка ЄС | Латвія | LMT (AS12578) |
| СНД/Східна Європа | Україна | Kyivstar (AS15895) |
| Будь-який EU e-commerce | Румунія або Латвія | Orange / LMT |
Румунські та латвійські IP розташовані в ЄС, що дозволяє проходити гео-обмеження на сайтах, орієнтованих на ЄС, та уникати блокувань, пов'язаних з GDPR.
Playwright vs. Puppeteer vs. Selenium
Для автоматизації з інтенсивним використанням проксі:
| Функція | Playwright | Puppeteer | Selenium |
|---|---|---|---|
| Нативний SOCKS5 | Так | Потребує прапор | Обмежено |
| Кілька браузерів | Так | Тільки Chromium | Так |
| Ізоляція контексту | Так (швидко) | Вручну | По сесії |
| Stealth-плагіни | playwright-extra | puppeteer-extra | Прапори webdriver |
| Імітація мобільного UA | Першокласно | Вручну | Вручну |
Playwright перемагає для проксі-скрейпінгу, бо його модель контекстів ідеально підходить для ізоляції проксі на рівні запиту без створення нових процесів браузера.
Швидкий чек-лист налаштування
✔ Встановити playwright та axios
✔ Використовувати SOCKS5 (не HTTP) для кращого покриття протоколів
✔ Встановити мобільний user agent, що відповідає ГЕО оператора
✔ Встановити мобільний viewport (390x844 або аналогічний)
✔ Створювати новий контекст для кожної сесії скрейпінгу
✔ Ротувати IP через API між сесіями, а не посередині сесії
✔ Додати випадкові затримки між діями
✔ Придушити властивість navigator.webdriver
✔ Зіставити локаль з ГЕО проксі
Поширені помилки
Використання HTTP-проксі замість SOCKS5
HTTP-проксі не можуть передавати всі типи трафіку. SOCKS5 є протоконезалежним і краще обробляє WebSocket-з'єднання, бінарні протоколи та TLS.
Ротація IP посередині сесії
Якщо ви ініціюєте ротацію під час завантаження сторінки, з'єднання обривається і запити завершуються з помилкою. Завжди ротуйте IP перед відкриттям нового контексту браузера.
Десктопний UA з мобільною IP
IP Kyivstar або LMT, що надсилає трафік десктопного Chrome — статистична аномалія. Більшість трафіку мобільних операторів надходить із мобільних пристроїв. Використовуйте відповідний мобільний UA.
Відсутність очікування після ротації
Після виклику ендпоінту ротації модему потрібно 2-4 секунди для завершення перепідключення та отримання нової IP від оператора. Пропустіть це очікування — і ваш перший запит піде зі старої IP.
Спробуйте справжні мобільні проксі
Україна · Румунія · Латвія — IP-адреси операторів 4G/5G, миттєва активація.