Playwright · Residential Proxy · Setup Guide

How to Use Playwright with Residential Proxy in 2026

📅 February 19, 2026 ⏱ 6 min read 👤 Virix Labs

Using a residential proxy with Playwright is no longer optional for serious web scraping in 2026. Anti-bot systems have gotten good enough that a data center IP — no matter how well you spoof the browser — will get blocked. This guide covers the complete setup: authentication, country selection, fingerprint matching, and common errors with fixes.

We'll use the human-browser package which handles all the proxy wiring and fingerprint setup automatically. If you just want to wire up the proxy yourself, we cover the raw Playwright proxy config too.

Why You Need a Residential Proxy with Playwright

Every time you make an HTTP request from a VPS, your IP address comes from an ASN (Autonomous System Number) that identifies your traffic as originating from a data center. Cloudflare, Meta, LinkedIn, and dozens of other services maintain real-time databases of these ASNs and block them automatically.

A residential proxy routes your traffic through a real home internet connection — someone's Comcast, DIGI Romania, or BT broadband. To any website, your traffic looks indistinguishable from a real person sitting at home browsing the web.

In 2026, here's what happens without a residential proxy:

  • Cloudflare: Challenge page or 403 within 1–2 seconds
  • Instagram: Rate limit and account flag within minutes
  • LinkedIn: CAPTCHA or block after first request
  • Most modern SaaS sites: Silent 403 or empty response

Data Center IP vs Residential IP: The Real Difference

It's not just about IP reputation. There are several signals that distinguish data center traffic from residential traffic:

  • ASN classification: AWS (AS16509), Hetzner (AS24940), DigitalOcean (AS14061) are instantly flagged
  • IP history: Data center IPs are shared across thousands of users and accumulate bad reputation
  • Reverse DNS: Data center IPs often resolve to hostnames like ec2-xxx.compute.amazonaws.com
  • Connection patterns: Data center connections have lower latency variance and higher throughput than residential connections
  • Geolocation mismatch: A browser claiming to be in Bucharest but connecting from a Frankfurt Hetzner node raises flags

A good residential proxy solves all of these at once. The IP genuinely belongs to a home ISP and has a clean history.

How to Configure Playwright Proxy Authentication

Option A: Using human-browser (recommended)

The human-browser package handles all proxy configuration automatically, including authentication, fingerprint matching, and human behavior simulation:

install
npm install human-browser
scraper.js
const { launchHuman } = require('human-browser');

// Proxy credentials set via environment variables:
// PROXY_USER, PROXY_PASS, PROXY_HOST, PROXY_PORT

const { browser, page, humanScroll } = await launchHuman({
  country: 'ro',   // Romania residential IP
  mobile: true    // iPhone 15 Pro fingerprint
});

await page.goto('https://example.com');
await humanScroll(page, 'down');
await browser.close();

Option B: Raw Playwright proxy configuration

If you want to wire up the proxy manually without the human-browser abstraction:

raw-proxy.js
const { chromium } = require('playwright');

const browser = await chromium.launch({
  headless: true,
  proxy: {
    server: 'http://brd.superproxy.io:22225',
    username: process.env.PROXY_USER,
    password: process.env.PROXY_PASS
  }
});

const context = await browser.newContext({
  userAgent: 'Mozilla/5.0 (iPhone; CPU iPhone OS 17_4_1 like Mac OS X) AppleWebKit/605.1.15',
  viewport: { width: 393, height: 852 },
  deviceScaleFactor: 3,
  isMobile: true,
  hasTouch: true,
  locale: 'ro-RO',
  timezoneId: 'Europe/Bucharest',
  geolocation: { latitude: 44.4268, longitude: 26.1025 },
  permissions: ['geolocation']
});

const page = await context.newPage();
await page.goto('https://example.com');
await browser.close();
💡 Pro tip: The raw Playwright approach still uses a data center IP with residential proxy routing, but without webdriver=false and other anti-detection patches, you'll fail fingerprint checks. Human Browser handles all 12+ anti-detection signals automatically.

Multi-Country Setup (Romania, US, UK, Germany, Japan)

Different websites work better with different country IPs. Here's a compatibility overview for 2026:

Country Cloudflare Sites Instagram LinkedIn Price Tier
🇷🇴 Romania ✅ Excellent ✅ Excellent ✅ Good Starter ($13.99)
🇺🇸 USA ✅ Excellent ⚠️ Rate limited faster ✅ Excellent Pro ($49.99)
🇬🇧 UK ✅ Excellent ⚠️ Good ✅ Excellent Pro ($49.99)
🇩🇪 Germany ✅ Excellent ⚠️ Good ✅ Good Pro ($49.99)
🇯🇵 Japan ✅ Excellent ⚠️ Good ⚠️ Good Pro ($49.99)

Romania is the best value option — the cheapest plan and one of the cleanest residential IP pools. It works for almost every use case. For US-specific content or LinkedIn scraping, US IPs are worth the upgrade.

Working Code Examples

Instagram with Romanian IP

instagram.js
const { launchHuman } = require('human-browser');

async function scrapeInstagram(username) {
  const { browser, page, humanRead, humanScroll } = await launchHuman({
    country: 'ro',
    mobile: true
  });

  try {
    await page.goto(`https://www.instagram.com/${username}/`, {
      waitUntil: 'domcontentloaded'
    });

    await humanRead(page);   // Pause like a real user
    await humanScroll(page, 'down');

    const data = await page.evaluate(() => ({
      followerCount: document.querySelector('[data-testid="follower-count"]')?.textContent,
      bio: document.querySelector('.-vDIg span')?.textContent
    }));

    return data;
  } finally {
    await browser.close();
  }
}

Multi-country rotation

multi-country.js
const { launchHuman } = require('human-browser');

const countries = ['ro', 'us', 'gb', 'de', 'jp'];

async function scrapeWithRotation(urls) {
  for (const [i, url] of urls.entries()) {
    const country = countries[i % countries.length];
    const { browser, page, humanRead } = await launchHuman({ country });

    await page.goto(url, { waitUntil: 'domcontentloaded' });
    await humanRead(page);

    const result = await page.evaluate(() => document.title);
    console.log(`[${country.toUpperCase()}] ${result}`);

    await browser.close();
    // Rate limiting: wait 2–5 seconds between requests
    await new Promise(r => setTimeout(r, 2000 + Math.random() * 3000));
  }
}

Common Errors and Fixes

Error: net::ERR_PROXY_CONNECTION_FAILED
✅ Fix: Check your PROXY_HOST and PROXY_PORT environment variables. Make sure the proxy server address is correct and the port is open. Try ping brd.superproxy.io to confirm connectivity.
Error: 407 Proxy Authentication Required
✅ Fix: Your PROXY_USER or PROXY_PASS is incorrect. Double-check your credentials from the humanbrowser.dev dashboard. Note that usernames are case-sensitive.
Error: Timeout 30000ms exceeded (on Cloudflare sites)
✅ Fix: Cloudflare challenge is taking too long to resolve. Increase timeout to 60000ms and add await sleep(5000) after page.goto(). If persistent, the IP may need to warm up — try a different country.
Error: 403 Forbidden despite residential IP
✅ Fix: Some sites block based on both IP and fingerprint. Make sure mobile: true is set in launchHuman() and you're not loading the page with waitUntil: 'networkidle' which triggers bot heuristics on some sites. Use 'domcontentloaded' instead.
Error: Bandwidth quota exceeded
✅ Fix: You've exceeded your monthly bandwidth. Upgrade to the Pro plan ($49.99/mo for 20GB) or add more bandwidth at $2.50/GB. Be mindful of loading heavy pages with many images — block unnecessary resources when possible.

FAQ

How do I add a proxy to Playwright?

Use the proxy option in chromium.launch() or newContext(). For residential proxies with authentication, pass server, username, and password. The human-browser package handles this automatically with launchHuman().

What is the difference between a datacenter proxy and a residential proxy?

A datacenter proxy routes through a server farm. Sites like Cloudflare, Instagram, and LinkedIn instantly detect and block these. A residential proxy routes through a real home internet connection — it's indistinguishable from a normal user browsing from their home.

Which countries work best for Playwright residential proxy?

Romania is the most cost-effective and works for most use cases. US IPs work well for US-specific content. UK IPs are useful for geo-locked content. Human Browser supports RO, US, UK, DE, NL, and JP.

Does Playwright support proxy authentication?

Yes. Playwright supports proxy authentication via the proxy.username and proxy.password fields in the context options. The human-browser package sets this up automatically from environment variables.

How do I block images to save bandwidth?

Use page.route() to intercept and abort image requests: await page.route('**/*.{png,jpg,gif,svg}', r => r.abort()). This can reduce bandwidth usage by 60–80% for text-heavy sites.

Get residential proxy credentials

Get started at humanbrowser.dev — residential proxy from $13.99/mo. Romania residential IP, iPhone 15 Pro fingerprint, bypasses Cloudflare out of the box.

Get Started — $13.99/mo →