集成 · 中级

在 Puppeteer 和无头 Chrome 中使用代理

Chrome 通过启动参数接收代理,Puppeteer 则为每个页面提供凭据。一个浏览器对应一个出口,粘性会话可让该出口持续有效。

阅读约需 2 分钟 5 个章节 更新于 发布于

使用代理启动并进行身份验证#

Node.js
import puppeteer from "puppeteer";

const browser = await puppeteer.launch({
  headless: true,
  args: ["--proxy-server=http://res.proxshift.com:9000", "--no-first-run"],
});
const page = await browser.newPage();
await page.authenticate({ username: "USER-cc-us-sid-run1-ttl-30m", password: "PASS" });

await page.goto("https://api.ipify.org", { waitUntil: "domcontentloaded", timeout: 45000 });
console.log(await page.evaluate(() => document.body.innerText));
await browser.close();

每次打开页面后,都要在首次导航前调用 page.authenticate;Chrome 会按页面请求代理凭据。用户名中包含国家/地区和会话 ID,因此在设定的有效期内,整个浏览器都会使用同一个家庭住宅出口。

每个浏览器使用一个代理#

Chrome 会将 --proxy-server 应用于整个浏览器实例。若需要多个国家/地区或会话,请运行多个浏览器(无头模式的开销很低),或建立 puppeteer.launch 工作池,让每个 worker 持有一个会话 ID。声称支持按页面代理的库会插入本地转发器;每个会话使用一个浏览器更为简单。

屏蔽图片、字体和媒体#

请求拦截
await page.setRequestInterception(true);
page.on("request", (req) => {
  const t = req.resourceType();
  if (["image", "media", "font", "stylesheet"].includes(t)) return req.abort();
  req.continue();
});

保持环境一致#

  • Accept-Language 和时区设为出口所在国家/地区:使用 page.setExtraHTTPHeaders({\"Accept-Language\": \"de-DE,de;q=0.9\"})page.emulateTimezone(\"Europe/Berlin\")
  • 在启动参数中加入 --force-webrtc-ip-handling-policy=disable_non_proxied_udp,防止 WebRTC 泄漏。
  • 每个账号使用一个浏览器;若账号需要表现为曾经访问过的设备,请复用其用户数据目录。

常见错误#

现象原因解决方法
net::ERR_TUNNEL_CONNECTION_FAILED网关拒绝 CONNECT:凭据或参数错误,或没有可用出口使用 cURL -v 重现问题并读取网关状态码
net::ERR_PROXY_AUTH_UNSUPPORTED / 弹出提示在导航后才调用 authenticate()在 goto 前调用 page.authenticate
每个浏览器都显示相同 IP重复使用了同一个会话 ID每个浏览器使用不同的 -sid-,或将其省略
首次加载非常慢家庭住宅出口加上资源繁重的页面屏蔽资源;将超时提高至 45 秒

大家常问的问题#

Puppeteer 可以使用带密码的 SOCKS5 吗?

Chrome 不支持 SOCKS5 身份验证。请配合 page.authenticate 使用 9000 端口的 HTTP 代理,或将服务器 IP 加入白名单,并传入 --proxy-server=socks5://res.proxshift.com:9001。

准备好即可开始

立即投入实际使用。

创建账户,充值 $20,然后将本指南中的端点粘贴到您的工具中。您购买的流量永不过期。