blob: 6a1346a619a4c6ff69aebfd3ebd976eb613d3a74 [file] [log] [blame]
// Copyright 2017 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "base/command_line.h"
#include "base/run_loop.h"
#include "base/stl_util.h"
#include "base/test/histogram_tester.h"
#include "chrome/browser/content_settings/cookie_settings_factory.h"
#include "chrome/browser/content_settings/host_content_settings_map_factory.h"
#include "chrome/browser/metrics/subprocess_metrics_provider.h"
#include "chrome/browser/net/url_request_mock_util.h"
#include "chrome/browser/profiles/profile.h"
#include "chrome/browser/ui/browser.h"
#include "chrome/test/base/in_process_browser_test.h"
#include "chrome/test/base/ui_test_utils.h"
#include "components/content_settings/core/browser/cookie_settings.h"
#include "components/content_settings/core/browser/host_content_settings_map.h"
#include "components/content_settings/core/common/pref_names.h"
#include "components/prefs/pref_service.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/common/browser_side_navigation_policy.h"
#include "content/public/common/content_switches.h"
#include "content/public/test/browser_test_utils.h"
#include "content/public/test/test_utils.h"
#include "net/test/embedded_test_server/embedded_test_server.h"
#include "net/test/embedded_test_server/http_request.h"
class ClientHintsBrowserTest : public InProcessBrowserTest {
public:
ClientHintsBrowserTest()
: http_server_(net::EmbeddedTestServer::TYPE_HTTP),
https_server_(net::EmbeddedTestServer::TYPE_HTTPS),
expect_client_hints_(false),
expect_client_hints_on_main_frame_only_(false),
count_client_hints_headers_seen_(0) {
http_server_.ServeFilesFromSourceDirectory("chrome/test/data/client_hints");
https_server_.ServeFilesFromSourceDirectory(
"chrome/test/data/client_hints");
http_server_.RegisterRequestMonitor(
base::Bind(&ClientHintsBrowserTest::MonitorResourceRequest,
base::Unretained(this)));
https_server_.RegisterRequestMonitor(
base::Bind(&ClientHintsBrowserTest::MonitorResourceRequest,
base::Unretained(this)));
EXPECT_TRUE(http_server_.Start());
EXPECT_TRUE(https_server_.Start());
accept_ch_with_lifetime_http_local_url_ =
http_server_.GetURL("/accept_ch_with_lifetime.html");
EXPECT_TRUE(accept_ch_with_lifetime_http_local_url_.SchemeIsHTTPOrHTTPS());
EXPECT_FALSE(
accept_ch_with_lifetime_http_local_url_.SchemeIsCryptographic());
accept_ch_with_lifetime_url_ =
https_server_.GetURL("/accept_ch_with_lifetime.html");
EXPECT_TRUE(accept_ch_with_lifetime_url_.SchemeIsHTTPOrHTTPS());
EXPECT_TRUE(accept_ch_with_lifetime_url_.SchemeIsCryptographic());
accept_ch_without_lifetime_url_ =
https_server_.GetURL("/accept_ch_without_lifetime.html");
EXPECT_TRUE(accept_ch_with_lifetime_url_.SchemeIsHTTPOrHTTPS());
EXPECT_TRUE(accept_ch_with_lifetime_url_.SchemeIsCryptographic());
without_accept_ch_without_lifetime_url_ =
https_server_.GetURL("/without_accept_ch_without_lifetime.html");
EXPECT_TRUE(without_accept_ch_without_lifetime_url_.SchemeIsHTTPOrHTTPS());
EXPECT_TRUE(
without_accept_ch_without_lifetime_url_.SchemeIsCryptographic());
without_accept_ch_without_lifetime_local_url_ =
http_server_.GetURL("/without_accept_ch_without_lifetime.html");
EXPECT_TRUE(
without_accept_ch_without_lifetime_local_url_.SchemeIsHTTPOrHTTPS());
EXPECT_FALSE(
without_accept_ch_without_lifetime_local_url_.SchemeIsCryptographic());
}
~ClientHintsBrowserTest() override {}
void SetUpOnMainThread() override {
content::BrowserThread::PostTask(
content::BrowserThread::IO, FROM_HERE,
base::BindOnce(&chrome_browser_net::SetUrlRequestMocksEnabled, true));
}
void SetUpCommandLine(base::CommandLine* cmd) override {
cmd->AppendSwitch(switches::kEnableExperimentalWebPlatformFeatures);
}
void SetClientHintExpectations(bool expect_client_hints) {
expect_client_hints_ = expect_client_hints;
}
void SetClientHintExpectationsOnMainFrameOnly(bool expect_client_hints) {
expect_client_hints_on_main_frame_only_ = expect_client_hints;
}
const GURL& accept_ch_with_lifetime_http_local_url() const {
return accept_ch_with_lifetime_http_local_url_;
}
// A URL whose response headers include Accept-CH and Accept-CH-Lifetime
// headers.
const GURL& accept_ch_with_lifetime_url() const {
return accept_ch_with_lifetime_url_;
}
// A URL whose response headers include only Accept-CH header.
const GURL& accept_ch_without_lifetime_url() const {
return accept_ch_without_lifetime_url_;
}
// A URL whose response headers do not include either Accept-CH or
// Accept-CH-Lifetime headers. Navigating to this URL also fetches an image.
const GURL& without_accept_ch_without_lifetime_url() const {
return without_accept_ch_without_lifetime_url_;
}
// A URL whose response headers do not include either Accept-CH or
// Accept-CH-Lifetime headers. Navigating to this URL also fetches an image.
const GURL& without_accept_ch_without_lifetime_local_url() const {
return without_accept_ch_without_lifetime_local_url_;
}
size_t count_client_hints_headers_seen() const {
return count_client_hints_headers_seen_;
}
private:
// Called by |https_server_|.
void MonitorResourceRequest(const net::test_server::HttpRequest& request) {
bool is_main_frame_navigation =
request.GetURL().spec().find(".html") != std::string::npos;
// When browser side navigation is enabled, dpr headers is not attached to
// the main frame request.
if (!expect_client_hints_on_main_frame_only_) {
EXPECT_EQ(
expect_client_hints_ && (!content::IsBrowserSideNavigationEnabled() ||
!is_main_frame_navigation),
base::ContainsKey(request.headers, "dpr"));
} else {
EXPECT_EQ(expect_client_hints_on_main_frame_only_ &&
is_main_frame_navigation &&
(!content::IsBrowserSideNavigationEnabled() ||
!is_main_frame_navigation),
base::ContainsKey(request.headers, "dpr"));
}
// When browser side navigation is enabled, device-memory header is attached
// to the main frame request.
if (!expect_client_hints_on_main_frame_only_) {
EXPECT_EQ(expect_client_hints_,
base::ContainsKey(request.headers, "device-memory"));
} else {
EXPECT_EQ(expect_client_hints_ && is_main_frame_navigation,
base::ContainsKey(request.headers, "device-memory"));
}
if (base::ContainsKey(request.headers, "dpr"))
count_client_hints_headers_seen_++;
if (base::ContainsKey(request.headers, "device-memory"))
count_client_hints_headers_seen_++;
}
net::EmbeddedTestServer http_server_;
net::EmbeddedTestServer https_server_;
GURL accept_ch_with_lifetime_http_local_url_;
GURL accept_ch_with_lifetime_url_;
GURL accept_ch_without_lifetime_url_;
GURL without_accept_ch_without_lifetime_url_;
GURL without_accept_ch_without_lifetime_local_url_;
bool expect_client_hints_;
// Expect client hints only on the main frame request, and not on
// subresources.
bool expect_client_hints_on_main_frame_only_;
size_t count_client_hints_headers_seen_;
DISALLOW_COPY_AND_ASSIGN(ClientHintsBrowserTest);
};
// Loads a webpage that requests persisting of client hints. Verifies that
// the browser receives the mojo notification from the renderer and persists the
// client hints to the disk.
IN_PROC_BROWSER_TEST_F(ClientHintsBrowserTest, ClientHintsHttps) {
base::HistogramTester histogram_tester;
ui_test_utils::NavigateToURL(browser(), accept_ch_with_lifetime_url());
histogram_tester.ExpectUniqueSample("ClientHints.UpdateEventCount", 1, 1);
content::FetchHistogramsFromChildProcesses();
SubprocessMetricsProvider::MergeHistogramDeltasForTesting();
// client_hints_url() sets two client hints.
histogram_tester.ExpectUniqueSample("ClientHints.UpdateSize", 2, 1);
// accept_ch_with_lifetime_url() sets client hints persist duration to 3600
// seconds.
histogram_tester.ExpectUniqueSample("ClientHints.PersistDuration",
3600 * 1000, 1);
}
// Loads a HTTP local webpage (which qualifies as a secure context) that
// requests persisting of client hints. Verifies that the browser receives the
// mojo notification from the renderer and persists the client hints to the
// disk.
IN_PROC_BROWSER_TEST_F(ClientHintsBrowserTest,
ClientHintsLifetimeFollowedByNoClientHintHttpLocal) {
base::HistogramTester histogram_tester;
ContentSettingsForOneType host_settings;
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(0u, host_settings.size());
ui_test_utils::NavigateToURL(browser(),
accept_ch_with_lifetime_http_local_url());
histogram_tester.ExpectUniqueSample("ClientHints.UpdateEventCount", 1, 1);
content::FetchHistogramsFromChildProcesses();
SubprocessMetricsProvider::MergeHistogramDeltasForTesting();
// client_hints_url() sets two client hints.
histogram_tester.ExpectUniqueSample("ClientHints.UpdateSize", 2, 1);
// accept_ch_with_lifetime_http_local_url() sets client hints persist duration
// to 3600 seconds.
histogram_tester.ExpectUniqueSample("ClientHints.PersistDuration",
3600 * 1000, 1);
base::RunLoop().RunUntilIdle();
// Clients hints preferences for one origin should be persisted.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(1u, host_settings.size());
SetClientHintExpectations(true);
ui_test_utils::NavigateToURL(browser(),
without_accept_ch_without_lifetime_local_url());
if (content::IsBrowserSideNavigationEnabled()) {
// When browser side navigation is enabled, two client hints are attached to
// the image request, and the device-memory header is attached to the main
// frame request.
EXPECT_EQ(3u, count_client_hints_headers_seen());
} else {
// When browser side navigation is not enabled, two client hints are
// attached to each of the HTML and the image requests.
EXPECT_EQ(4u, count_client_hints_headers_seen());
}
}
// Loads a webpage that does not request persisting of client hints.
IN_PROC_BROWSER_TEST_F(ClientHintsBrowserTest, NoClientHintsHttps) {
base::HistogramTester histogram_tester;
ui_test_utils::NavigateToURL(browser(),
without_accept_ch_without_lifetime_url());
histogram_tester.ExpectTotalCount("ClientHints.UpdateEventCount", 0);
content::FetchHistogramsFromChildProcesses();
SubprocessMetricsProvider::MergeHistogramDeltasForTesting();
// no_client_hints_url() does not sets the client hints.
histogram_tester.ExpectTotalCount("ClientHints.UpdateSize", 0);
histogram_tester.ExpectTotalCount("ClientHints.PersistDuration", 0);
}
IN_PROC_BROWSER_TEST_F(ClientHintsBrowserTest,
ClientHintsLifetimeFollowedByNoClientHint) {
base::HistogramTester histogram_tester;
ContentSettingsForOneType host_settings;
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(0u, host_settings.size());
// Fetching accept_ch_with_lifetime_url() should persist the request for
// client hints.
ui_test_utils::NavigateToURL(browser(), accept_ch_with_lifetime_url());
histogram_tester.ExpectUniqueSample("ClientHints.UpdateEventCount", 1, 1);
content::FetchHistogramsFromChildProcesses();
SubprocessMetricsProvider::MergeHistogramDeltasForTesting();
// client_hints_url() sets two client hints.
histogram_tester.ExpectUniqueSample("ClientHints.UpdateSize", 2, 1);
// accept_ch_with_lifetime_url() sets client hints persist duration to 3600
// seconds.
histogram_tester.ExpectUniqueSample("ClientHints.PersistDuration",
3600 * 1000, 1);
base::RunLoop().RunUntilIdle();
// Clients hints preferences for one origin should be persisted.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(1u, host_settings.size());
SetClientHintExpectations(true);
ui_test_utils::NavigateToURL(browser(),
without_accept_ch_without_lifetime_url());
if (content::IsBrowserSideNavigationEnabled()) {
// When browser side navigation is enabled, two client hints are attached to
// the image request, and the device-memory header is attached to the main
// frame request.
EXPECT_EQ(3u, count_client_hints_headers_seen());
} else {
// When browser side navigation is not enabled, two client hints are
// attached to each of the HTML and the image requests.
EXPECT_EQ(4u, count_client_hints_headers_seen());
}
}
// Ensure that when cookies are blocked, client hint preferences are not
// persisted.
IN_PROC_BROWSER_TEST_F(ClientHintsBrowserTest,
ClientHintsLifetimeNotPersistedCookiesBlocked) {
scoped_refptr<content_settings::CookieSettings> cookie_settings_ =
CookieSettingsFactory::GetForProfile(browser()->profile());
base::HistogramTester histogram_tester;
ContentSettingsForOneType host_settings;
// Block cookies.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->SetContentSettingDefaultScope(accept_ch_without_lifetime_url(), GURL(),
CONTENT_SETTINGS_TYPE_COOKIES,
std::string(), CONTENT_SETTING_BLOCK);
// Fetching accept_ch_with_lifetime_url() should not persist the request for
// client hints since cookies are blocked.
ui_test_utils::NavigateToURL(browser(), accept_ch_with_lifetime_url());
histogram_tester.ExpectTotalCount("ClientHints.UpdateEventCount", 0);
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(0u, host_settings.size());
// Allow cookies.
cookie_settings_->SetCookieSetting(accept_ch_without_lifetime_url(),
CONTENT_SETTING_ALLOW);
// Fetching accept_ch_with_lifetime_url() should persist the request for
// client hints since cookies are allowed.
ui_test_utils::NavigateToURL(browser(), accept_ch_with_lifetime_url());
histogram_tester.ExpectTotalCount("ClientHints.UpdateEventCount", 1);
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(1u, host_settings.size());
}
IN_PROC_BROWSER_TEST_F(ClientHintsBrowserTest,
ClientHintsLifetimeNotAttachedCookiesBlocked) {
base::HistogramTester histogram_tester;
ContentSettingsForOneType host_settings;
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(0u, host_settings.size());
// Fetching accept_ch_with_lifetime_url() should persist the request for
// client hints.
ui_test_utils::NavigateToURL(browser(), accept_ch_with_lifetime_url());
histogram_tester.ExpectUniqueSample("ClientHints.UpdateEventCount", 1, 1);
content::FetchHistogramsFromChildProcesses();
SubprocessMetricsProvider::MergeHistogramDeltasForTesting();
// client_hints_url() sets two client hints.
histogram_tester.ExpectUniqueSample("ClientHints.UpdateSize", 2, 1);
// accept_ch_with_lifetime_url() tries to set client hints persist duration to
// 3600 seconds.
histogram_tester.ExpectUniqueSample("ClientHints.PersistDuration",
3600 * 1000, 1);
base::RunLoop().RunUntilIdle();
// Clients hints preferences for one origin should be persisted.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(1u, host_settings.size());
// Block the cookies: Client hints should not be attached.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->SetContentSettingDefaultScope(accept_ch_without_lifetime_url(), GURL(),
CONTENT_SETTINGS_TYPE_COOKIES,
std::string(), CONTENT_SETTING_BLOCK);
ui_test_utils::NavigateToURL(browser(),
without_accept_ch_without_lifetime_url());
EXPECT_EQ(0u, count_client_hints_headers_seen());
// Allow the cookies: Client hints should now be attached.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->SetContentSettingDefaultScope(accept_ch_without_lifetime_url(), GURL(),
CONTENT_SETTINGS_TYPE_COOKIES,
std::string(), CONTENT_SETTING_ALLOW);
SetClientHintExpectations(true);
ui_test_utils::NavigateToURL(browser(),
without_accept_ch_without_lifetime_url());
if (content::IsBrowserSideNavigationEnabled()) {
// When browser side navigation is enabled, two client hints are attached to
// the image request, and the device-memory header is attached to the main
// frame request.
EXPECT_EQ(3u, count_client_hints_headers_seen());
} else {
// When browser side navigation is not enabled, two client hints are
// attached to each of the HTML and the image requests.
EXPECT_EQ(4u, count_client_hints_headers_seen());
}
// Clear settings.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->ClearSettingsForOneType(CONTENT_SETTINGS_TYPE_COOKIES);
}
// Ensure that when the JavaScript is blocked, client hint preferences are not
// persisted.
IN_PROC_BROWSER_TEST_F(ClientHintsBrowserTest,
ClientHintsLifetimeNotPersistedJavaScriptBlocked) {
ContentSettingsForOneType host_settings;
// Start a navigation. This navigation makes it possible to block JavaScript
// later.
ui_test_utils::NavigateToURL(browser(),
without_accept_ch_without_lifetime_url());
// Block the JavaScript: Client hint preferences should not be persisted.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->SetContentSettingDefaultScope(accept_ch_with_lifetime_url(), GURL(),
CONTENT_SETTINGS_TYPE_JAVASCRIPT,
std::string(), CONTENT_SETTING_BLOCK);
ui_test_utils::NavigateToURL(browser(), accept_ch_with_lifetime_url());
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(0u, host_settings.size());
// Allow the JavaScript: Client hint preferences should be persisted.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->SetContentSettingDefaultScope(accept_ch_with_lifetime_url(), GURL(),
CONTENT_SETTINGS_TYPE_JAVASCRIPT,
std::string(), CONTENT_SETTING_ALLOW);
ui_test_utils::NavigateToURL(browser(), accept_ch_with_lifetime_url());
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(1u, host_settings.size());
}
// Ensure that when the JavaScript is blocked, persisted client hints are not
// attached to the request headers.
IN_PROC_BROWSER_TEST_F(ClientHintsBrowserTest,
ClientHintsLifetimeNotAttachedJavaScriptBlocked) {
base::HistogramTester histogram_tester;
ContentSettingsForOneType host_settings;
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(0u, host_settings.size());
// Fetching accept_ch_with_lifetime_url() should persist the request for
// client hints.
ui_test_utils::NavigateToURL(browser(), accept_ch_with_lifetime_url());
histogram_tester.ExpectUniqueSample("ClientHints.UpdateEventCount", 1, 1);
content::FetchHistogramsFromChildProcesses();
SubprocessMetricsProvider::MergeHistogramDeltasForTesting();
// client_hints_url() sets two client hints.
histogram_tester.ExpectUniqueSample("ClientHints.UpdateSize", 2, 1);
// accept_ch_with_lifetime_url() tries to set client hints persist duration to
// 3600 seconds.
histogram_tester.ExpectUniqueSample("ClientHints.PersistDuration",
3600 * 1000, 1);
base::RunLoop().RunUntilIdle();
// Clients hints preferences for one origin should be persisted.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(1u, host_settings.size());
// Block the Javascript: Client hints should not be attached.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->SetContentSettingDefaultScope(without_accept_ch_without_lifetime_url(),
GURL(), CONTENT_SETTINGS_TYPE_JAVASCRIPT,
std::string(), CONTENT_SETTING_BLOCK);
ui_test_utils::NavigateToURL(browser(),
without_accept_ch_without_lifetime_url());
EXPECT_EQ(0u, count_client_hints_headers_seen());
// Allow the Javascript: Client hints should now be attached.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->SetContentSettingDefaultScope(without_accept_ch_without_lifetime_url(),
GURL(), CONTENT_SETTINGS_TYPE_JAVASCRIPT,
std::string(), CONTENT_SETTING_ALLOW);
SetClientHintExpectations(true);
ui_test_utils::NavigateToURL(browser(),
without_accept_ch_without_lifetime_url());
if (content::IsBrowserSideNavigationEnabled()) {
// When browser side navigation is enabled, two client hints are attached to
// the image request, and the device-memory header is attached to the main
// frame request.
EXPECT_EQ(3u, count_client_hints_headers_seen());
} else {
// When browser side navigation is not enabled, two client hints are
// attached to each of the HTML and the image requests.
EXPECT_EQ(4u, count_client_hints_headers_seen());
}
// Clear settings.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->ClearSettingsForOneType(CONTENT_SETTINGS_TYPE_JAVASCRIPT);
}
IN_PROC_BROWSER_TEST_F(ClientHintsBrowserTest,
ClientHintsNoLifetimeFollowedByNoClientHint) {
base::HistogramTester histogram_tester;
ContentSettingsForOneType host_settings;
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(0u, host_settings.size());
// Fetching accept_ch_without_lifetime_url() should not persist the request
// for client hints.
ui_test_utils::NavigateToURL(browser(), accept_ch_without_lifetime_url());
histogram_tester.ExpectTotalCount("ClientHints.UpdateEventCount", 0);
content::FetchHistogramsFromChildProcesses();
SubprocessMetricsProvider::MergeHistogramDeltasForTesting();
histogram_tester.ExpectTotalCount("ClientHints.UpdateSize", 0);
histogram_tester.ExpectTotalCount("ClientHints.PersistDuration", 0);
base::RunLoop().RunUntilIdle();
// Clients hints preferences should not be persisted.
HostContentSettingsMapFactory::GetForProfile(browser()->profile())
->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_CLIENT_HINTS, std::string(),
&host_settings);
EXPECT_EQ(0u, host_settings.size());
// Next request should not have client hint headers attached.
ui_test_utils::NavigateToURL(browser(),
without_accept_ch_without_lifetime_url());
}
// Check the client hints for the given URL in an incognito window.
// Start incognito browser twice to ensure that client hints prefs are
// not carried over.
IN_PROC_BROWSER_TEST_F(ClientHintsBrowserTest, ClientHintsHttpsIncognito) {
for (size_t i = 0; i < 2; ++i) {
base::HistogramTester histogram_tester;
Browser* incognito = CreateIncognitoBrowser();
ui_test_utils::NavigateToURL(incognito, accept_ch_with_lifetime_url());
histogram_tester.ExpectUniqueSample("ClientHints.UpdateEventCount", 1, 1);
content::FetchHistogramsFromChildProcesses();
SubprocessMetricsProvider::MergeHistogramDeltasForTesting();
// accept_ch_with_lifetime_url() sets two client hints.
histogram_tester.ExpectUniqueSample("ClientHints.UpdateSize", 2, 1);
// At least one renderer must have been created. All the renderers created
// must have read 0 client hints.
EXPECT_LE(1u,
histogram_tester.GetAllSamples("ClientHints.CountRulesReceived")
.size());
for (const auto& bucket :
histogram_tester.GetAllSamples("ClientHints.CountRulesReceived")) {
EXPECT_EQ(0, bucket.min);
}
// |url| sets client hints persist duration to 3600 seconds.
histogram_tester.ExpectUniqueSample("ClientHints.PersistDuration",
3600 * 1000, 1);
CloseBrowserSynchronously(incognito);
}
}