| Index: chrome/browser/subresource_filter/subresource_filter_browsertest.cc
|
| diff --git a/chrome/browser/subresource_filter/subresource_filter_browsertest.cc b/chrome/browser/subresource_filter/subresource_filter_browsertest.cc
|
| index 61e93674f650ec1f7ab7e28416e58eaf3002a530..0931e09ce8fb1f81c8b1a64e44c20db42d726f85 100644
|
| --- a/chrome/browser/subresource_filter/subresource_filter_browsertest.cc
|
| +++ b/chrome/browser/subresource_filter/subresource_filter_browsertest.cc
|
| @@ -56,6 +56,7 @@
|
| #include "content/public/browser/notification_types.h"
|
| #include "content/public/browser/render_frame_host.h"
|
| #include "content/public/browser/web_contents.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_navigation_observer.h"
|
| @@ -341,6 +342,24 @@ class SubresourceFilterBrowserTestImpl : public InProcessBrowserTest {
|
| }
|
| }
|
|
|
| + void ExpectFramesIncludedInLayout(const std::vector<const char*>& frame_names,
|
| + const std::vector<bool>& expect_displayed) {
|
| + const char kScript[] =
|
| + "window.domAutomationController.send("
|
| + " document.getElementsByName(\"%s\")[0].clientWidth"
|
| + ");";
|
| +
|
| + ASSERT_EQ(expect_displayed.size(), frame_names.size());
|
| + for (size_t i = 0; i < frame_names.size(); ++i) {
|
| + SCOPED_TRACE(frame_names[i]);
|
| + int client_width = 0;
|
| + EXPECT_TRUE(content::ExecuteScriptAndExtractInt(
|
| + web_contents()->GetMainFrame(),
|
| + base::StringPrintf(kScript, frame_names[i]), &client_width));
|
| + EXPECT_EQ(expect_displayed[i], !!client_width) << client_width;
|
| + }
|
| + }
|
| +
|
| bool IsDynamicScriptElementLoaded(content::RenderFrameHost* rfh) {
|
| DCHECK(rfh);
|
| bool script_resource_was_loaded = false;
|
| @@ -359,9 +378,21 @@ class SubresourceFilterBrowserTestImpl : public InProcessBrowserTest {
|
| }
|
|
|
| void NavigateFromRendererSide(const GURL& url) {
|
| + content::TestNavigationObserver navigation_observer(web_contents(), 1);
|
| ASSERT_TRUE(content::ExecuteScript(
|
| web_contents()->GetMainFrame(),
|
| base::StringPrintf("window.location = \"%s\";", url.spec().c_str())));
|
| + navigation_observer.Wait();
|
| + }
|
| +
|
| + void NavigateFrame(const char* frame_name, const GURL& url) {
|
| + content::TestNavigationObserver navigation_observer(web_contents(), 1);
|
| + ASSERT_TRUE(content::ExecuteScript(
|
| + web_contents()->GetMainFrame(),
|
| + base::StringPrintf(
|
| + "document.getElementsByName(\"%s\")[0].src = \"%s\";", frame_name,
|
| + url.spec().c_str())));
|
| + navigation_observer.Wait();
|
| }
|
|
|
| void SetRulesetToDisallowURLsWithPathSuffix(const std::string& suffix) {
|
| @@ -567,31 +598,71 @@ IN_PROC_BROWSER_TEST_F(SubresourceFilterBrowserTest, SubFrameActivation) {
|
|
|
| IN_PROC_BROWSER_TEST_F(SubresourceFilterBrowserTest,
|
| SubframeDocumentLoadFiltering) {
|
| + base::HistogramTester histogram_tester;
|
| GURL url(GetTestUrl(kTestFrameSetPath));
|
| ConfigureAsPhishingURL(url);
|
|
|
| - // Disallow all the subframes that end up loading included_script.js.
|
| - ASSERT_NO_FATAL_FAILURE(
|
| - SetRulesetToDisallowURLsWithPathSuffix("included_script.html"));
|
| - base::HistogramTester tester;
|
| + // Disallow loading subframe documents that in turn would end up loading
|
| + // included_script.js, unless the document is loaded from a whitelisted
|
| + // domain. This enables the third part of this test disallowing a load only
|
| + // after the first redirect.
|
| + const char kWhitelistedDomain[] = "whitelisted.com";
|
| + proto::UrlRule rule = testing::CreateSuffixRule("included_script.html");
|
| + proto::UrlRule whitelist_rule = testing::CreateSuffixRule(kWhitelistedDomain);
|
| + whitelist_rule.set_anchor_right(proto::ANCHOR_TYPE_NONE);
|
| + whitelist_rule.set_semantics(proto::RULE_SEMANTICS_WHITELIST);
|
| + ASSERT_NO_FATAL_FAILURE(SetRulesetWithRules({rule, whitelist_rule}));
|
| +
|
| ui_test_utils::NavigateToURL(browser(), url);
|
|
|
| const std::vector<const char*> kSubframeNames{"one", "two", "three"};
|
| - const std::vector<bool> kExpectScriptInFrameToLoad{false, true, false};
|
| + const std::vector<bool> kExpectOnlySecondSubframe{false, true, false};
|
| ASSERT_NO_FATAL_FAILURE(ExpectParsedScriptElementLoadedStatusInFrames(
|
| - kSubframeNames, kExpectScriptInFrameToLoad));
|
| + kSubframeNames, kExpectOnlySecondSubframe));
|
| + ExpectFramesIncludedInLayout(kSubframeNames, kExpectOnlySecondSubframe);
|
| + histogram_tester.ExpectBucketCount(kSubresourceFilterActionsHistogram,
|
| + kActionUIShown, 1);
|
| +
|
| + // Now navigate the first subframe to an allowed URL and ensure that the load
|
| + // successfully commits and the frame gets restored (no longer collapsed).
|
| + GURL allowed_subdocument_url(
|
| + GetTestUrl("subresource_filter/frame_with_allowed_script.html"));
|
| + NavigateFrame(kSubframeNames[0], allowed_subdocument_url);
|
| +
|
| + const std::vector<bool> kExpectFirstAndSecondSubframe{true, true, false};
|
| + ASSERT_NO_FATAL_FAILURE(ExpectParsedScriptElementLoadedStatusInFrames(
|
| + kSubframeNames, kExpectFirstAndSecondSubframe));
|
| + ExpectFramesIncludedInLayout(kSubframeNames, kExpectFirstAndSecondSubframe);
|
| +
|
| + // Navigate the first subframe to a document that does not load the probe JS.
|
| + GURL allowed_empty_subdocument_url(
|
| + GetTestUrl("subresource_filter/frame_with_no_subresources.html"));
|
| + NavigateFrame(kSubframeNames[0], allowed_empty_subdocument_url);
|
| +
|
| + // Finally, navigate the first subframe to an allowed URL that redirects to a
|
| + // disallowed URL, and verify that:
|
| + // -- The navigation gets blocked and the frame collapsed (with PlzNavigate).
|
| + // -- The navigation is cancelled, but the frame is not collapsed (without
|
| + // PlzNavigate, where BLOCK_REQUEST_AND_COLLAPSE is not supported).
|
| + GURL disallowed_subdocument_url(
|
| + GetTestUrl("subresource_filter/frame_with_included_script.html"));
|
| + GURL redirect_to_disallowed_subdocument_url(embedded_test_server()->GetURL(
|
| + kWhitelistedDomain,
|
| + "/server-redirect?" + disallowed_subdocument_url.spec()));
|
| + NavigateFrame(kSubframeNames[0], redirect_to_disallowed_subdocument_url);
|
|
|
| - // The subframe navigations never commit.
|
| - for (size_t i = 0; i < kSubframeNames.size(); ++i) {
|
| - const char* subframe_name = kSubframeNames[i];
|
| - bool expect_loaded = kExpectScriptInFrameToLoad[i];
|
| - content::RenderFrameHost* frame = FindFrameByName(subframe_name);
|
| - if (!expect_loaded)
|
| - EXPECT_EQ(GURL(), frame->GetLastCommittedURL());
|
| - }
|
| + ASSERT_NO_FATAL_FAILURE(ExpectParsedScriptElementLoadedStatusInFrames(
|
| + kSubframeNames, kExpectOnlySecondSubframe));
|
|
|
| - tester.ExpectBucketCount(kSubresourceFilterActionsHistogram, kActionUIShown,
|
| - 1);
|
| + content::RenderFrameHost* frame = FindFrameByName(kSubframeNames[0]);
|
| + ASSERT_TRUE(frame);
|
| + if (content::IsBrowserSideNavigationEnabled()) {
|
| + EXPECT_EQ(disallowed_subdocument_url, frame->GetLastCommittedURL());
|
| + ExpectFramesIncludedInLayout(kSubframeNames, kExpectOnlySecondSubframe);
|
| + } else {
|
| + EXPECT_EQ(allowed_empty_subdocument_url, frame->GetLastCommittedURL());
|
| + ExpectFramesIncludedInLayout(kSubframeNames, kExpectFirstAndSecondSubframe);
|
| + }
|
| }
|
|
|
| IN_PROC_BROWSER_TEST_F(SubresourceFilterBrowserTest,
|
|
|