OLD | NEW |
| (Empty) |
1 // Copyright 2014 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 "chrome/browser/safe_browsing/incident_reporting_service.h" | |
6 | |
7 #include <map> | |
8 #include <string> | |
9 | |
10 #include "base/bind.h" | |
11 #include "base/callback.h" | |
12 #include "base/lazy_instance.h" | |
13 #include "base/strings/utf_string_conversions.h" | |
14 #include "base/test/test_simple_task_runner.h" | |
15 #include "base/thread_task_runner_handle.h" | |
16 #include "base/threading/thread_local.h" | |
17 #include "chrome/browser/prefs/browser_prefs.h" | |
18 #include "chrome/browser/safe_browsing/incident_report_uploader.h" | |
19 #include "chrome/browser/safe_browsing/last_download_finder.h" | |
20 #include "chrome/common/pref_names.h" | |
21 #include "chrome/common/safe_browsing/csd.pb.h" | |
22 #include "chrome/test/base/testing_browser_process.h" | |
23 #include "chrome/test/base/testing_pref_service_syncable.h" | |
24 #include "chrome/test/base/testing_profile.h" | |
25 #include "chrome/test/base/testing_profile_manager.h" | |
26 #include "net/url_request/url_request_context_getter.h" | |
27 #include "testing/gtest/include/gtest/gtest.h" | |
28 | |
29 // A test fixture that sets up a test task runner and makes it the thread's | |
30 // runner. The fixture implements a fake envrionment data collector and a fake | |
31 // report uploader. | |
32 class IncidentReportingServiceTest : public testing::Test { | |
33 protected: | |
34 // An IRS class that allows a test harness to provide a fake environment | |
35 // collector and report uploader via callbacks. | |
36 class TestIncidentReportingService | |
37 : public safe_browsing::IncidentReportingService { | |
38 public: | |
39 typedef base::Callback<void(Profile*)> PreProfileAddCallback; | |
40 | |
41 typedef base::Callback< | |
42 void(safe_browsing::ClientIncidentReport_EnvironmentData*)> | |
43 CollectEnvironmentCallback; | |
44 | |
45 typedef base::Callback<scoped_ptr<safe_browsing::LastDownloadFinder>( | |
46 const safe_browsing::LastDownloadFinder::LastDownloadCallback& | |
47 callback)> CreateDownloadFinderCallback; | |
48 | |
49 typedef base::Callback<scoped_ptr<safe_browsing::IncidentReportUploader>( | |
50 const safe_browsing::IncidentReportUploader::OnResultCallback&, | |
51 const safe_browsing::ClientIncidentReport& report)> StartUploadCallback; | |
52 | |
53 TestIncidentReportingService( | |
54 const scoped_refptr<base::TaskRunner>& task_runner, | |
55 const PreProfileAddCallback& pre_profile_add_callback, | |
56 const CollectEnvironmentCallback& collect_environment_callback, | |
57 const CreateDownloadFinderCallback& create_download_finder_callback, | |
58 const StartUploadCallback& start_upload_callback) | |
59 : IncidentReportingService(NULL, | |
60 NULL, | |
61 base::TimeDelta::FromMilliseconds(5), | |
62 task_runner), | |
63 pre_profile_add_callback_(pre_profile_add_callback), | |
64 collect_environment_callback_(collect_environment_callback), | |
65 create_download_finder_callback_(create_download_finder_callback), | |
66 start_upload_callback_(start_upload_callback) { | |
67 SetCollectEnvironmentHook(&CollectEnvironmentData, task_runner); | |
68 test_instance_.Get().Set(this); | |
69 } | |
70 | |
71 virtual ~TestIncidentReportingService() { test_instance_.Get().Set(NULL); } | |
72 | |
73 protected: | |
74 virtual void OnProfileAdded(Profile* profile) OVERRIDE { | |
75 pre_profile_add_callback_.Run(profile); | |
76 safe_browsing::IncidentReportingService::OnProfileAdded(profile); | |
77 } | |
78 | |
79 virtual scoped_ptr<safe_browsing::LastDownloadFinder> CreateDownloadFinder( | |
80 const safe_browsing::LastDownloadFinder::LastDownloadCallback& callback) | |
81 OVERRIDE { | |
82 return create_download_finder_callback_.Run(callback); | |
83 } | |
84 | |
85 virtual scoped_ptr<safe_browsing::IncidentReportUploader> StartReportUpload( | |
86 const safe_browsing::IncidentReportUploader::OnResultCallback& callback, | |
87 const scoped_refptr<net::URLRequestContextGetter>& | |
88 request_context_getter, | |
89 const safe_browsing::ClientIncidentReport& report) OVERRIDE { | |
90 return start_upload_callback_.Run(callback, report); | |
91 } | |
92 | |
93 private: | |
94 static TestIncidentReportingService& current() { | |
95 return *test_instance_.Get().Get(); | |
96 } | |
97 | |
98 static void CollectEnvironmentData( | |
99 safe_browsing::ClientIncidentReport_EnvironmentData* data) { | |
100 current().collect_environment_callback_.Run(data); | |
101 }; | |
102 | |
103 static base::LazyInstance<base::ThreadLocalPointer< | |
104 TestIncidentReportingService> >::Leaky test_instance_; | |
105 | |
106 PreProfileAddCallback pre_profile_add_callback_; | |
107 CollectEnvironmentCallback collect_environment_callback_; | |
108 CreateDownloadFinderCallback create_download_finder_callback_; | |
109 StartUploadCallback start_upload_callback_; | |
110 }; | |
111 | |
112 // A type for specifying whether or not a profile created by CreateProfile | |
113 // participates in safe browsing. | |
114 enum SafeBrowsingDisposition { | |
115 SAFE_BROWSING_OPT_OUT, | |
116 SAFE_BROWSING_OPT_IN, | |
117 }; | |
118 | |
119 // A type for specifying the action to be taken by the test fixture during | |
120 // profile initialization (before NOTIFICATION_PROFILE_ADDED is sent). | |
121 enum OnProfileAdditionAction { | |
122 ON_PROFILE_ADDITION_NO_ACTION, | |
123 ON_PROFILE_ADDITION_ADD_INCIDENT, // Add an incident to the service. | |
124 ON_PROFILE_ADDITION_ADD_TWO_INCIDENTS, // Add two incidents to the service. | |
125 }; | |
126 | |
127 // A type for specifying the action to be taken by the test fixture when the | |
128 // service creates a LastDownloadFinder. | |
129 enum OnCreateDownloadFinderAction { | |
130 // Post a task that reports a download. | |
131 ON_CREATE_DOWNLOAD_FINDER_DOWNLOAD_FOUND, | |
132 // Post a task that reports no downloads found. | |
133 ON_CREATE_DOWNLOAD_FINDER_NO_DOWNLOADS, | |
134 // Immediately return due to a lack of eligible profiles. | |
135 ON_CREATE_DOWNLOAD_FINDER_NO_PROFILES, | |
136 }; | |
137 | |
138 // A type for specifying the action to be taken by the test fixture when its | |
139 // delayed analysis callback is run. | |
140 enum OnDelayedAnalysisAction { | |
141 ON_DELAYED_ANALYSIS_NO_ACTION, | |
142 ON_DELAYED_ANALYSIS_ADD_INCIDENT, // Add an incident to the service. | |
143 }; | |
144 | |
145 static const int64 kIncidentTimeMsec; | |
146 static const char kFakeOsName[]; | |
147 static const char kFakeDownloadToken[]; | |
148 static const char kTestTrackedPrefPath[]; | |
149 | |
150 IncidentReportingServiceTest() | |
151 : task_runner_(new base::TestSimpleTaskRunner), | |
152 thread_task_runner_handle_(task_runner_), | |
153 profile_manager_(TestingBrowserProcess::GetGlobal()), | |
154 instance_(new TestIncidentReportingService( | |
155 task_runner_, | |
156 base::Bind(&IncidentReportingServiceTest::PreProfileAdd, | |
157 base::Unretained(this)), | |
158 base::Bind(&IncidentReportingServiceTest::CollectEnvironmentData, | |
159 base::Unretained(this)), | |
160 base::Bind(&IncidentReportingServiceTest::CreateDownloadFinder, | |
161 base::Unretained(this)), | |
162 base::Bind(&IncidentReportingServiceTest::StartUpload, | |
163 base::Unretained(this)))), | |
164 on_create_download_finder_action_( | |
165 ON_CREATE_DOWNLOAD_FINDER_DOWNLOAD_FOUND), | |
166 on_delayed_analysis_action_(ON_DELAYED_ANALYSIS_NO_ACTION), | |
167 upload_result_(safe_browsing::IncidentReportUploader::UPLOAD_SUCCESS), | |
168 environment_collected_(), | |
169 download_finder_created_(), | |
170 download_finder_destroyed_(), | |
171 uploader_destroyed_(), | |
172 delayed_analysis_ran_() {} | |
173 | |
174 virtual void SetUp() OVERRIDE { | |
175 testing::Test::SetUp(); | |
176 ASSERT_TRUE(profile_manager_.SetUp()); | |
177 } | |
178 | |
179 // Sets the action to be taken by the test fixture when the service creates a | |
180 // LastDownloadFinder. | |
181 void SetCreateDownloadFinderAction(OnCreateDownloadFinderAction action) { | |
182 on_create_download_finder_action_ = action; | |
183 } | |
184 | |
185 // Creates and returns a profile (owned by the profile manager) with or | |
186 // without safe browsing enabled. An incident will be created within | |
187 // PreProfileAdd if requested. | |
188 TestingProfile* CreateProfile(const std::string& profile_name, | |
189 SafeBrowsingDisposition safe_browsing_opt_in, | |
190 OnProfileAdditionAction on_addition_action) { | |
191 // Create prefs for the profile with safe browsing enabled or not. | |
192 scoped_ptr<TestingPrefServiceSyncable> prefs( | |
193 new TestingPrefServiceSyncable); | |
194 chrome::RegisterUserProfilePrefs(prefs->registry()); | |
195 prefs->SetBoolean(prefs::kSafeBrowsingEnabled, | |
196 safe_browsing_opt_in == SAFE_BROWSING_OPT_IN); | |
197 | |
198 // Remember whether or not to create an incident. | |
199 profile_properties_[profile_name].on_addition_action = on_addition_action; | |
200 | |
201 // Boom (or fizzle). | |
202 return profile_manager_.CreateTestingProfile( | |
203 profile_name, | |
204 prefs.PassAs<PrefServiceSyncable>(), | |
205 base::ASCIIToUTF16(profile_name), | |
206 0, // avatar_id (unused) | |
207 std::string(), // supervised_user_id (unused) | |
208 TestingProfile::TestingFactories()); | |
209 } | |
210 | |
211 // Configures a callback to run when the next upload is started that will post | |
212 // a task to delete the profile. This task will run before the upload | |
213 // finishes. | |
214 void DeleteProfileOnUpload(Profile* profile) { | |
215 ASSERT_TRUE(on_start_upload_callback_.is_null()); | |
216 on_start_upload_callback_ = | |
217 base::Bind(&IncidentReportingServiceTest::DelayedDeleteProfile, | |
218 base::Unretained(this), | |
219 profile); | |
220 } | |
221 | |
222 // Returns an incident suitable for testing. | |
223 scoped_ptr<safe_browsing::ClientIncidentReport_IncidentData> | |
224 MakeTestIncident() { | |
225 scoped_ptr<safe_browsing::ClientIncidentReport_IncidentData> incident( | |
226 new safe_browsing::ClientIncidentReport_IncidentData()); | |
227 incident->set_incident_time_msec(kIncidentTimeMsec); | |
228 safe_browsing::ClientIncidentReport_IncidentData_TrackedPreferenceIncident* | |
229 tp_incident = incident->mutable_tracked_preference(); | |
230 tp_incident->set_path(kTestTrackedPrefPath); | |
231 return incident.Pass(); | |
232 } | |
233 | |
234 // Adds a test incident to the service. | |
235 void AddTestIncident(Profile* profile) { | |
236 instance_->GetAddIncidentCallback(profile).Run(MakeTestIncident().Pass()); | |
237 } | |
238 | |
239 // Registers the callback to be run for delayed analysis. | |
240 void RegisterAnalysis(OnDelayedAnalysisAction on_delayed_analysis_action) { | |
241 on_delayed_analysis_action_ = on_delayed_analysis_action; | |
242 instance_->RegisterDelayedAnalysisCallback( | |
243 base::Bind(&IncidentReportingServiceTest::OnDelayedAnalysis, | |
244 base::Unretained(this))); | |
245 } | |
246 | |
247 // Confirms that the test incident(s) was/were uploaded by the service, then | |
248 // clears the instance for subsequent incidents. | |
249 void ExpectTestIncidentUploaded(int incident_count) { | |
250 ASSERT_TRUE(uploaded_report_); | |
251 ASSERT_EQ(incident_count, uploaded_report_->incident_size()); | |
252 for (int i = 0; i < incident_count; ++i) { | |
253 ASSERT_TRUE(uploaded_report_->incident(i).has_incident_time_msec()); | |
254 ASSERT_EQ(kIncidentTimeMsec, | |
255 uploaded_report_->incident(i).incident_time_msec()); | |
256 ASSERT_TRUE(uploaded_report_->incident(i).has_tracked_preference()); | |
257 ASSERT_TRUE( | |
258 uploaded_report_->incident(i).tracked_preference().has_path()); | |
259 ASSERT_EQ(std::string(kTestTrackedPrefPath), | |
260 uploaded_report_->incident(i).tracked_preference().path()); | |
261 } | |
262 ASSERT_TRUE(uploaded_report_->has_environment()); | |
263 ASSERT_TRUE(uploaded_report_->environment().has_os()); | |
264 ASSERT_TRUE(uploaded_report_->environment().os().has_os_name()); | |
265 ASSERT_EQ(std::string(kFakeOsName), | |
266 uploaded_report_->environment().os().os_name()); | |
267 ASSERT_EQ(std::string(kFakeDownloadToken), | |
268 uploaded_report_->download().token()); | |
269 | |
270 uploaded_report_.reset(); | |
271 } | |
272 | |
273 void AssertNoUpload() { ASSERT_FALSE(uploaded_report_); } | |
274 | |
275 bool HasCollectedEnvironmentData() const { return environment_collected_; } | |
276 bool HasCreatedDownloadFinder() const { return download_finder_created_; } | |
277 bool DownloadFinderDestroyed() const { return download_finder_destroyed_; } | |
278 bool UploaderDestroyed() const { return uploader_destroyed_; } | |
279 bool DelayedAnalysisRan() const { return delayed_analysis_ran_; } | |
280 | |
281 scoped_refptr<base::TestSimpleTaskRunner> task_runner_; | |
282 base::ThreadTaskRunnerHandle thread_task_runner_handle_; | |
283 TestingProfileManager profile_manager_; | |
284 scoped_ptr<safe_browsing::IncidentReportingService> instance_; | |
285 base::Closure on_start_upload_callback_; | |
286 OnCreateDownloadFinderAction on_create_download_finder_action_; | |
287 OnDelayedAnalysisAction on_delayed_analysis_action_; | |
288 safe_browsing::IncidentReportUploader::Result upload_result_; | |
289 bool environment_collected_; | |
290 bool download_finder_created_; | |
291 scoped_ptr<safe_browsing::ClientIncidentReport> uploaded_report_; | |
292 bool download_finder_destroyed_; | |
293 bool uploader_destroyed_; | |
294 bool delayed_analysis_ran_; | |
295 | |
296 private: | |
297 // A fake IncidentReportUploader that posts a task to provide a given response | |
298 // back to the incident reporting service. It also reports back to the test | |
299 // harness via a closure when it is deleted by the incident reporting service. | |
300 class FakeUploader : public safe_browsing::IncidentReportUploader { | |
301 public: | |
302 FakeUploader( | |
303 const base::Closure& on_deleted, | |
304 const safe_browsing::IncidentReportUploader::OnResultCallback& callback, | |
305 safe_browsing::IncidentReportUploader::Result result) | |
306 : safe_browsing::IncidentReportUploader(callback), | |
307 on_deleted_(on_deleted), | |
308 result_(result) { | |
309 // Post a task that will provide the response. | |
310 base::ThreadTaskRunnerHandle::Get()->PostTask( | |
311 FROM_HERE, | |
312 base::Bind(&FakeUploader::FinishUpload, base::Unretained(this))); | |
313 } | |
314 virtual ~FakeUploader() { on_deleted_.Run(); } | |
315 | |
316 private: | |
317 void FinishUpload() { | |
318 // Callbacks have a tendency to delete the uploader, so no touching | |
319 // anything after this. | |
320 callback_.Run(result_, | |
321 scoped_ptr<safe_browsing::ClientIncidentResponse>()); | |
322 } | |
323 | |
324 base::Closure on_deleted_; | |
325 safe_browsing::IncidentReportUploader::Result result_; | |
326 | |
327 DISALLOW_COPY_AND_ASSIGN(FakeUploader); | |
328 }; | |
329 | |
330 class FakeDownloadFinder : public safe_browsing::LastDownloadFinder { | |
331 public: | |
332 static scoped_ptr<safe_browsing::LastDownloadFinder> Create( | |
333 const base::Closure& on_deleted, | |
334 scoped_ptr<safe_browsing::ClientIncidentReport_DownloadDetails> | |
335 download, | |
336 const safe_browsing::LastDownloadFinder::LastDownloadCallback& | |
337 callback) { | |
338 // Post a task to run the callback. | |
339 base::ThreadTaskRunnerHandle::Get()->PostTask( | |
340 FROM_HERE, base::Bind(callback, base::Passed(&download))); | |
341 return scoped_ptr<safe_browsing::LastDownloadFinder>( | |
342 new FakeDownloadFinder(on_deleted)); | |
343 } | |
344 | |
345 virtual ~FakeDownloadFinder() { on_deleted_.Run(); } | |
346 | |
347 private: | |
348 explicit FakeDownloadFinder(const base::Closure& on_deleted) | |
349 : on_deleted_(on_deleted) {} | |
350 | |
351 base::Closure on_deleted_; | |
352 | |
353 DISALLOW_COPY_AND_ASSIGN(FakeDownloadFinder); | |
354 }; | |
355 | |
356 // Properties for a profile that impact the behavior of the test. | |
357 struct ProfileProperties { | |
358 ProfileProperties() : on_addition_action(ON_PROFILE_ADDITION_NO_ACTION) {} | |
359 | |
360 // The action taken by the test fixture during profile initialization | |
361 // (before NOTIFICATION_PROFILE_ADDED is sent). | |
362 OnProfileAdditionAction on_addition_action; | |
363 }; | |
364 | |
365 // Returns the name of a profile as provided to CreateProfile. | |
366 static std::string GetProfileName(Profile* profile) { | |
367 // Cannot reliably use profile->GetProfileName() since the test needs the | |
368 // name before the profile manager sets it (which happens after profile | |
369 // addition). | |
370 return profile->GetPath().BaseName().AsUTF8Unsafe(); | |
371 } | |
372 | |
373 // Posts a task to delete the profile. | |
374 void DelayedDeleteProfile(Profile* profile) { | |
375 base::ThreadTaskRunnerHandle::Get()->PostTask( | |
376 FROM_HERE, | |
377 base::Bind(&TestingProfileManager::DeleteTestingProfile, | |
378 base::Unretained(&profile_manager_), | |
379 GetProfileName(profile))); | |
380 } | |
381 | |
382 // A callback run by the test fixture when a profile is added. An incident | |
383 // is added. | |
384 void PreProfileAdd(Profile* profile) { | |
385 // The instance must have already been created. | |
386 ASSERT_TRUE(instance_); | |
387 // Add a test incident to the service if requested. | |
388 switch (profile_properties_[GetProfileName(profile)].on_addition_action) { | |
389 case ON_PROFILE_ADDITION_ADD_INCIDENT: | |
390 AddTestIncident(profile); | |
391 break; | |
392 case ON_PROFILE_ADDITION_ADD_TWO_INCIDENTS: | |
393 AddTestIncident(profile); | |
394 AddTestIncident(profile); | |
395 break; | |
396 default: | |
397 ASSERT_EQ( | |
398 ON_PROFILE_ADDITION_NO_ACTION, | |
399 profile_properties_[GetProfileName(profile)].on_addition_action); | |
400 break; | |
401 } | |
402 } | |
403 | |
404 // A fake CollectEnvironmentData implementation invoked by the service during | |
405 // operation. | |
406 void CollectEnvironmentData( | |
407 safe_browsing::ClientIncidentReport_EnvironmentData* data) { | |
408 ASSERT_NE( | |
409 static_cast<safe_browsing::ClientIncidentReport_EnvironmentData*>(NULL), | |
410 data); | |
411 data->mutable_os()->set_os_name(kFakeOsName); | |
412 environment_collected_ = true; | |
413 } | |
414 | |
415 // A fake CreateDownloadFinder implementation invoked by the service during | |
416 // operation. | |
417 scoped_ptr<safe_browsing::LastDownloadFinder> CreateDownloadFinder( | |
418 const safe_browsing::LastDownloadFinder::LastDownloadCallback& callback) { | |
419 download_finder_created_ = true; | |
420 scoped_ptr<safe_browsing::ClientIncidentReport_DownloadDetails> download; | |
421 if (on_create_download_finder_action_ == | |
422 ON_CREATE_DOWNLOAD_FINDER_NO_PROFILES) { | |
423 return scoped_ptr<safe_browsing::LastDownloadFinder>(); | |
424 } | |
425 if (on_create_download_finder_action_ == | |
426 ON_CREATE_DOWNLOAD_FINDER_DOWNLOAD_FOUND) { | |
427 download.reset(new safe_browsing::ClientIncidentReport_DownloadDetails); | |
428 download->set_token(kFakeDownloadToken); | |
429 } | |
430 return scoped_ptr<safe_browsing::LastDownloadFinder>( | |
431 FakeDownloadFinder::Create( | |
432 base::Bind(&IncidentReportingServiceTest::OnDownloadFinderDestroyed, | |
433 base::Unretained(this)), | |
434 download.Pass(), | |
435 callback)); | |
436 } | |
437 | |
438 // A fake StartUpload implementation invoked by the service during operation. | |
439 scoped_ptr<safe_browsing::IncidentReportUploader> StartUpload( | |
440 const safe_browsing::IncidentReportUploader::OnResultCallback& callback, | |
441 const safe_browsing::ClientIncidentReport& report) { | |
442 // Remember the report that is being uploaded. | |
443 uploaded_report_.reset(new safe_browsing::ClientIncidentReport(report)); | |
444 // Run and clear the OnStartUpload callback, if provided. | |
445 if (!on_start_upload_callback_.is_null()) { | |
446 on_start_upload_callback_.Run(); | |
447 on_start_upload_callback_ = base::Closure(); | |
448 } | |
449 return scoped_ptr<safe_browsing::IncidentReportUploader>( | |
450 new FakeUploader( | |
451 base::Bind( | |
452 &IncidentReportingServiceTest::OnUploaderDestroyed, | |
453 base::Unretained(this)), | |
454 callback, | |
455 upload_result_)).Pass(); | |
456 } | |
457 | |
458 void OnDownloadFinderDestroyed() { download_finder_destroyed_ = true; } | |
459 void OnUploaderDestroyed() { uploader_destroyed_ = true; } | |
460 | |
461 void OnDelayedAnalysis(const safe_browsing::AddIncidentCallback& callback) { | |
462 delayed_analysis_ran_ = true; | |
463 if (on_delayed_analysis_action_ == ON_DELAYED_ANALYSIS_ADD_INCIDENT) | |
464 callback.Run(MakeTestIncident().Pass()); | |
465 } | |
466 | |
467 // A mapping of profile name to its corresponding properties. | |
468 std::map<std::string, ProfileProperties> profile_properties_; | |
469 }; | |
470 | |
471 // static | |
472 base::LazyInstance<base::ThreadLocalPointer< | |
473 IncidentReportingServiceTest::TestIncidentReportingService> >::Leaky | |
474 IncidentReportingServiceTest::TestIncidentReportingService::test_instance_ = | |
475 LAZY_INSTANCE_INITIALIZER; | |
476 | |
477 const int64 IncidentReportingServiceTest::kIncidentTimeMsec = 47LL; | |
478 const char IncidentReportingServiceTest::kFakeOsName[] = "fakedows"; | |
479 const char IncidentReportingServiceTest::kFakeDownloadToken[] = "fakedlt"; | |
480 const char IncidentReportingServiceTest::kTestTrackedPrefPath[] = "some_pref"; | |
481 | |
482 // Tests that an incident added during profile initialization when safe browsing | |
483 // is on is uploaded. | |
484 TEST_F(IncidentReportingServiceTest, AddIncident) { | |
485 CreateProfile( | |
486 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_ADD_INCIDENT); | |
487 | |
488 // Let all tasks run. | |
489 task_runner_->RunUntilIdle(); | |
490 | |
491 // Verify that environment collection took place. | |
492 EXPECT_TRUE(HasCollectedEnvironmentData()); | |
493 | |
494 // Verify that the most recent download was looked for. | |
495 EXPECT_TRUE(HasCreatedDownloadFinder()); | |
496 | |
497 // Verify that report upload took place and contained the incident, | |
498 // environment data, and download details. | |
499 ExpectTestIncidentUploaded(1); | |
500 | |
501 // Verify that the download finder and the uploader were destroyed. | |
502 ASSERT_TRUE(DownloadFinderDestroyed()); | |
503 ASSERT_TRUE(UploaderDestroyed()); | |
504 } | |
505 | |
506 // Tests that multiple incidents are coalesced into the same report. | |
507 TEST_F(IncidentReportingServiceTest, CoalesceIncidents) { | |
508 CreateProfile( | |
509 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_ADD_TWO_INCIDENTS); | |
510 | |
511 // Let all tasks run. | |
512 task_runner_->RunUntilIdle(); | |
513 | |
514 // Verify that environment collection took place. | |
515 EXPECT_TRUE(HasCollectedEnvironmentData()); | |
516 | |
517 // Verify that the most recent download was looked for. | |
518 EXPECT_TRUE(HasCreatedDownloadFinder()); | |
519 | |
520 // Verify that report upload took place and contained the incident, | |
521 // environment data, and download details. | |
522 ExpectTestIncidentUploaded(2); | |
523 | |
524 // Verify that the download finder and the uploader were destroyed. | |
525 ASSERT_TRUE(DownloadFinderDestroyed()); | |
526 ASSERT_TRUE(UploaderDestroyed()); | |
527 } | |
528 | |
529 // Tests that an incident added during profile initialization when safe browsing | |
530 // is off is not uploaded. | |
531 TEST_F(IncidentReportingServiceTest, NoSafeBrowsing) { | |
532 // Create the profile, thereby causing the test to begin. | |
533 CreateProfile( | |
534 "profile1", SAFE_BROWSING_OPT_OUT, ON_PROFILE_ADDITION_ADD_INCIDENT); | |
535 | |
536 // Let all tasks run. | |
537 task_runner_->RunUntilIdle(); | |
538 | |
539 // Verify that no report upload took place. | |
540 AssertNoUpload(); | |
541 } | |
542 | |
543 // Tests that no incident report is uploaded if there is no recent download. | |
544 TEST_F(IncidentReportingServiceTest, NoDownloadNoUpload) { | |
545 // Tell the fixture to return no downloads found. | |
546 SetCreateDownloadFinderAction(ON_CREATE_DOWNLOAD_FINDER_NO_DOWNLOADS); | |
547 | |
548 // Create the profile, thereby causing the test to begin. | |
549 CreateProfile( | |
550 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_ADD_INCIDENT); | |
551 | |
552 // Let all tasks run. | |
553 task_runner_->RunUntilIdle(); | |
554 | |
555 // Verify that the download finder was run but that no report upload took | |
556 // place. | |
557 EXPECT_TRUE(HasCreatedDownloadFinder()); | |
558 AssertNoUpload(); | |
559 EXPECT_TRUE(DownloadFinderDestroyed()); | |
560 } | |
561 | |
562 // Tests that no incident report is uploaded if there is no recent download. | |
563 TEST_F(IncidentReportingServiceTest, NoProfilesNoUpload) { | |
564 // Tell the fixture to pretend there are no profiles eligible for finding | |
565 // downloads. | |
566 SetCreateDownloadFinderAction(ON_CREATE_DOWNLOAD_FINDER_NO_PROFILES); | |
567 | |
568 // Create the profile, thereby causing the test to begin. | |
569 CreateProfile( | |
570 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_ADD_INCIDENT); | |
571 | |
572 // Let all tasks run. | |
573 task_runner_->RunUntilIdle(); | |
574 | |
575 // Verify that the download finder was run but that no report upload took | |
576 // place. | |
577 EXPECT_TRUE(HasCreatedDownloadFinder()); | |
578 AssertNoUpload(); | |
579 // Although CreateDownloadFinder was called, no instance was returned so there | |
580 // is nothing to have been destroyed. | |
581 EXPECT_FALSE(DownloadFinderDestroyed()); | |
582 } | |
583 | |
584 // Tests that an identical incident added after upload is not uploaded again. | |
585 TEST_F(IncidentReportingServiceTest, OneIncidentOneUpload) { | |
586 // Create the profile, thereby causing the test to begin. | |
587 Profile* profile = CreateProfile( | |
588 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_ADD_INCIDENT); | |
589 | |
590 // Let all tasks run. | |
591 task_runner_->RunUntilIdle(); | |
592 | |
593 // Verify that report upload took place and contained the incident and | |
594 // environment data. | |
595 ExpectTestIncidentUploaded(1); | |
596 | |
597 // Add the incident to the service again. | |
598 AddTestIncident(profile); | |
599 | |
600 // Let all tasks run. | |
601 task_runner_->RunUntilIdle(); | |
602 | |
603 // Verify that no additional report upload took place. | |
604 AssertNoUpload(); | |
605 } | |
606 | |
607 // Tests that two incidents of the same type with different payloads lead to two | |
608 // uploads. | |
609 TEST_F(IncidentReportingServiceTest, TwoIncidentsTwoUploads) { | |
610 // Create the profile, thereby causing the test to begin. | |
611 Profile* profile = CreateProfile( | |
612 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_ADD_INCIDENT); | |
613 | |
614 // Let all tasks run. | |
615 task_runner_->RunUntilIdle(); | |
616 | |
617 // Verify that report upload took place and contained the incident and | |
618 // environment data. | |
619 ExpectTestIncidentUploaded(1); | |
620 | |
621 // Add a variation on the incident to the service. | |
622 scoped_ptr<safe_browsing::ClientIncidentReport_IncidentData> incident( | |
623 MakeTestIncident()); | |
624 incident->mutable_tracked_preference()->set_atomic_value("leeches"); | |
625 instance_->GetAddIncidentCallback(profile).Run(incident.Pass()); | |
626 | |
627 // Let all tasks run. | |
628 task_runner_->RunUntilIdle(); | |
629 | |
630 // Verify that an additional report upload took place. | |
631 ExpectTestIncidentUploaded(1); | |
632 } | |
633 | |
634 // Tests that the same incident added for two different profiles in sequence | |
635 // results in two uploads. | |
636 TEST_F(IncidentReportingServiceTest, TwoProfilesTwoUploads) { | |
637 // Create the profile, thereby causing the test to begin. | |
638 CreateProfile( | |
639 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_ADD_INCIDENT); | |
640 | |
641 // Let all tasks run. | |
642 task_runner_->RunUntilIdle(); | |
643 | |
644 // Verify that report upload took place and contained the incident and | |
645 // environment data. | |
646 ExpectTestIncidentUploaded(1); | |
647 | |
648 // Create a second profile with its own incident on addition. | |
649 CreateProfile( | |
650 "profile2", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_ADD_INCIDENT); | |
651 | |
652 // Let all tasks run. | |
653 task_runner_->RunUntilIdle(); | |
654 | |
655 // Verify that a second report upload took place. | |
656 ExpectTestIncidentUploaded(1); | |
657 } | |
658 | |
659 // Tests that an upload succeeds if the profile is destroyed while it is | |
660 // pending. | |
661 TEST_F(IncidentReportingServiceTest, ProfileDestroyedDuringUpload) { | |
662 // Create a profile for which an incident will be added. | |
663 Profile* profile = CreateProfile( | |
664 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_ADD_INCIDENT); | |
665 | |
666 // Hook up a callback to run when the upload is started that will post a task | |
667 // to delete the profile. This task will run before the upload finishes. | |
668 DeleteProfileOnUpload(profile); | |
669 | |
670 // Let all tasks run. | |
671 task_runner_->RunUntilIdle(); | |
672 | |
673 // Verify that report upload took place and contained the incident and | |
674 // environment data. | |
675 ExpectTestIncidentUploaded(1); | |
676 | |
677 // The lack of a crash indicates that the deleted profile was not accessed by | |
678 // the service while handling the upload response. | |
679 } | |
680 | |
681 // Tests that no upload takes place if the old pref was present. | |
682 TEST_F(IncidentReportingServiceTest, MigrateOldPref) { | |
683 Profile* profile = CreateProfile( | |
684 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_NO_ACTION); | |
685 | |
686 // This is a legacy profile. | |
687 profile->GetPrefs()->SetBoolean(prefs::kSafeBrowsingIncidentReportSent, true); | |
688 | |
689 // Add the test incident. | |
690 AddTestIncident(profile); | |
691 | |
692 // Let all tasks run. | |
693 task_runner_->RunUntilIdle(); | |
694 | |
695 // No upload should have taken place. | |
696 AssertNoUpload(); | |
697 | |
698 // The legacy pref should have been cleared. | |
699 ASSERT_FALSE( | |
700 profile->GetPrefs()->GetBoolean(prefs::kSafeBrowsingIncidentReportSent)); | |
701 | |
702 // Adding the same incident again should still result in no upload. | |
703 AddTestIncident(profile); | |
704 | |
705 // Let all tasks run. | |
706 task_runner_->RunUntilIdle(); | |
707 | |
708 // No upload should have taken place. | |
709 AssertNoUpload(); | |
710 } | |
711 | |
712 // Tests that no upload results from adding an incident that is not affiliated | |
713 // with a profile. | |
714 TEST_F(IncidentReportingServiceTest, ProcessWideNoProfileNoUpload) { | |
715 // Add the test incident. | |
716 AddTestIncident(NULL); | |
717 | |
718 // Let all tasks run. | |
719 task_runner_->RunUntilIdle(); | |
720 | |
721 // No upload should have taken place. | |
722 AssertNoUpload(); | |
723 } | |
724 | |
725 // Tests that there is an upload when a profile is present for a proc-wide | |
726 // incident and that pruning works. | |
727 TEST_F(IncidentReportingServiceTest, ProcessWideOneUpload) { | |
728 // Add a profile that participates in safe browsing. | |
729 CreateProfile( | |
730 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_NO_ACTION); | |
731 | |
732 // Add the test incident. | |
733 AddTestIncident(NULL); | |
734 | |
735 // Let all tasks run. | |
736 task_runner_->RunUntilIdle(); | |
737 | |
738 // An upload should have taken place. | |
739 ExpectTestIncidentUploaded(1); | |
740 | |
741 // Add the incident to the service again. | |
742 AddTestIncident(NULL); | |
743 | |
744 // Let all tasks run. | |
745 task_runner_->RunUntilIdle(); | |
746 | |
747 // Verify that no additional report upload took place. | |
748 AssertNoUpload(); | |
749 } | |
750 | |
751 // Tests that two process-wide incidents of the same type with different | |
752 // payloads added via the same callback lead to two uploads. | |
753 TEST_F(IncidentReportingServiceTest, ProcessWideTwoUploads) { | |
754 // Add a profile that participates in safe browsing. | |
755 CreateProfile( | |
756 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_NO_ACTION); | |
757 | |
758 // Add the test incident. | |
759 safe_browsing::AddIncidentCallback add_incident( | |
760 instance_->GetAddIncidentCallback(NULL)); | |
761 add_incident.Run(MakeTestIncident().Pass()); | |
762 | |
763 // Let all tasks run. | |
764 task_runner_->RunUntilIdle(); | |
765 | |
766 // An upload should have taken place. | |
767 ExpectTestIncidentUploaded(1); | |
768 | |
769 // Add a variation on the incident to the service. | |
770 scoped_ptr<safe_browsing::ClientIncidentReport_IncidentData> incident( | |
771 MakeTestIncident()); | |
772 incident->mutable_tracked_preference()->set_atomic_value("leeches"); | |
773 add_incident.Run(incident.Pass()); | |
774 | |
775 // Let all tasks run. | |
776 task_runner_->RunUntilIdle(); | |
777 | |
778 // Verify that an additional report upload took place. | |
779 ExpectTestIncidentUploaded(1); | |
780 } | |
781 | |
782 // Tests that there is an upload when a profile appears after a proc-wide | |
783 // incident. | |
784 TEST_F(IncidentReportingServiceTest, ProcessWideOneUploadAfterProfile) { | |
785 // Add the test incident. | |
786 AddTestIncident(NULL); | |
787 | |
788 // Let all tasks run. | |
789 task_runner_->RunUntilIdle(); | |
790 | |
791 // Verify that no report upload took place. | |
792 AssertNoUpload(); | |
793 | |
794 // Add a profile that participates in safe browsing. | |
795 CreateProfile( | |
796 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_NO_ACTION); | |
797 | |
798 // Let all tasks run. | |
799 task_runner_->RunUntilIdle(); | |
800 | |
801 // An upload should have taken place. | |
802 ExpectTestIncidentUploaded(1); | |
803 } | |
804 | |
805 // Tests that delayed analysis callbacks are called following the addition of a | |
806 // profile that participates in safe browsing. | |
807 TEST_F(IncidentReportingServiceTest, AnalysisAfterProfile) { | |
808 // Register a callback. | |
809 RegisterAnalysis(ON_DELAYED_ANALYSIS_NO_ACTION); | |
810 | |
811 // Let all tasks run. | |
812 task_runner_->RunUntilIdle(); | |
813 | |
814 // Not run yet. | |
815 ASSERT_FALSE(DelayedAnalysisRan()); | |
816 | |
817 // Add a profile that participates in safe browsing. | |
818 CreateProfile( | |
819 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_NO_ACTION); | |
820 | |
821 // Let all tasks run. | |
822 task_runner_->RunUntilIdle(); | |
823 | |
824 // And now they have. | |
825 ASSERT_TRUE(DelayedAnalysisRan()); | |
826 } | |
827 | |
828 // Tests that delayed analysis callbacks are called following their registration | |
829 // when a profile that participates in safe browsing is already present. | |
830 TEST_F(IncidentReportingServiceTest, AnalysisWhenRegisteredWithProfile) { | |
831 // Add a profile that participates in safe browsing. | |
832 CreateProfile( | |
833 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_NO_ACTION); | |
834 | |
835 // Register a callback. | |
836 RegisterAnalysis(ON_DELAYED_ANALYSIS_NO_ACTION); | |
837 | |
838 // Let all tasks run. | |
839 task_runner_->RunUntilIdle(); | |
840 | |
841 // Confirm that the callbacks were run. | |
842 ASSERT_TRUE(DelayedAnalysisRan()); | |
843 } | |
844 | |
845 // Tests that no upload results from a delayed analysis incident when no | |
846 // safe browsing profile is present. | |
847 TEST_F(IncidentReportingServiceTest, DelayedAnalysisNoProfileNoUpload) { | |
848 // Register a callback that will add an incident. | |
849 RegisterAnalysis(ON_DELAYED_ANALYSIS_ADD_INCIDENT); | |
850 | |
851 // Add a profile that does not participate in safe browsing. | |
852 CreateProfile( | |
853 "profile1", SAFE_BROWSING_OPT_OUT, ON_PROFILE_ADDITION_NO_ACTION); | |
854 | |
855 // Let all tasks run. | |
856 task_runner_->RunUntilIdle(); | |
857 | |
858 // The callback should not have been run. | |
859 ASSERT_FALSE(DelayedAnalysisRan()); | |
860 | |
861 // No upload should have taken place. | |
862 AssertNoUpload(); | |
863 } | |
864 | |
865 // Tests that there is an upload when a profile is present for a delayed | |
866 // analysis incident and that pruning works. | |
867 TEST_F(IncidentReportingServiceTest, DelayedAnalysisOneUpload) { | |
868 // Register a callback that will add an incident. | |
869 RegisterAnalysis(ON_DELAYED_ANALYSIS_ADD_INCIDENT); | |
870 | |
871 // Add a profile that participates in safe browsing. | |
872 CreateProfile( | |
873 "profile1", SAFE_BROWSING_OPT_IN, ON_PROFILE_ADDITION_NO_ACTION); | |
874 | |
875 // Let all tasks run. | |
876 task_runner_->RunUntilIdle(); | |
877 | |
878 // The callback should have been run. | |
879 ASSERT_TRUE(DelayedAnalysisRan()); | |
880 | |
881 // An upload should have taken place. | |
882 ExpectTestIncidentUploaded(1); | |
883 | |
884 // Add the incident to the service again. | |
885 AddTestIncident(NULL); | |
886 | |
887 // Let all tasks run. | |
888 task_runner_->RunUntilIdle(); | |
889 | |
890 // Verify that no additional report upload took place. | |
891 AssertNoUpload(); | |
892 } | |
893 | |
894 // Parallel uploads | |
895 // Shutdown during processing | |
896 // environment colection taking longer than incident delay timer | |
897 // environment colection taking longer than incident delay timer, and then | |
898 // another incident arriving | |
OLD | NEW |