我正在使用新的 WebView2 控件(在开发人员预览版中(来替换 Windows.Forms 应用程序中的 WebBrowser 控件。
切换到WebView2控件的主要原因是它基于与WebRTC一起工作的Chromium,而WebBrowser控件由不支持WebRTC的Internet Explorer提供支持。
所以我遇到的问题是找到一种方法来为我希望 WebView2 导航到的 url 设置 cookie。 过去,在使用WebBrowser时,可以通过在webBrowser.Navigate之前调用InternetSetCookie来设置cookie,但InternetSetCookie仅适用于Internet Explorer。
Cookie 需要设置为在第三方网站上进行身份验证,即向网站证明我的应用程序已经登录(由我的应用程序的其他未使用 WebView2 的部分提前完成(。 该应用程序成功捕获了登录响应中的身份验证 cookie,但我只是找不到在使用 WebView2 控件导航时如何将 cookie 传递回网站。 WebView2 控件用于导航到同一网站上使用 WebRTC 的另一个页面。
https://github.com/MicrosoftEdge/WebViewFeedback/issues/4 解释说,目前还没有提供用于在 WebView2 中设置 cookie 的快速机制,但建议处理 WebResourceRequested 事件,然后通过修改请求来设置 Cookie。来自 WebResourceRequest 事件处理程序内部的标头。
那么谁能解释一下如何实际让 WebResourceRequest 事件为 WebView2 触发? 我尝试过这个不成功:
private string myUrl = "https://www.somedomain.com";
private void WebView_CoreWebView2Ready(object sender, EventArgs e)
{
webView.CoreWebView2.AddWebResourceRequestedFilter(myUrl,CoreWebView2WebResourceContext.All);
webView.CoreWebView2.WebResourceRequested += CoreWebView2_WebResourceRequested;
}
private void CoreWebView2_WebResourceRequested(object sender, CoreWebView2WebResourceRequestedEventArgs e)
{
Uri myUri = new Uri(myUrl);
if (myUri.IsBaseOf(e.Request.RequestUri))
{
e.Request.Headers.Add("Cookie", cookieName, authToken);
}
}
WebResourceRequest事件永远不会触发。 我尝试通过调用WebView2.Navigate,WebView2.CoreWebView2.Naving和WebView2.Source来触发它,但它们都不会导致WebResourceRequest事件触发。
我之所以从事件中挂接 WebResourceRequest 的事件处理程序WebView_CoreWebView2Ready是因为如果您尝试更早地挂接它(例如在表单加载中(,那么 CoreWebView2 将为空,因为它需要更多时间。 我已经成功地挂接到了WebView_CoreWebView2Ready内部的其他事件,并且它们确实触发了(例如 NavigationStart 事件(。
谢谢。
仅当资源的活动筛选器存在且该筛选器匹配时,才会触发 WebResource Request 事件。可以使用以下命令添加截获所有请求的筛选器
WebView2.CoreWebView2.AddWebResourceRequestedFilter("*", CoreWebView2WebResourceContext.All);
要缩小和更新您感兴趣的实际请求的筛选器,您可以在 CoreWebView2OnWebResourceRequest 事件中检查args.Request.RequestUri
。
通过创建本地服务器并通过 WebView 连接到它,您可以看到 WebView 预览在将 .NET HttpRequest 转换为 Web View 本身使用的 COM WebRequest 时不会复制 Cookie。
using (HttpListener listener = new HttpListener())
{
listener.Prefixes.Add($"http://localhost:8080/");
listener.Start();
while (listener.IsListening)
{
var context = await listener.GetContextAsync();
using (var response = context.Response)
{
for (int i = 0; i < context.Request.Headers.Count; i++)
{
Console.WriteLine($"{context.Request.Headers.GetKey(i)} : {context.Request.Headers.Get(i)}");
}
using (var writer = new StreamWriter(response.OutputStream))
{
context.Response.ContentType = "text";
writer.WriteLine("Test.");
writer.Flush();
}
}
}
}
您可能应该提交 Edge WebView 预览版的错误报告。
我发现我无法在 WebResourceRequest 事件处理程序中从内部设置 cookie 的原因是因为这是一个已知的错误,已经报告给Microsoft这里:
无法在 Web资源请求的事件处理程序中设置标头
因此,总而言之,我的代码确实显示了添加cookie的正确方法,但是在Microsoft修复错误之前,它不起作用。
我很欣赏这个答案没有提供解决方法,但它至少回答了为什么代码当前无法添加 cookie 的问题。