Updating trunk VERSION from 2139.0 to 2140.0
[chromium-blink-merge.git] / components / suggestions / suggestions_service_unittest.cc
blobae9aa916bcac63598b91ba81b316f575148b0322
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.
5 #include "components/suggestions/suggestions_service.h"
7 #include <map>
8 #include <sstream>
9 #include <string>
11 #include "base/bind.h"
12 #include "base/memory/scoped_ptr.h"
13 #include "base/message_loop/message_loop.h"
14 #include "base/metrics/field_trial.h"
15 #include "base/prefs/pref_service.h"
16 #include "base/strings/utf_string_conversions.h"
17 #include "components/suggestions/blacklist_store.h"
18 #include "components/suggestions/image_manager.h"
19 #include "components/suggestions/proto/suggestions.pb.h"
20 #include "components/suggestions/suggestions_store.h"
21 #include "components/suggestions/suggestions_utils.h"
22 #include "components/variations/entropy_provider.h"
23 #include "components/variations/variations_associated_data.h"
24 #include "net/http/http_response_headers.h"
25 #include "net/http/http_status_code.h"
26 #include "net/url_request/test_url_fetcher_factory.h"
27 #include "net/url_request/url_request_status.h"
28 #include "net/url_request/url_request_test_util.h"
29 #include "testing/gmock/include/gmock/gmock.h"
30 #include "testing/gtest/include/gtest/gtest.h"
32 using testing::DoAll;
33 using ::testing::Eq;
34 using ::testing::Return;
35 using testing::SetArgPointee;
36 using ::testing::NiceMock;
37 using ::testing::StrictMock;
38 using ::testing::_;
40 namespace {
42 const char kFakeSuggestionsURL[] = "https://mysuggestions.com/proto";
43 const char kFakeSuggestionsCommonParams[] = "foo=bar";
44 const char kFakeBlacklistPath[] = "/blacklist";
45 const char kFakeBlacklistUrlParam[] = "baz";
47 const char kTestTitle[] = "a title";
48 const char kTestUrl[] = "http://go.com";
49 const char kBlacklistUrl[] = "http://blacklist.com";
50 const int64 kTestDefaultExpiry = 1402200000000000;
51 const int64 kTestSetExpiry = 1404792000000000;
53 scoped_ptr<net::FakeURLFetcher> CreateURLFetcher(
54 const GURL& url, net::URLFetcherDelegate* delegate,
55 const std::string& response_data, net::HttpStatusCode response_code,
56 net::URLRequestStatus::Status status) {
57 scoped_ptr<net::FakeURLFetcher> fetcher(new net::FakeURLFetcher(
58 url, delegate, response_data, response_code, status));
60 if (response_code == net::HTTP_OK) {
61 scoped_refptr<net::HttpResponseHeaders> download_headers(
62 new net::HttpResponseHeaders(""));
63 download_headers->AddHeader("Content-Type: text/html");
64 fetcher->set_response_headers(download_headers);
66 return fetcher.Pass();
69 std::string GetExpectedBlacklistRequestUrl(const GURL& blacklist_url) {
70 std::stringstream request_url;
71 request_url << kFakeSuggestionsURL << kFakeBlacklistPath << "?"
72 << kFakeSuggestionsCommonParams << "&" << kFakeBlacklistUrlParam
73 << "=" << net::EscapeQueryParamValue(blacklist_url.spec(), true);
74 return request_url.str();
77 // GMock matcher for protobuf equality.
78 MATCHER_P(EqualsProto, message, "") {
79 // This implementation assumes protobuf serialization is deterministic, which
80 // is true in practice but technically not something that code is supposed
81 // to rely on. However, it vastly simplifies the implementation.
82 std::string expected_serialized, actual_serialized;
83 message.SerializeToString(&expected_serialized);
84 arg.SerializeToString(&actual_serialized);
85 return expected_serialized == actual_serialized;
88 } // namespace
90 namespace suggestions {
92 scoped_ptr<SuggestionsProfile> CreateSuggestionsProfile() {
93 scoped_ptr<SuggestionsProfile> profile(new SuggestionsProfile());
94 ChromeSuggestion* suggestion = profile->add_suggestions();
95 suggestion->set_title(kTestTitle);
96 suggestion->set_url(kTestUrl);
97 suggestion->set_expiry_ts(kTestSetExpiry);
98 return profile.Pass();
101 // Creates one suggestion with expiry timestamp and one without.
102 SuggestionsProfile CreateSuggestionsProfileWithExpiryTimestamps() {
103 SuggestionsProfile profile;
104 ChromeSuggestion* suggestion = profile.add_suggestions();
105 suggestion->set_title(kTestTitle);
106 suggestion->set_url(kTestUrl);
107 suggestion->set_expiry_ts(kTestSetExpiry);
109 suggestion = profile.add_suggestions();
110 suggestion->set_title(kTestTitle);
111 suggestion->set_url(kTestUrl);
113 return profile;
116 class MockSuggestionsStore : public suggestions::SuggestionsStore {
117 public:
118 MOCK_METHOD1(LoadSuggestions, bool(SuggestionsProfile*));
119 MOCK_METHOD1(StoreSuggestions, bool(const SuggestionsProfile&));
120 MOCK_METHOD0(ClearSuggestions, void());
123 class MockImageManager : public suggestions::ImageManager {
124 public:
125 MockImageManager() {}
126 virtual ~MockImageManager() {}
127 MOCK_METHOD1(Initialize, void(const SuggestionsProfile&));
128 MOCK_METHOD2(GetImageForURL,
129 void(const GURL&,
130 base::Callback<void(const GURL&, const SkBitmap*)>));
133 class MockBlacklistStore : public suggestions::BlacklistStore {
134 public:
135 MOCK_METHOD1(BlacklistUrl, bool(const GURL&));
136 MOCK_METHOD1(GetFirstUrlFromBlacklist, bool(GURL*));
137 MOCK_METHOD1(RemoveUrl, bool(const GURL&));
138 MOCK_METHOD1(FilterSuggestions, void(SuggestionsProfile*));
141 class SuggestionsServiceTest : public testing::Test {
142 public:
143 void CheckSuggestionsData(const SuggestionsProfile& suggestions_profile) {
144 EXPECT_EQ(1, suggestions_profile.suggestions_size());
145 EXPECT_EQ(kTestTitle, suggestions_profile.suggestions(0).title());
146 EXPECT_EQ(kTestUrl, suggestions_profile.suggestions(0).url());
147 ++suggestions_data_check_count_;
150 void ExpectEmptySuggestionsProfile(const SuggestionsProfile& profile) {
151 EXPECT_EQ(0, profile.suggestions_size());
152 ++suggestions_empty_data_count_;
155 int suggestions_data_check_count_;
156 int suggestions_empty_data_count_;
158 protected:
159 SuggestionsServiceTest()
160 : suggestions_data_check_count_(0),
161 suggestions_empty_data_count_(0),
162 factory_(NULL, base::Bind(&CreateURLFetcher)),
163 mock_suggestions_store_(NULL),
164 mock_thumbnail_manager_(NULL) {}
166 virtual ~SuggestionsServiceTest() {}
168 virtual void SetUp() OVERRIDE {
169 request_context_ = new net::TestURLRequestContextGetter(
170 io_message_loop_.message_loop_proxy());
173 // Enables the "ChromeSuggestions.Group1" field trial.
174 void EnableFieldTrial(const std::string& url,
175 const std::string& common_params,
176 const std::string& blacklist_path,
177 const std::string& blacklist_url_param,
178 bool control_group) {
179 // Clear the existing |field_trial_list_| to avoid firing a DCHECK.
180 field_trial_list_.reset(NULL);
181 field_trial_list_.reset(
182 new base::FieldTrialList(new metrics::SHA1EntropyProvider("foo")));
184 variations::testing::ClearAllVariationParams();
185 std::map<std::string, std::string> params;
186 params[kSuggestionsFieldTrialStateParam] =
187 kSuggestionsFieldTrialStateEnabled;
188 if (control_group) {
189 params[kSuggestionsFieldTrialControlParam] =
190 kSuggestionsFieldTrialStateEnabled;
192 params[kSuggestionsFieldTrialURLParam] = url;
193 params[kSuggestionsFieldTrialCommonParamsParam] = common_params;
194 params[kSuggestionsFieldTrialBlacklistPathParam] = blacklist_path;
195 params[kSuggestionsFieldTrialBlacklistUrlParam] = blacklist_url_param;
196 variations::AssociateVariationParams(kSuggestionsFieldTrialName, "Group1",
197 params);
198 field_trial_ = base::FieldTrialList::CreateFieldTrial(
199 kSuggestionsFieldTrialName, "Group1");
200 field_trial_->group();
203 // Should not be called more than once per test since it stashes the
204 // SuggestionsStore in |mock_suggestions_store_|.
205 SuggestionsService* CreateSuggestionsServiceWithMocks() {
206 mock_suggestions_store_ = new StrictMock<MockSuggestionsStore>();
207 mock_thumbnail_manager_ = new StrictMock<MockImageManager>();
208 mock_blacklist_store_ = new MockBlacklistStore();
209 return new SuggestionsService(
210 request_context_.get(),
211 scoped_ptr<SuggestionsStore>(mock_suggestions_store_),
212 scoped_ptr<ImageManager>(mock_thumbnail_manager_),
213 scoped_ptr<BlacklistStore>(mock_blacklist_store_));
216 void FetchSuggestionsDataNoTimeoutHelper(bool interleaved_requests) {
217 // Field trial enabled with a specific suggestions URL.
218 EnableFieldTrial(kFakeSuggestionsURL, kFakeSuggestionsCommonParams,
219 kFakeBlacklistPath, kFakeBlacklistUrlParam, false);
220 scoped_ptr<SuggestionsService> suggestions_service(
221 CreateSuggestionsServiceWithMocks());
222 EXPECT_TRUE(suggestions_service != NULL);
223 scoped_ptr<SuggestionsProfile> suggestions_profile(
224 CreateSuggestionsProfile());
225 // Set up net::FakeURLFetcherFactory.
226 std::string expected_url =
227 (std::string(kFakeSuggestionsURL) + "?") + kFakeSuggestionsCommonParams;
228 factory_.SetFakeResponse(GURL(expected_url),
229 suggestions_profile->SerializeAsString(),
230 net::HTTP_OK, net::URLRequestStatus::SUCCESS);
231 // Set up expectations on the SuggestionsStore. The number depends on
232 // whether the second request is issued (it won't be issued if the second
233 // fetch occurs before the first request has completed).
234 int expected_count = interleaved_requests ? 1 : 2;
235 EXPECT_CALL(*mock_suggestions_store_,
236 StoreSuggestions(EqualsProto(*suggestions_profile)))
237 .Times(expected_count)
238 .WillRepeatedly(Return(true));
240 // Since there are two requests below, Initialize() will be called twice.
241 EXPECT_CALL(*mock_thumbnail_manager_,
242 Initialize(EqualsProto(*suggestions_profile)))
243 .Times(expected_count);
245 // Expect a call to the blacklist store. Return that there's nothing to
246 // blacklist.
247 EXPECT_CALL(*mock_blacklist_store_, FilterSuggestions(_))
248 .Times(expected_count);
249 EXPECT_CALL(*mock_blacklist_store_, GetFirstUrlFromBlacklist(_))
250 .Times(expected_count)
251 .WillRepeatedly(Return(false));
253 // Send the request. The data will be returned to the callback.
254 suggestions_service->FetchSuggestionsDataNoTimeout(base::Bind(
255 &SuggestionsServiceTest::CheckSuggestionsData, base::Unretained(this)));
257 if (!interleaved_requests)
258 io_message_loop_.RunUntilIdle(); // Let request complete.
260 // Send the request a second time.
261 suggestions_service->FetchSuggestionsDataNoTimeout(base::Bind(
262 &SuggestionsServiceTest::CheckSuggestionsData, base::Unretained(this)));
264 // (Testing only) wait until suggestion fetch is complete.
265 io_message_loop_.RunUntilIdle();
267 // Ensure that CheckSuggestionsData() ran twice.
268 EXPECT_EQ(2, suggestions_data_check_count_);
271 protected:
272 base::MessageLoopForIO io_message_loop_;
273 net::FakeURLFetcherFactory factory_;
274 // Only used if the SuggestionsService is built with mocks. Not owned.
275 MockSuggestionsStore* mock_suggestions_store_;
276 MockImageManager* mock_thumbnail_manager_;
277 MockBlacklistStore* mock_blacklist_store_;
278 scoped_refptr<net::TestURLRequestContextGetter> request_context_;
280 private:
281 scoped_ptr<base::FieldTrialList> field_trial_list_;
282 scoped_refptr<base::FieldTrial> field_trial_;
284 DISALLOW_COPY_AND_ASSIGN(SuggestionsServiceTest);
287 TEST_F(SuggestionsServiceTest, IsControlGroup) {
288 // Field trial enabled.
289 EnableFieldTrial("", "", "", "", false);
290 EXPECT_FALSE(SuggestionsService::IsControlGroup());
292 EnableFieldTrial("", "", "", "", true);
293 EXPECT_TRUE(SuggestionsService::IsControlGroup());
296 TEST_F(SuggestionsServiceTest, FetchSuggestionsDataNoTimeout) {
297 FetchSuggestionsDataNoTimeoutHelper(false);
300 TEST_F(SuggestionsServiceTest, FetchSuggestionsDataNoTimeoutInterleaved) {
301 FetchSuggestionsDataNoTimeoutHelper(true);
304 TEST_F(SuggestionsServiceTest, FetchSuggestionsDataRequestError) {
305 // Field trial enabled with a specific suggestions URL.
306 EnableFieldTrial(kFakeSuggestionsURL, kFakeSuggestionsCommonParams,
307 kFakeBlacklistPath, kFakeBlacklistUrlParam, false);
308 scoped_ptr<SuggestionsService> suggestions_service(
309 CreateSuggestionsServiceWithMocks());
310 EXPECT_TRUE(suggestions_service != NULL);
312 // Fake a request error.
313 std::string expected_url =
314 (std::string(kFakeSuggestionsURL) + "?") + kFakeSuggestionsCommonParams;
315 factory_.SetFakeResponse(GURL(expected_url), "irrelevant", net::HTTP_OK,
316 net::URLRequestStatus::FAILED);
318 // Set up expectations on the SuggestionsStore.
319 EXPECT_CALL(*mock_suggestions_store_, LoadSuggestions(_))
320 .WillOnce(Return(true));
321 EXPECT_CALL(*mock_thumbnail_manager_, Initialize(_));
323 // Expect a call to the blacklist store. Return that there's nothing to
324 // blacklist.
325 EXPECT_CALL(*mock_blacklist_store_, FilterSuggestions(_));
326 EXPECT_CALL(*mock_blacklist_store_, GetFirstUrlFromBlacklist(_))
327 .WillOnce(Return(false));
329 // Send the request. Empty data will be returned to the callback.
330 suggestions_service->FetchSuggestionsData(
331 INITIALIZED_ENABLED_HISTORY, // Normal mode.
332 base::Bind(&SuggestionsServiceTest::ExpectEmptySuggestionsProfile,
333 base::Unretained(this)));
335 // (Testing only) wait until suggestion fetch is complete.
336 io_message_loop_.RunUntilIdle();
338 // Ensure that ExpectEmptySuggestionsProfile ran once.
339 EXPECT_EQ(1, suggestions_empty_data_count_);
342 TEST_F(SuggestionsServiceTest, FetchSuggestionsDataResponseNotOK) {
343 // Field trial enabled with a specific suggestions URL.
344 EnableFieldTrial(kFakeSuggestionsURL, kFakeSuggestionsCommonParams,
345 kFakeBlacklistPath, kFakeBlacklistUrlParam, false);
346 scoped_ptr<SuggestionsService> suggestions_service(
347 CreateSuggestionsServiceWithMocks());
348 EXPECT_TRUE(suggestions_service != NULL);
350 // Response code != 200.
351 std::string expected_url =
352 (std::string(kFakeSuggestionsURL) + "?") + kFakeSuggestionsCommonParams;
353 factory_.SetFakeResponse(GURL(expected_url), "irrelevant",
354 net::HTTP_BAD_REQUEST,
355 net::URLRequestStatus::SUCCESS);
357 // Set up expectations on the SuggestionsStore.
358 EXPECT_CALL(*mock_suggestions_store_, ClearSuggestions());
360 // Expect a call to the blacklist store. Return that there's nothing to
361 // blacklist.
362 EXPECT_CALL(*mock_blacklist_store_, GetFirstUrlFromBlacklist(_))
363 .WillOnce(Return(false));
365 // Send the request. Empty data will be returned to the callback.
366 suggestions_service->FetchSuggestionsData(
367 INITIALIZED_ENABLED_HISTORY, // Normal mode.
368 base::Bind(&SuggestionsServiceTest::ExpectEmptySuggestionsProfile,
369 base::Unretained(this)));
371 // (Testing only) wait until suggestion fetch is complete.
372 io_message_loop_.RunUntilIdle();
374 // Ensure that ExpectEmptySuggestionsProfile ran once.
375 EXPECT_EQ(1, suggestions_empty_data_count_);
378 TEST_F(SuggestionsServiceTest, FetchSuggestionsDataSyncDisabled) {
379 // Field trial enabled with a specific suggestions URL.
380 EnableFieldTrial(kFakeSuggestionsURL, kFakeSuggestionsCommonParams,
381 kFakeBlacklistPath, kFakeBlacklistUrlParam, false);
382 scoped_ptr<SuggestionsService> suggestions_service(
383 CreateSuggestionsServiceWithMocks());
384 EXPECT_TRUE(suggestions_service != NULL);
386 // Set up expectations on the SuggestionsStore.
387 EXPECT_CALL(*mock_suggestions_store_, ClearSuggestions());
389 // Send the request. Cache is cleared and empty data will be returned to the
390 // callback.
391 suggestions_service->FetchSuggestionsData(
392 SYNC_OR_HISTORY_SYNC_DISABLED,
393 base::Bind(&SuggestionsServiceTest::ExpectEmptySuggestionsProfile,
394 base::Unretained(this)));
396 // Wait for posted task to complete.
397 base::MessageLoop::current()->RunUntilIdle();
399 // Ensure that ExpectEmptySuggestionsProfile ran once.
400 EXPECT_EQ(1, suggestions_empty_data_count_);
403 TEST_F(SuggestionsServiceTest, FetchSuggestionsDataSyncNotInitializedEnabled) {
404 // Field trial enabled with a specific suggestions URL.
405 EnableFieldTrial(kFakeSuggestionsURL, kFakeSuggestionsCommonParams,
406 kFakeBlacklistPath, kFakeBlacklistUrlParam, false);
407 scoped_ptr<SuggestionsService> suggestions_service(
408 CreateSuggestionsServiceWithMocks());
409 EXPECT_TRUE(suggestions_service != NULL);
410 scoped_ptr<SuggestionsProfile> suggestions_profile(
411 CreateSuggestionsProfile());
413 // Expectations.
414 EXPECT_CALL(*mock_suggestions_store_, LoadSuggestions(_))
415 .WillOnce(DoAll(SetArgPointee<0>(*suggestions_profile), Return(true)));
416 EXPECT_CALL(*mock_thumbnail_manager_,
417 Initialize(EqualsProto(*suggestions_profile)));
418 EXPECT_CALL(*mock_blacklist_store_, FilterSuggestions(_));
420 // Send the request. In this state, cached data will be returned to the
421 // caller.
422 suggestions_service->FetchSuggestionsData(
423 NOT_INITIALIZED_ENABLED,
424 base::Bind(&SuggestionsServiceTest::CheckSuggestionsData,
425 base::Unretained(this)));
427 // Wait for posted task to complete.
428 base::MessageLoop::current()->RunUntilIdle();
430 // Ensure that CheckSuggestionsData ran once.
431 EXPECT_EQ(1, suggestions_data_check_count_);
434 TEST_F(SuggestionsServiceTest, BlacklistURL) {
435 EnableFieldTrial(kFakeSuggestionsURL, kFakeSuggestionsCommonParams,
436 kFakeBlacklistPath, kFakeBlacklistUrlParam, false);
437 scoped_ptr<SuggestionsService> suggestions_service(
438 CreateSuggestionsServiceWithMocks());
439 EXPECT_TRUE(suggestions_service != NULL);
441 GURL blacklist_url(kBlacklistUrl);
442 std::string request_url = GetExpectedBlacklistRequestUrl(blacklist_url);
443 scoped_ptr<SuggestionsProfile> suggestions_profile(
444 CreateSuggestionsProfile());
445 factory_.SetFakeResponse(GURL(request_url),
446 suggestions_profile->SerializeAsString(),
447 net::HTTP_OK, net::URLRequestStatus::SUCCESS);
449 // Set up expectations on the SuggestionsStore.
450 EXPECT_CALL(*mock_suggestions_store_,
451 StoreSuggestions(EqualsProto(*suggestions_profile)))
452 .WillOnce(Return(true));
453 EXPECT_CALL(*mock_thumbnail_manager_,
454 Initialize(EqualsProto(*suggestions_profile)));
456 // Expected calls to the blacklist store.
457 EXPECT_CALL(*mock_blacklist_store_, BlacklistUrl(Eq(blacklist_url)))
458 .WillOnce(Return(true));
459 EXPECT_CALL(*mock_blacklist_store_, RemoveUrl(Eq(blacklist_url)))
460 .WillOnce(Return(true));
461 EXPECT_CALL(*mock_blacklist_store_, FilterSuggestions(_));
462 EXPECT_CALL(*mock_blacklist_store_, GetFirstUrlFromBlacklist(_))
463 .WillOnce(Return(false));
465 // Send the request. The data will be returned to the callback.
466 suggestions_service->BlacklistURL(
467 blacklist_url, base::Bind(&SuggestionsServiceTest::CheckSuggestionsData,
468 base::Unretained(this)));
470 // (Testing only) wait until blacklist request is complete.
471 io_message_loop_.RunUntilIdle();
473 // Ensure that CheckSuggestionsData() ran once.
474 EXPECT_EQ(1, suggestions_data_check_count_);
477 // Initial blacklist request fails, triggering a scheduled upload which
478 // succeeds.
479 TEST_F(SuggestionsServiceTest, BlacklistURLFails) {
480 EnableFieldTrial(kFakeSuggestionsURL, kFakeSuggestionsCommonParams,
481 kFakeBlacklistPath, kFakeBlacklistUrlParam, false);
482 scoped_ptr<SuggestionsService> suggestions_service(
483 CreateSuggestionsServiceWithMocks());
484 EXPECT_TRUE(suggestions_service != NULL);
485 suggestions_service->set_blacklist_delay(0); // Don't wait during a test!
486 scoped_ptr<SuggestionsProfile> suggestions_profile(
487 CreateSuggestionsProfile());
488 GURL blacklist_url(kBlacklistUrl);
490 // Set up behavior for the first call to blacklist.
491 std::string request_url = GetExpectedBlacklistRequestUrl(blacklist_url);
492 factory_.SetFakeResponse(GURL(request_url), "irrelevant", net::HTTP_OK,
493 net::URLRequestStatus::FAILED);
495 // Expectations specific to the first request.
496 EXPECT_CALL(*mock_blacklist_store_, BlacklistUrl(Eq(blacklist_url)))
497 .WillOnce(Return(true));
498 EXPECT_CALL(*mock_suggestions_store_, LoadSuggestions(_))
499 .WillOnce(DoAll(SetArgPointee<0>(*suggestions_profile), Return(true)));
501 // Expectations specific to the second request.
502 EXPECT_CALL(*mock_suggestions_store_,
503 StoreSuggestions(EqualsProto(*suggestions_profile)))
504 .WillOnce(Return(true));
505 EXPECT_CALL(*mock_blacklist_store_, RemoveUrl(Eq(blacklist_url)))
506 .WillOnce(Return(true));
508 // Expectations pertaining to both requests.
509 EXPECT_CALL(*mock_blacklist_store_, FilterSuggestions(_)).Times(2);
510 EXPECT_CALL(*mock_blacklist_store_, GetFirstUrlFromBlacklist(_))
511 .WillOnce(Return(true))
512 .WillOnce(DoAll(SetArgPointee<0>(blacklist_url), Return(true)))
513 .WillOnce(Return(false));
514 // There will be two calls to Initialize() (one store, one load).
515 EXPECT_CALL(*mock_thumbnail_manager_,
516 Initialize(EqualsProto(*suggestions_profile)))
517 .Times(2);
519 // Send the request. The data will be returned to the callback.
520 suggestions_service->BlacklistURL(
521 blacklist_url, base::Bind(&SuggestionsServiceTest::CheckSuggestionsData,
522 base::Unretained(this)));
524 // The first FakeURLFetcher was created; we can now set up behavior for the
525 // second call to blacklist.
526 factory_.SetFakeResponse(GURL(request_url),
527 suggestions_profile->SerializeAsString(),
528 net::HTTP_OK, net::URLRequestStatus::SUCCESS);
530 // (Testing only) wait until both requests are complete.
531 io_message_loop_.RunUntilIdle();
532 // ... Other task gets posted to the message loop.
533 base::MessageLoop::current()->RunUntilIdle();
534 // ... And completes.
535 io_message_loop_.RunUntilIdle();
537 // Ensure that CheckSuggestionsData() ran once.
538 EXPECT_EQ(1, suggestions_data_check_count_);
541 TEST_F(SuggestionsServiceTest, GetBlacklistedUrl) {
542 EnableFieldTrial(kFakeSuggestionsURL, kFakeSuggestionsCommonParams,
543 kFakeBlacklistPath, kFakeBlacklistUrlParam, false);
545 scoped_ptr<GURL> request_url;
546 scoped_ptr<net::FakeURLFetcher> fetcher;
547 GURL retrieved_url;
549 // Not a blacklist request.
550 request_url.reset(new GURL("http://not-blacklisting.com/a?b=c"));
551 fetcher = CreateURLFetcher(*request_url, NULL, "", net::HTTP_OK,
552 net::URLRequestStatus::SUCCESS);
553 EXPECT_FALSE(SuggestionsService::GetBlacklistedUrl(*fetcher, &retrieved_url));
555 // An actual blacklist request.
556 string blacklisted_url = "http://blacklisted.com/a?b=c&d=e";
557 string encoded_blacklisted_url =
558 "http%3A%2F%2Fblacklisted.com%2Fa%3Fb%3Dc%26d%3De";
559 string blacklist_request_prefix =
560 "https://mysuggestions.com/proto/blacklist?foo=bar&baz=";
561 request_url.reset(
562 new GURL(blacklist_request_prefix + encoded_blacklisted_url));
563 fetcher.reset();
564 fetcher = CreateURLFetcher(*request_url, NULL, "", net::HTTP_OK,
565 net::URLRequestStatus::SUCCESS);
566 EXPECT_TRUE(SuggestionsService::GetBlacklistedUrl(*fetcher, &retrieved_url));
567 EXPECT_EQ(blacklisted_url, retrieved_url.spec());
570 TEST_F(SuggestionsServiceTest, UpdateBlacklistDelay) {
571 scoped_ptr<SuggestionsService> suggestions_service(
572 CreateSuggestionsServiceWithMocks());
573 int initial_delay = suggestions_service->blacklist_delay();
575 // Delay unchanged on success.
576 suggestions_service->UpdateBlacklistDelay(true);
577 EXPECT_EQ(initial_delay, suggestions_service->blacklist_delay());
579 // Delay increases on failure.
580 suggestions_service->UpdateBlacklistDelay(false);
581 EXPECT_GT(suggestions_service->blacklist_delay(), initial_delay);
583 // Delay resets on success.
584 suggestions_service->UpdateBlacklistDelay(true);
585 EXPECT_EQ(initial_delay, suggestions_service->blacklist_delay());
588 TEST_F(SuggestionsServiceTest, CheckDefaultTimeStamps) {
589 scoped_ptr<SuggestionsService> suggestions_service(
590 CreateSuggestionsServiceWithMocks());
591 SuggestionsProfile suggestions =
592 CreateSuggestionsProfileWithExpiryTimestamps();
593 suggestions_service->SetDefaultExpiryTimestamp(&suggestions,
594 kTestDefaultExpiry);
595 EXPECT_EQ(kTestSetExpiry, suggestions.suggestions(0).expiry_ts());
596 EXPECT_EQ(kTestDefaultExpiry, suggestions.suggestions(1).expiry_ts());
598 } // namespace suggestions