WebView2 中的新 Sec-* headers
New Sec-* headers in WebView2
在 C++ 中使用 MS WebView2,如果访问 https://manytools.org/http-html-text/http-request-headers/
,我可以看到许多“Sec-*”-headers
举几个例子:
Sec-Fetch-Dest document
Sec-Fetch-User ?1
Sec-Fetch-Mode navigate
Sec-Fetch-Site none
Sec-Ch-Ua-Mobile ?0
Sec-Ch-Ua "Not A;Brand";v="99", "Chromium";v="100", "Microsoft Edge";v="100", "Microsoft Edge WebView2";v="100"
这些新的 headers 在 https://wicg.github.io/ua-client-hints/
中提到
有什么方法可以 access/edit 那些 headers,最好是在 C++ 中?
可以使用命令行选项禁用 Sec-Ch headers:
--disable-features=UserAgentClientHint
并从 C++ 执行此操作:
Microsoft::WRL::ComPtr<CoreWebView2EnvironmentOptions> options = Microsoft::WRL::Make<CoreWebView2EnvironmentOptions>();
options->put_AdditionalBrowserArguments(L"--disable-features=UserAgentClientHint");
但是,我希望能够编辑这些值。
进一步的谷歌搜索显示了这个页面,我猜它回答了这个 post:
https://developer.mozilla.org/en-US/docs/Glossary/Forbidden_header_name
你说得对 sec-*
header 是“禁止 header”列表的一部分。但是它们被禁止用于客户端代码,例如在 user-agent 上运行的 JS。但是 user-agent 浏览器可以设置这些字段。
您可以更改添加到 add_WebResourceRequested
的回调中的某些 sec-*
header。一些字段如 Sec-Fetch-Site
之后会被覆盖,其他字段如 Sec-Fetch-Mode
可以设置,但不能删除,因为如果在 WebResourceRequestedEvent 之后未设置,它们将获得默认值。但是您可以像这样更改大多数 sec-ch
:
注意:这段代码只是为了演示方法,它缺少一堆错误处理
EventRegistrationToken webResourceRequestedToken;
webviewWindow->AddWebResourceRequestedFilter(L"*", COREWEBVIEW2_WEB_RESOURCE_CONTEXT_ALL);
webviewWindow->add_WebResourceRequested(
Callback<ICoreWebView2WebResourceRequestedEventHandler>([](ICoreWebView2* sender,
ICoreWebView2WebResourceRequestedEventArgs* args) {
COREWEBVIEW2_WEB_RESOURCE_CONTEXT resourceContext;
args->get_ResourceContext(&resourceContext);
ICoreWebView2WebResourceRequest* req = nullptr;
ICoreWebView2HttpRequestHeaders* headers = nullptr;
ICoreWebView2HttpHeadersCollectionIterator* iter = nullptr;
args->get_Request(&req);
req->get_Headers(&headers);
headers->GetIterator(&iter);
BOOL hasCurrent = FALSE;
iter->get_HasCurrentHeader(&hasCurrent);
std::vector<std::wstring> headersToDelete;
std::wstring secChPrefix = L"sec-ch";
while (hasCurrent) {
LPWSTR name = nullptr, value = nullptr;
iter->GetCurrentHeader(&name, &value);
if (secChPrefix.compare(0, secChPrefix.size(), name, secChPrefix.size()) == 0) {
headersToDelete.push_back(name);
}
iter->MoveNext(&hasCurrent);
}
for (auto header : headersToDelete) {
headers->RemoveHeader(header.c_str());
}
// Setting "Sec-Fetch-Site" will have no effect, will get overwritten afterwards
headers->SetHeader(L"Sec-Fetch-Site", L"same-origin");
// This will work, but removing this key will just make it take the default value
headers->SetHeader(L"Sec-Fetch-Mode", L"same-origin");
return S_OK;
}).Get(),
&webResourceRequestedToken);
在 C++ 中使用 MS WebView2,如果访问 https://manytools.org/http-html-text/http-request-headers/
,我可以看到许多“Sec-*”-headers举几个例子:
Sec-Fetch-Dest document
Sec-Fetch-User ?1
Sec-Fetch-Mode navigate
Sec-Fetch-Site none
Sec-Ch-Ua-Mobile ?0
Sec-Ch-Ua "Not A;Brand";v="99", "Chromium";v="100", "Microsoft Edge";v="100", "Microsoft Edge WebView2";v="100"
这些新的 headers 在 https://wicg.github.io/ua-client-hints/
中提到有什么方法可以 access/edit 那些 headers,最好是在 C++ 中?
可以使用命令行选项禁用 Sec-Ch headers:
--disable-features=UserAgentClientHint
并从 C++ 执行此操作:
Microsoft::WRL::ComPtr<CoreWebView2EnvironmentOptions> options = Microsoft::WRL::Make<CoreWebView2EnvironmentOptions>();
options->put_AdditionalBrowserArguments(L"--disable-features=UserAgentClientHint");
但是,我希望能够编辑这些值。
进一步的谷歌搜索显示了这个页面,我猜它回答了这个 post: https://developer.mozilla.org/en-US/docs/Glossary/Forbidden_header_name
你说得对 sec-*
header 是“禁止 header”列表的一部分。但是它们被禁止用于客户端代码,例如在 user-agent 上运行的 JS。但是 user-agent 浏览器可以设置这些字段。
您可以更改添加到 add_WebResourceRequested
的回调中的某些 sec-*
header。一些字段如 Sec-Fetch-Site
之后会被覆盖,其他字段如 Sec-Fetch-Mode
可以设置,但不能删除,因为如果在 WebResourceRequestedEvent 之后未设置,它们将获得默认值。但是您可以像这样更改大多数 sec-ch
:
注意:这段代码只是为了演示方法,它缺少一堆错误处理
EventRegistrationToken webResourceRequestedToken;
webviewWindow->AddWebResourceRequestedFilter(L"*", COREWEBVIEW2_WEB_RESOURCE_CONTEXT_ALL);
webviewWindow->add_WebResourceRequested(
Callback<ICoreWebView2WebResourceRequestedEventHandler>([](ICoreWebView2* sender,
ICoreWebView2WebResourceRequestedEventArgs* args) {
COREWEBVIEW2_WEB_RESOURCE_CONTEXT resourceContext;
args->get_ResourceContext(&resourceContext);
ICoreWebView2WebResourceRequest* req = nullptr;
ICoreWebView2HttpRequestHeaders* headers = nullptr;
ICoreWebView2HttpHeadersCollectionIterator* iter = nullptr;
args->get_Request(&req);
req->get_Headers(&headers);
headers->GetIterator(&iter);
BOOL hasCurrent = FALSE;
iter->get_HasCurrentHeader(&hasCurrent);
std::vector<std::wstring> headersToDelete;
std::wstring secChPrefix = L"sec-ch";
while (hasCurrent) {
LPWSTR name = nullptr, value = nullptr;
iter->GetCurrentHeader(&name, &value);
if (secChPrefix.compare(0, secChPrefix.size(), name, secChPrefix.size()) == 0) {
headersToDelete.push_back(name);
}
iter->MoveNext(&hasCurrent);
}
for (auto header : headersToDelete) {
headers->RemoveHeader(header.c_str());
}
// Setting "Sec-Fetch-Site" will have no effect, will get overwritten afterwards
headers->SetHeader(L"Sec-Fetch-Site", L"same-origin");
// This will work, but removing this key will just make it take the default value
headers->SetHeader(L"Sec-Fetch-Mode", L"same-origin");
return S_OK;
}).Get(),
&webResourceRequestedToken);