Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(115)

Side by Side Diff: components/subresource_filter/content/common/document_subresource_filter_unittest.cc

Issue 2697363005: Move DocumentSubresourceFilter to core/common. (Closed)
Patch Set: Address comments from engedy@. Created 3 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 // Copyright 2016 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "components/subresource_filter/content/common/document_subresource_filt er.h"
6
7 #include "base/bind.h"
8 #include "base/callback.h"
9 #include "base/files/file.h"
10 #include "base/macros.h"
11 #include "base/memory/ref_counted.h"
12 #include "base/strings/string_piece.h"
13 #include "components/subresource_filter/core/common/memory_mapped_ruleset.h"
14 #include "components/subresource_filter/core/common/test_ruleset_creator.h"
15 #include "components/subresource_filter/core/common/test_ruleset_utils.h"
16 #include "testing/gtest/include/gtest/gtest.h"
17 #include "third_party/WebKit/public/platform/WebURL.h"
18 #include "third_party/WebKit/public/platform/WebURLRequest.h"
19 #include "url/gurl.h"
20
21 namespace subresource_filter {
22
23 namespace {
24
25 constexpr auto kDisabled = ActivationLevel::DISABLED;
26 constexpr auto kDryRun = ActivationLevel::DRYRUN;
27 constexpr auto kEnabled = ActivationLevel::ENABLED;
28
29 const char kTestAlphaURL[] = "http://example.com/alpha";
30 const char kTestAlphaDataURI[] = "data:text/plain,alpha";
31 const char kTestBetaURL[] = "http://example.com/beta";
32
33 const char kTestAlphaURLPathSuffix[] = "alpha";
34
35 class TestCallbackReceiver {
36 public:
37 TestCallbackReceiver() = default;
38 base::OnceClosure closure() {
39 return base::BindOnce(&TestCallbackReceiver::CallbackMethod,
40 base::Unretained(this));
41 }
42 size_t callback_count() const { return callback_count_; }
43
44 private:
45 void CallbackMethod() { ++callback_count_; }
46
47 size_t callback_count_ = 0;
48
49 DISALLOW_COPY_AND_ASSIGN(TestCallbackReceiver);
50 };
51
52 } // namespace
53
54 // Tests for DocumentSubresourceFilter class. ----------------------------------
55
56 class DocumentSubresourceFilterTest : public ::testing::Test {
57 public:
58 DocumentSubresourceFilterTest() {}
59
60 protected:
61 void SetUp() override {
62 ASSERT_NO_FATAL_FAILURE(
63 SetTestRulesetToDisallowURLsWithPathSuffix(kTestAlphaURLPathSuffix));
64 }
65
66 void SetTestRulesetToDisallowURLsWithPathSuffix(base::StringPiece suffix) {
67 testing::TestRulesetPair test_ruleset_pair;
68 ASSERT_NO_FATAL_FAILURE(
69 test_ruleset_creator_.CreateRulesetToDisallowURLsWithPathSuffix(
70 suffix, &test_ruleset_pair));
71 ruleset_ = new MemoryMappedRuleset(
72 testing::TestRuleset::Open(test_ruleset_pair.indexed));
73 }
74
75 const MemoryMappedRuleset* ruleset() { return ruleset_.get(); }
76
77 private:
78 testing::TestRulesetCreator test_ruleset_creator_;
79 scoped_refptr<const MemoryMappedRuleset> ruleset_;
80
81 DISALLOW_COPY_AND_ASSIGN(DocumentSubresourceFilterTest);
82 };
83
84 TEST_F(DocumentSubresourceFilterTest, DryRun) {
85 blink::WebURLRequest::RequestContext request_context =
86 blink::WebURLRequest::RequestContextImage;
87 TestCallbackReceiver first_disallowed_load_callback_receiver;
88
89 ActivationState activation_state(kDryRun);
90 activation_state.measure_performance = true;
91 DocumentSubresourceFilter filter(
92 url::Origin(), activation_state, ruleset(),
93 first_disallowed_load_callback_receiver.closure());
94
95 EXPECT_EQ(blink::WebDocumentSubresourceFilter::WouldDisallow,
96 filter.getLoadPolicy(GURL(kTestAlphaURL), request_context));
97 EXPECT_EQ(blink::WebDocumentSubresourceFilter::Allow,
98 filter.getLoadPolicy(GURL(kTestAlphaDataURI), request_context));
99 EXPECT_EQ(blink::WebDocumentSubresourceFilter::Allow,
100 filter.getLoadPolicy(GURL(kTestBetaURL), request_context));
101 EXPECT_EQ(blink::WebDocumentSubresourceFilter::WouldDisallow,
102 filter.GetLoadPolicyForSubdocument(GURL(kTestAlphaURL)));
103 EXPECT_EQ(blink::WebDocumentSubresourceFilter::Allow,
104 filter.GetLoadPolicyForSubdocument(GURL(kTestBetaURL)));
105
106 const auto& statistics = filter.statistics();
107 EXPECT_EQ(5, statistics.num_loads_total);
108 EXPECT_EQ(4, statistics.num_loads_evaluated);
109 EXPECT_EQ(2, statistics.num_loads_matching_rules);
110 EXPECT_EQ(0, statistics.num_loads_disallowed);
111
112 EXPECT_EQ(0u, first_disallowed_load_callback_receiver.callback_count());
113 }
114
115 TEST_F(DocumentSubresourceFilterTest, Enabled) {
116 auto test_impl = [this](bool measure_performance) {
117 blink::WebURLRequest::RequestContext request_context =
118 blink::WebURLRequest::RequestContextImage;
119 ActivationState activation_state(kEnabled);
120 activation_state.measure_performance = measure_performance;
121 DocumentSubresourceFilter filter(url::Origin(), activation_state, ruleset(),
122 base::OnceClosure());
123
124 EXPECT_EQ(blink::WebDocumentSubresourceFilter::Disallow,
125 filter.getLoadPolicy(GURL(kTestAlphaURL), request_context));
126 EXPECT_EQ(blink::WebDocumentSubresourceFilter::Allow,
127 filter.getLoadPolicy(GURL(kTestAlphaDataURI), request_context));
128 EXPECT_EQ(blink::WebDocumentSubresourceFilter::Allow,
129 filter.getLoadPolicy(GURL(kTestBetaURL), request_context));
130 EXPECT_EQ(blink::WebDocumentSubresourceFilter::Disallow,
131 filter.GetLoadPolicyForSubdocument(GURL(kTestAlphaURL)));
132 EXPECT_EQ(blink::WebDocumentSubresourceFilter::Allow,
133 filter.GetLoadPolicyForSubdocument(GURL(kTestBetaURL)));
134
135 const auto& statistics = filter.statistics();
136 EXPECT_EQ(5, statistics.num_loads_total);
137 EXPECT_EQ(4, statistics.num_loads_evaluated);
138 EXPECT_EQ(2, statistics.num_loads_matching_rules);
139 EXPECT_EQ(2, statistics.num_loads_disallowed);
140
141 if (!measure_performance) {
142 EXPECT_TRUE(statistics.evaluation_total_cpu_duration.is_zero());
143 EXPECT_TRUE(statistics.evaluation_total_wall_duration.is_zero());
144 }
145 // Otherwise, don't expect |total_duration| to be non-zero, although it
146 // practically is (when timer is supported).
147 };
148
149 test_impl(true /* measure_performance */);
150 test_impl(false /* measure_performance */);
151 }
152
153 TEST_F(DocumentSubresourceFilterTest,
154 CallbackFiredExactlyOnceAfterFirstDisallowedLoad) {
155 TestCallbackReceiver first_disallowed_load_callback_receiver;
156
157 ActivationState activation_state(kEnabled);
158 activation_state.measure_performance = true;
159 DocumentSubresourceFilter filter(
160 url::Origin(), activation_state, ruleset(),
161 first_disallowed_load_callback_receiver.closure());
162
163 EXPECT_EQ(0u, first_disallowed_load_callback_receiver.callback_count());
164 filter.reportDisallowedLoad();
165 EXPECT_EQ(1u, first_disallowed_load_callback_receiver.callback_count());
166 filter.reportDisallowedLoad();
167 EXPECT_EQ(1u, first_disallowed_load_callback_receiver.callback_count());
168 }
169
170 // Tests for ComputeActivationState functions. ---------------------------------
171
172 class SubresourceFilterComputeActivationStateTest : public ::testing::Test {
173 public:
174 SubresourceFilterComputeActivationStateTest() {}
175
176 protected:
177 void SetUp() override {
178 constexpr int32_t kDocument = proto::ACTIVATION_TYPE_DOCUMENT;
179 constexpr int32_t kGenericBlock = proto::ACTIVATION_TYPE_GENERICBLOCK;
180
181 std::vector<proto::UrlRule> rules;
182 rules.push_back(testing::CreateWhitelistRuleForDocument(
183 "child1.com", kDocument, {"parent1.com", "parent2.com"}));
184 rules.push_back(testing::CreateWhitelistRuleForDocument(
185 "child2.com", kGenericBlock, {"parent1.com", "parent2.com"}));
186 rules.push_back(testing::CreateWhitelistRuleForDocument(
187 "child3.com", kDocument | kGenericBlock,
188 {"parent1.com", "parent2.com"}));
189
190 testing::TestRulesetPair test_ruleset_pair;
191 ASSERT_NO_FATAL_FAILURE(test_ruleset_creator_.CreateRulesetWithRules(
192 rules, &test_ruleset_pair));
193 ruleset_ = new MemoryMappedRuleset(
194 testing::TestRuleset::Open(test_ruleset_pair.indexed));
195 }
196
197 static ActivationState MakeState(
198 bool filtering_disabled_for_document,
199 bool generic_blocking_rules_disabled = false,
200 ActivationLevel activation_level = kEnabled) {
201 ActivationState activation_state(activation_level);
202 activation_state.filtering_disabled_for_document =
203 filtering_disabled_for_document;
204 activation_state.generic_blocking_rules_disabled =
205 generic_blocking_rules_disabled;
206 return activation_state;
207 };
208
209 const MemoryMappedRuleset* ruleset() { return ruleset_.get(); }
210
211 private:
212 testing::TestRulesetCreator test_ruleset_creator_;
213 scoped_refptr<const MemoryMappedRuleset> ruleset_;
214
215 DISALLOW_COPY_AND_ASSIGN(SubresourceFilterComputeActivationStateTest);
216 };
217
218 TEST_F(SubresourceFilterComputeActivationStateTest,
219 ActivationBitsCorrectlyPropagateToChildDocument) {
220 // Make sure that the |generic_blocking_rules_disabled| flag is disregarded
221 // when |filtering_disabled_for_document| is true.
222 ASSERT_EQ(MakeState(true, false), MakeState(true, true));
223
224 // TODO(pkalinnikov): Find a short way to express all these tests.
225 const struct {
226 const char* document_url;
227 const char* parent_document_origin;
228 ActivationState parent_activation;
229 ActivationState expected_activation_state;
230 } kTestCases[] = {
231 {"http://example.com", "http://example.com", MakeState(false, false),
232 MakeState(false, false)},
233 {"http://example.com", "http://example.com", MakeState(false, true),
234 MakeState(false, true)},
235 {"http://example.com", "http://example.com", MakeState(true, false),
236 MakeState(true)},
237 {"http://example.com", "http://example.com", MakeState(true, true),
238 MakeState(true)},
239
240 {"http://child1.com", "http://parrrrent1.com", MakeState(false, false),
241 MakeState(false, false)},
242 {"http://child1.com", "http://parent1.com", MakeState(false, false),
243 MakeState(true, false)},
244 {"http://child1.com", "http://parent2.com", MakeState(false, false),
245 MakeState(true, false)},
246 {"http://child1.com", "http://parent2.com", MakeState(true, false),
247 MakeState(true)},
248 {"http://child1.com", "http://parent2.com", MakeState(false, true),
249 MakeState(true)},
250
251 {"http://child2.com", "http://parent1.com", MakeState(false, false),
252 MakeState(false, true)},
253 {"http://child2.com", "http://parent1.com", MakeState(false, true),
254 MakeState(false, true)},
255 {"http://child2.com", "http://parent1.com", MakeState(true, false),
256 MakeState(true)},
257 {"http://child2.com", "http://parent1.com", MakeState(true, true),
258 MakeState(true)},
259
260 {"http://child3.com", "http://parent1.com", MakeState(false, false),
261 MakeState(true)},
262 {"http://child3.com", "http://parent1.com", MakeState(false, true),
263 MakeState(true)},
264 {"http://child3.com", "http://parent1.com", MakeState(true, false),
265 MakeState(true)},
266 {"http://child3.com", "http://parent1.com", MakeState(true, true),
267 MakeState(true)},
268 };
269
270 for (size_t i = 0, size = arraysize(kTestCases); i != size; ++i) {
271 SCOPED_TRACE(::testing::Message() << "Test number: " << i);
272 const auto& test_case = kTestCases[i];
273
274 GURL document_url(test_case.document_url);
275 url::Origin parent_document_origin(GURL(test_case.parent_document_origin));
276 ActivationState activation_state =
277 ComputeActivationState(document_url, parent_document_origin,
278 test_case.parent_activation, ruleset());
279 EXPECT_EQ(test_case.expected_activation_state, activation_state);
280 }
281 }
282
283 TEST_F(SubresourceFilterComputeActivationStateTest,
284 ActivationStateCorrectlyPropagatesDownDocumentHierarchy) {
285 const struct {
286 std::vector<std::string> ancestor_document_urls;
287 ActivationLevel activation_level;
288 ActivationState expected_activation_state;
289 } kTestCases[] = {
290 {{"http://example.com"}, kEnabled, MakeState(false)},
291 {std::vector<std::string>(2, "http://example.com"), kEnabled,
292 MakeState(false)},
293 {std::vector<std::string>(4, "http://example.com"), kEnabled,
294 MakeState(false)},
295
296 {std::vector<std::string>(4, "http://example.com"), kEnabled,
297 MakeState(false, false, kEnabled)},
298 {std::vector<std::string>(4, "http://example.com"), kDisabled,
299 MakeState(false, false, kDisabled)},
300 {std::vector<std::string>(4, "http://example.com"), kDryRun,
301 MakeState(false, false, kDryRun)},
302
303 {{"http://ex.com", "http://child1.com", "http://parent1.com",
304 "http://root.com"},
305 kEnabled,
306 MakeState(true)},
307
308 {{"http://ex.com", "http://child1.com", "http://parent1.com",
309 "http://root.com"},
310 kEnabled,
311 MakeState(true)},
312
313 {{"http://ex.com", "http://child2.com", "http://parent1.com",
314 "http://root.com"},
315 kEnabled,
316 MakeState(false, true)},
317
318 {{"http://ex.com", "http://ex.com", "http://child3.com",
319 "http://parent1.com", "http://root.com"},
320 kDryRun,
321 MakeState(true, false, kDryRun)},
322 };
323
324 for (size_t i = 0, size = arraysize(kTestCases); i != size; ++i) {
325 const auto& test_case = kTestCases[i];
326 SCOPED_TRACE(::testing::Message() << "Test number: " << i);
327
328 std::vector<GURL> ancestor_document_urls;
329 for (const auto& url_string : test_case.ancestor_document_urls)
330 ancestor_document_urls.emplace_back(url_string);
331
332 ActivationState activation_state = ComputeActivationState(
333 test_case.activation_level, false, ancestor_document_urls, ruleset());
334 EXPECT_EQ(test_case.expected_activation_state, activation_state);
335 }
336 }
337
338 } // namespace subresource_filter
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698