Skip to main content

网络

介绍

🌐 Introduction

Playwright 提供了用于监控修改浏览器网络流量(包括 HTTP 和 HTTPS)的 API。页面发出的任何请求,包括 XHRfetch 请求,都可以被跟踪、修改和处理。

🌐 Playwright provides APIs to monitor and modify browser network traffic, both HTTP and HTTPS. Any requests that a page does, including XHRs and fetch requests, can be tracked, modified and handled.

模拟 API

🌐 Mock APIs

查看我们的API 模拟指南以了解更多相关信息

🌐 Check out our API mocking guide to learn more on how to

  • 模拟 API 请求并且从不访问 API
  • 执行 API 请求并修改响应
  • 使用 HAR 文件来模拟网络请求。

HTTP 认证

🌐 HTTP Authentication

执行 HTTP 身份验证。

🌐 Perform HTTP Authentication.

using var context = await Browser.NewContextAsync(new()
{
HttpCredentials = new HttpCredentials
{
Username = "bill",
Password = "pa55w0rd"
},
});
var page = await context.NewPageAsync();
await page.GotoAsync("https://example.com");

HTTP 代理

🌐 HTTP Proxy

你可以配置页面通过 HTTP(S) 代理或 SOCKSv5 加载。代理可以为整个浏览器全局设置,也可以单独为每个浏览器上下文设置。

🌐 You can configure pages to load over the HTTP(S) proxy or SOCKSv5. Proxy can be either set globally for the entire browser, or for each browser context individually.

你可以选择为 HTTP(S) 代理指定用户名和密码,也可以指定要绕过 代理 的主机。

🌐 You can optionally specify username and password for HTTP(S) proxy, you can also specify hosts to bypass the Proxy for.

这是全局代理的示例:

🌐 Here is an example of a global proxy:

var proxy = new Proxy
{
Server = "http://myproxy.com:3128",
Username = "user",
Password = "pwd"
};
await using var browser = await BrowserType.LaunchAsync(new()
{
Proxy = proxy
});

也可以按上下文指定它:

🌐 Its also possible to specify it per context:

await using var browser = await BrowserType.LaunchAsync();
await using var context = await browser.NewContextAsync(new()
{
Proxy = new Proxy { Server = "http://myproxy.com:3128" },
});

网络事件

🌐 Network events

你可以监控所有的 [请求] 和 [响应]:

🌐 You can monitor all the Requests and Responses:

using Microsoft.Playwright;

using var playwright = await Playwright.CreateAsync();
await using var browser = await playwright.Chromium.LaunchAsync();
var page = await browser.NewPageAsync();
page.Request += (_, request) => Console.WriteLine(">> " + request.Method + " " + request.Url);
page.Response += (_, response) => Console.WriteLine("<< " + response.Status + " " + response.Url);
await page.GotoAsync("https://example.com");

或者在按钮点击后等待网络响应,使用 Page.RunAndWaitForResponseAsync()

🌐 Or wait for a network response after the button click with Page.RunAndWaitForResponseAsync():

// Use a glob URL pattern
var waitForResponseTask = page.WaitForResponseAsync("**/api/fetch_data");
await page.GetByText("Update").ClickAsync();
var response = await waitForResponseTask;

变化

🌐 Variations

等待 Response,使用 Page.RunAndWaitForResponseAsync()

🌐 Wait for Responses with Page.RunAndWaitForResponseAsync()

// Use a regular expression
var waitForResponseTask = page.WaitForResponseAsync(new Regex("\\.jpeg$"));
await page.GetByText("Update").ClickAsync();
var response = await waitForResponseTask;

// Use a predicate taking a Response object
var waitForResponseTask = page.WaitForResponseAsync(r => r.Url.Contains(token));
await page.GetByText("Update").ClickAsync();
var response = await waitForResponseTask;

处理请求

🌐 Handle requests

你可以通过处理 Playwright 脚本中的网络请求来模拟 API 端点。

🌐 You can mock API endpoints via handling the network requests in your Playwright script.

变化

🌐 Variations

使用 BrowserContext.RouteAsync() 在整个浏览器上下文中设置路由,或使用 Page.RouteAsync() 在页面上设置路由。它将应用于弹出窗口和打开的链接。

🌐 Set up route on the entire browser context with BrowserContext.RouteAsync() or page with Page.RouteAsync(). It will apply to popup windows and opened links.

await page.RouteAsync("**/api/fetch_data", async route => {
await route.FulfillAsync(new() { Status = 200, Body = testData });
});
await page.GotoAsync("https://example.com");

修改请求

🌐 Modify requests

// Delete header
await page.RouteAsync("**/*", async route => {
var headers = new Dictionary<string, string>(route.Request.Headers.ToDictionary(x => x.Key, x => x.Value));
headers.Remove("X-Secret");
await route.ContinueAsync(new() { Headers = headers });
});

// Continue requests as POST.
await Page.RouteAsync("**/*", async route => await route.ContinueAsync(new() { Method = "POST" }));

你可以继续发送带有修改的请求。上面的例子是从发送的请求中移除一个 HTTP 头。

🌐 You can continue requests with modifications. Example above removes an HTTP header from the outgoing requests.

中止请求

🌐 Abort requests

你可以使用 Page.RouteAsync()Route.AbortAsync() 来中止请求。

🌐 You can abort requests using Page.RouteAsync() and Route.AbortAsync().

await page.RouteAsync("**/*.{png,jpg,jpeg}", route => route.AbortAsync());

// Abort based on the request type
await page.RouteAsync("**/*", async route => {
if ("image".Equals(route.Request.ResourceType))
await route.AbortAsync();
else
await route.ContinueAsync();
});

修改响应

🌐 Modify responses

要修改响应,请使用 APIRequestContext 获取原始响应,然后将响应传递给 Route.FulfillAsync()。你可以通过选项覆盖响应中的各个字段:

🌐 To modify a response use APIRequestContext to get the original response and then pass the response to Route.FulfillAsync(). You can override individual fields on the response via options:

await Page.RouteAsync("**/title.html", async route =>
{
// Fetch original response.
var response = await route.FetchAsync();
// Add a prefix to the title.
var body = await response.TextAsync();
body = body.Replace("<title>", "<title>My prefix:");

var headers = response.Headers;
headers.Add("Content-Type", "text/html");

await route.FulfillAsync(new()
{
// Pass all fields from the response.
Response = response,
// Override response body.
Body = body,
// Force content type to be html.
Headers = headers,
});
});

Glob URL 模式

🌐 Glob URL patterns

Playwright 在网络拦截方法中,如 Page.RouteAsync()Page.RunAndWaitForResponseAsync(),使用简化的通配符模式进行 URL 匹配。这些模式支持基本的通配符:

🌐 Playwright uses simplified glob patterns for URL matching in network interception methods like Page.RouteAsync() or Page.RunAndWaitForResponseAsync(). These patterns support basic wildcards:

  1. 星号:
    • 单个 * 匹配除 / 之外的任意字符
    • 双重 ** 匹配包括 / 在内的任意字符
  2. 问号 ? 只匹配问号 ?。如果你想匹配任意字符,请使用 *
  3. 大括号 {} 可用于匹配由逗号分隔的选项列表 ,
  4. 反斜杠 \ 可用于转义任何特殊字符(注意,如果要转义反斜杠本身,则写作 \\

示例:

🌐 Examples:

  • https://example.com/*.js 匹配 https://example.com/file.js 但不匹配 https://example.com/path/file.js
  • https://example.com/?page=1 匹配 https://example.com/?page=1 但不匹配 https://example.com
  • **/*.js 同时匹配 https://example.com/file.jshttps://example.com/path/file.js
  • **/*.{png,jpg,jpeg} 匹配所有图片请求

重要说明:

🌐 Important notes:

  • glob 模式必须匹配整个 URL,而不仅仅是其中的一部分。
  • 使用 glob 进行 URL 匹配时,请考虑完整的 URL 结构,包括协议和路径分隔符。
  • 对于更复杂的匹配要求,请考虑使用 [RegExp] 而不是 glob 模式。

WebSockets

Playwright 原生支持 WebSockets 的检查、模拟和修改。请参阅我们的 API 模拟指南 了解如何模拟 WebSockets。

🌐 Playwright supports WebSockets inspection, mocking and modifying out of the box. See our API mocking guide to learn how to mock WebSockets.

每当创建一个 WebSocket 时,都会触发 Page.WebSocket 事件。此事件包含 WebSocket 实例,以便进一步检查 WebSocket 帧:

🌐 Every time a WebSocket is created, the Page.WebSocket event is fired. This event contains the WebSocket instance for further web socket frames inspection:

page.WebSocket += (_, ws) =>
{
Console.WriteLine("WebSocket opened: " + ws.Url);
ws.FrameSent += (_, f) => Console.WriteLine(f.Text);
ws.FrameReceived += (_, f) => Console.WriteLine(f.Text);
ws.Close += (_, ws1) => Console.WriteLine("WebSocket closed");
};

缺少网络事件和 Service Worker

🌐 Missing Network Events and Service Workers

Playwright 内置的 BrowserContext.RouteAsync()Page.RouteAsync() 允许你的测试原生地路由请求,并进行模拟和拦截。

🌐 Playwright's built-in BrowserContext.RouteAsync() and Page.RouteAsync() allow your tests to natively route requests and perform mocking and interception.

如果你正在使用 Playwright 的原生 BrowserContext.RouteAsync()Page.RouteAsync(),并且发现网络事件缺失,可以通过将 ServiceWorkers 设置为 'block' 来禁用 Service Workers。

🌐 If you're using Playwright's native BrowserContext.RouteAsync() and Page.RouteAsync(), and it appears network events are missing, disable Service Workers by setting ServiceWorkers to 'block'.

可能是你正在使用像 Mock Service Worker (MSW) 这样的模拟工具。虽然这个工具开箱即用可以模拟响应,但它会添加自己的 Service Worker 来接管网络请求,因此使这些请求对 BrowserContext.RouteAsync()Page.RouteAsync() 来说不可见。如果你对网络测试和模拟都感兴趣,可以考虑使用内置的 BrowserContext.RouteAsync()Page.RouteAsync() 来进行 响应模拟

🌐 It might be that you are using a mock tool such as Mock Service Worker (MSW). While this tool works out of the box for mocking responses, it adds its own Service Worker that takes over the network requests, hence making them invisible to BrowserContext.RouteAsync() and Page.RouteAsync(). If you are interested in both network testing and mocking, consider using built-in BrowserContext.RouteAsync() and Page.RouteAsync() for response mocking.