Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "components/ntp_snippets/ntp_snippets_service.h" | 5 #include "components/ntp_snippets/ntp_snippets_service.h" |
| 6 | 6 |
| 7 #include <memory> | 7 #include <memory> |
| 8 #include <vector> | 8 #include <vector> |
| 9 | 9 |
| 10 #include "base/command_line.h" | 10 #include "base/command_line.h" |
| (...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 46 namespace { | 46 namespace { |
| 47 | 47 |
| 48 MATCHER_P(IdEq, value, "") { | 48 MATCHER_P(IdEq, value, "") { |
| 49 return arg->id() == value; | 49 return arg->id() == value; |
| 50 } | 50 } |
| 51 | 51 |
| 52 const base::Time::Exploded kDefaultCreationTime = {2015, 11, 4, 25, 13, 46, 45}; | 52 const base::Time::Exploded kDefaultCreationTime = {2015, 11, 4, 25, 13, 46, 45}; |
| 53 const char kTestContentSnippetsServerFormat[] = | 53 const char kTestContentSnippetsServerFormat[] = |
| 54 "https://chromereader-pa.googleapis.com/v1/fetch?key=%s"; | 54 "https://chromereader-pa.googleapis.com/v1/fetch?key=%s"; |
| 55 | 55 |
| 56 const char kSnippetUrl[] = "http://localhost/foobar"; | |
| 57 const char kSnippetTitle[] = "Title"; | |
| 58 const char kSnippetText[] = "Snippet"; | |
| 59 const char kSnippetSalientImage[] = "http://localhost/salient_image"; | |
| 60 const char kSnippetPublisherName[] = "Foo News"; | |
| 61 const char kSnippetAmpUrl[] = "http://localhost/amp"; | |
| 62 const float kSnippetScore = 5.0; | |
| 63 | |
| 56 base::Time GetDefaultCreationTime() { | 64 base::Time GetDefaultCreationTime() { |
| 57 return base::Time::FromUTCExploded(kDefaultCreationTime); | 65 return base::Time::FromUTCExploded(kDefaultCreationTime); |
| 58 } | 66 } |
| 59 | 67 |
| 60 std::string GetTestJson(const std::string& content_creation_time_str, | 68 base::Time GetDefaultExpirationTime() { |
| 61 const std::string& expiry_time_str) { | 69 return base::Time::Now() + base::TimeDelta::FromHours(1); |
| 62 char json_str_format[] = | |
| 63 "{ \"recos\": [ " | |
| 64 "{ \"contentInfo\": {" | |
| 65 "\"url\" : \"http://localhost/foobar\"," | |
| 66 "\"title\" : \"Title\"," | |
| 67 "\"snippet\" : \"Snippet\"," | |
| 68 "\"thumbnailUrl\" : \"http://localhost/salient_image\"," | |
| 69 "\"creationTimestampSec\" : \"%s\"," | |
| 70 "\"expiryTimestampSec\" : \"%s\"," | |
| 71 "\"sourceCorpusInfo\" : [ " | |
| 72 "{\"ampUrl\" : \"http://localhost/amp\"," | |
| 73 "\"corpusId\" : \"http://localhost/foobar\"," | |
| 74 "\"publisherData\": { \"sourceName\" : \"Foo News\"}}]" | |
| 75 "}}" | |
| 76 "]}"; | |
| 77 | |
| 78 return base::StringPrintf(json_str_format, content_creation_time_str.c_str(), | |
| 79 expiry_time_str.c_str()); | |
| 80 } | 70 } |
| 81 | 71 |
| 82 std::string GetTestJsonWithSources(const std::string& content_creation_time_str, | 72 std::string GetTestJson(const std::vector<std::string>& snippets) { |
| 83 const std::string& expiry_time_str, | 73 char json_str_format[] = "{ \"recos\": [ %s]}"; |
|
Marc Treib
2016/05/17 12:38:45
Might as well just inline this below (and remove t
jkrcal
2016/05/20 09:50:50
Done.
| |
| 84 const std::vector<std::string>& source_urls, | 74 return base::StringPrintf(json_str_format, |
| 85 const std::vector<std::string>& publishers, | 75 base::JoinString(snippets, ", ").c_str()); |
| 86 const std::vector<std::string>& amp_urls) { | 76 } |
| 77 | |
| 78 std::string GetSnippetWithSources(const std::string& url, | |
|
Marc Treib
2016/05/17 12:38:45
GetSnippetWithTimesAndSources? If we have "With...
jkrcal
2016/05/20 09:50:50
Done.
| |
| 79 const std::string& content_creation_time_str, | |
| 80 const std::string& expiry_time_str, | |
| 81 const std::vector<std::string>& source_urls, | |
| 82 const std::vector<std::string>& publishers, | |
| 83 const std::vector<std::string>& amp_urls) { | |
| 87 char json_str_format[] = | 84 char json_str_format[] = |
| 88 "{ \"recos\": [ " | |
| 89 "{ \"contentInfo\": {" | 85 "{ \"contentInfo\": {" |
| 90 "\"url\" : \"http://localhost/foobar\"," | 86 "\"url\" : \"%s\"," |
| 91 "\"title\" : \"Title\"," | 87 "\"title\" : \"%s\"," |
| 92 "\"snippet\" : \"Snippet\"," | 88 "\"snippet\" : \"%s\"," |
| 93 "\"thumbnailUrl\" : \"http://localhost/salient_image\"," | 89 "\"thumbnailUrl\" : \"%s\"," |
| 94 "\"creationTimestampSec\" : \"%s\"," | 90 "\"creationTimestampSec\" : \"%s\"," |
| 95 "\"expiryTimestampSec\" : \"%s\"," | 91 "\"expiryTimestampSec\" : \"%s\"," |
| 96 "\"sourceCorpusInfo\" : [%s]" | 92 "\"sourceCorpusInfo\" : [%s]" |
| 97 "}}" | 93 "}, " |
| 98 "]}"; | 94 "\"score\" : %f}"; |
| 99 | 95 |
| 100 char source_corpus_info_format[] = | 96 char source_corpus_info_format[] = |
| 101 "{\"corpusId\": \"%s\"," | 97 "{\"corpusId\": \"%s\"," |
| 102 "\"publisherData\": {" | 98 "\"publisherData\": {" |
| 103 "\"sourceName\": \"%s\"" | 99 "\"sourceName\": \"%s\"" |
| 104 "}," | 100 "}," |
| 105 "\"ampUrl\": \"%s\"}"; | 101 "\"ampUrl\": \"%s\"}"; |
| 106 | 102 |
| 107 std::string source_corpus_info_list_str; | 103 std::string source_corpus_info_list_str; |
| 108 for (size_t i = 0; i < source_urls.size(); ++i) { | 104 for (size_t i = 0; i < source_urls.size(); ++i) { |
| 109 std::string source_corpus_info_str = | 105 std::string source_corpus_info_str = |
| 110 base::StringPrintf(source_corpus_info_format, | 106 base::StringPrintf(source_corpus_info_format, |
| 111 source_urls[i].empty() ? "" : source_urls[i].c_str(), | 107 source_urls[i].empty() ? "" : source_urls[i].c_str(), |
| 112 publishers[i].empty() ? "" : publishers[i].c_str(), | 108 publishers[i].empty() ? "" : publishers[i].c_str(), |
| 113 amp_urls[i].empty() ? "" : amp_urls[i].c_str()); | 109 amp_urls[i].empty() ? "" : amp_urls[i].c_str()); |
| 114 source_corpus_info_list_str.append(source_corpus_info_str); | 110 source_corpus_info_list_str.append(source_corpus_info_str); |
| 115 source_corpus_info_list_str.append(","); | 111 source_corpus_info_list_str.append(","); |
| 116 } | 112 } |
| 117 // Remove the last comma | 113 // Remove the last comma |
| 118 source_corpus_info_list_str.erase(source_corpus_info_list_str.size()-1, 1); | 114 source_corpus_info_list_str.erase(source_corpus_info_list_str.size()-1, 1); |
| 119 return base::StringPrintf(json_str_format, content_creation_time_str.c_str(), | 115 return base::StringPrintf(json_str_format, url.c_str(), kSnippetTitle, |
| 116 kSnippetText, kSnippetSalientImage, | |
| 117 content_creation_time_str.c_str(), | |
| 120 expiry_time_str.c_str(), | 118 expiry_time_str.c_str(), |
| 121 source_corpus_info_list_str.c_str()); | 119 source_corpus_info_list_str.c_str(), kSnippetScore); |
| 122 } | 120 } |
| 123 | 121 |
| 124 std::string GetTestJsonWithSources(const std::vector<std::string>& source_urls, | 122 std::string GetSnippetWithSources(const std::vector<std::string>& source_urls, |
| 125 const std::vector<std::string>& publishers, | 123 const std::vector<std::string>& publishers, |
| 126 const std::vector<std::string>& amp_urls) { | 124 const std::vector<std::string>& amp_urls) { |
| 127 base::Time expiry_time = base::Time::Now() + base::TimeDelta::FromHours(1); | 125 return GetSnippetWithSources( |
| 128 return GetTestJsonWithSources( | 126 kSnippetUrl, NTPSnippet::TimeToJsonString(GetDefaultCreationTime()), |
| 129 NTPSnippet::TimeToJsonString(GetDefaultCreationTime()), | 127 NTPSnippet::TimeToJsonString(GetDefaultExpirationTime()), source_urls, |
| 130 NTPSnippet::TimeToJsonString(expiry_time), source_urls, publishers, | 128 publishers, amp_urls); |
| 131 amp_urls); | |
| 132 } | 129 } |
| 133 | 130 |
| 134 std::string GetTestJson(const std::string& content_creation_time_str) { | 131 std::string GetSnippet(const std::string& url, |
|
Marc Treib
2016/05/17 12:38:45
Also here: GetSnippetWithUrlAndTimes
jkrcal
2016/05/20 09:50:50
Done.
| |
| 135 base::Time expiry_time = base::Time::Now() + base::TimeDelta::FromHours(1); | 132 const std::string& content_creation_time_str, |
| 136 return GetTestJson(content_creation_time_str, | 133 const std::string& expiry_time_str) { |
| 137 NTPSnippet::TimeToJsonString(expiry_time)); | 134 return GetSnippetWithSources( |
| 135 url, content_creation_time_str, expiry_time_str, | |
| 136 std::vector<std::string>({kSnippetUrl}), | |
|
Marc Treib
2016/05/17 12:38:45
Is the std::vector<std::string>() required here?
jkrcal
2016/05/20 09:50:50
You are right, not really. Though it seems that at
Marc Treib
2016/05/20 09:59:13
Makes sense - without that, you'll probably get a
| |
| 137 std::vector<std::string>({kSnippetPublisherName}), | |
| 138 std::vector<std::string>({kSnippetAmpUrl})); | |
| 138 } | 139 } |
| 139 | 140 |
| 140 std::string GetTestJson() { | 141 std::string GetSnippet() { |
| 141 return GetTestJson(NTPSnippet::TimeToJsonString(GetDefaultCreationTime())); | 142 return GetSnippet(kSnippetUrl, |
| 143 NTPSnippet::TimeToJsonString(GetDefaultCreationTime()), | |
| 144 NTPSnippet::TimeToJsonString(GetDefaultExpirationTime())); | |
| 142 } | 145 } |
| 143 | 146 |
| 144 std::string GetTestExpiredJson() { | 147 std::string GetSnippetWithTimes(const std::string& content_creation_time_str, |
| 145 return GetTestJson(NTPSnippet::TimeToJsonString(GetDefaultCreationTime()), | 148 const std::string& expiry_time_str) { |
| 146 NTPSnippet::TimeToJsonString(base::Time::Now())); | 149 return GetSnippet(kSnippetUrl, content_creation_time_str, expiry_time_str); |
| 147 } | 150 } |
| 148 | 151 |
| 149 std::string GetInvalidJson() { | 152 std::string GetSnippetWithUrl(const std::string& url) { |
| 150 std::string json_str = GetTestJson(); | 153 return GetSnippet(url, NTPSnippet::TimeToJsonString(GetDefaultCreationTime()), |
| 154 NTPSnippet::TimeToJsonString(GetDefaultExpirationTime())); | |
| 155 } | |
| 156 | |
| 157 std::string GetExpiredSnippet() { | |
| 158 return GetSnippetWithTimes( | |
| 159 NTPSnippet::TimeToJsonString(GetDefaultCreationTime()), | |
| 160 NTPSnippet::TimeToJsonString(base::Time::Now())); | |
| 161 } | |
| 162 | |
| 163 std::string GetInvalidSnippet() { | |
| 164 std::string json_str = GetSnippet(); | |
| 151 // Make the json invalid by removing the final closing brace. | 165 // Make the json invalid by removing the final closing brace. |
| 152 return json_str.substr(0, json_str.size() - 1); | 166 return json_str.substr(0, json_str.size() - 1); |
| 153 } | 167 } |
| 154 | 168 |
| 155 std::string GetIncompleteJson() { | 169 std::string GetIncompleteSnippet() { |
| 156 std::string json_str = GetTestJson(); | 170 std::string json_str = GetSnippet(); |
| 157 // Rename the "url" entry. The result is syntactically valid json that will | 171 // Rename the "url" entry. The result is syntactically valid json that will |
| 158 // fail to parse as snippets. | 172 // fail to parse as snippets. |
| 159 size_t pos = json_str.find("\"url\""); | 173 size_t pos = json_str.find("\"url\""); |
| 160 if (pos == std::string::npos) { | 174 if (pos == std::string::npos) { |
| 161 NOTREACHED(); | 175 NOTREACHED(); |
| 162 return std::string(); | 176 return std::string(); |
| 163 } | 177 } |
| 164 json_str[pos + 1] = 'x'; | 178 json_str[pos + 1] = 'x'; |
| 165 return json_str; | 179 return json_str; |
| 166 } | 180 } |
| (...skipping 118 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 285 | 299 |
| 286 TEST_F(NTPSnippetsServiceTest, ScheduleIfEnabled) { | 300 TEST_F(NTPSnippetsServiceTest, ScheduleIfEnabled) { |
| 287 // SetUp() checks that Schedule is called. | 301 // SetUp() checks that Schedule is called. |
| 288 } | 302 } |
| 289 | 303 |
| 290 TEST_F(NTPSnippetsServiceDisabledTest, Unschedule) { | 304 TEST_F(NTPSnippetsServiceDisabledTest, Unschedule) { |
| 291 // SetUp() checks that Unschedule is called. | 305 // SetUp() checks that Unschedule is called. |
| 292 } | 306 } |
| 293 | 307 |
| 294 TEST_F(NTPSnippetsServiceTest, Full) { | 308 TEST_F(NTPSnippetsServiceTest, Full) { |
| 295 std::string json_str(GetTestJson()); | 309 std::string json_str(GetTestJson({GetSnippet()})); |
| 296 | 310 |
| 297 LoadFromJSONString(json_str); | 311 LoadFromJSONString(json_str); |
| 298 ASSERT_THAT(service()->snippets(), SizeIs(1)); | 312 ASSERT_THAT(service()->snippets(), SizeIs(1)); |
| 299 const NTPSnippet& snippet = *service()->snippets().front(); | 313 const NTPSnippet& snippet = *service()->snippets().front(); |
| 300 EXPECT_EQ(snippet.id(), "http://localhost/foobar"); | 314 |
| 301 EXPECT_EQ(snippet.best_source().publisher_name, "Foo News"); | 315 EXPECT_EQ(snippet.id(), kSnippetUrl); |
| 302 EXPECT_EQ(snippet.title(), "Title"); | 316 EXPECT_EQ(snippet.title(), kSnippetTitle); |
| 303 EXPECT_EQ(snippet.snippet(), "Snippet"); | 317 EXPECT_EQ(snippet.snippet(), kSnippetText); |
| 304 EXPECT_EQ(snippet.salient_image_url(), | 318 EXPECT_EQ(snippet.salient_image_url(), GURL(kSnippetSalientImage)); |
| 305 GURL("http://localhost/salient_image")); | |
| 306 EXPECT_EQ(GetDefaultCreationTime(), snippet.publish_date()); | 319 EXPECT_EQ(GetDefaultCreationTime(), snippet.publish_date()); |
| 307 EXPECT_EQ(snippet.best_source().amp_url.spec(), | 320 EXPECT_EQ(snippet.best_source().publisher_name, kSnippetPublisherName); |
| 308 GURL("http://localhost/amp").spec()); | 321 EXPECT_EQ(snippet.best_source().amp_url.spec(), GURL(kSnippetAmpUrl).spec()); |
|
Marc Treib
2016/05/17 12:38:45
I think the ".spec()" isn't required here - GURLs
jkrcal
2016/05/20 09:50:50
Done.
| |
| 309 } | 322 } |
| 310 | 323 |
| 311 TEST_F(NTPSnippetsServiceTest, Clear) { | 324 TEST_F(NTPSnippetsServiceTest, Clear) { |
| 312 std::string json_str(GetTestJson()); | 325 std::string json_str(GetTestJson({GetSnippet()})); |
| 313 | 326 |
| 314 LoadFromJSONString(json_str); | 327 LoadFromJSONString(json_str); |
| 315 EXPECT_THAT(service()->snippets(), SizeIs(1)); | 328 EXPECT_THAT(service()->snippets(), SizeIs(1)); |
| 316 | 329 |
| 317 service()->ClearSnippets(); | 330 service()->ClearSnippets(); |
| 318 EXPECT_THAT(service()->snippets(), IsEmpty()); | 331 EXPECT_THAT(service()->snippets(), IsEmpty()); |
| 319 } | 332 } |
| 320 | 333 |
| 321 TEST_F(NTPSnippetsServiceTest, InsertAtFront) { | 334 TEST_F(NTPSnippetsServiceTest, InsertAtFront) { |
| 322 base::Time expiry_time = base::Time::Now() + base::TimeDelta::FromHours(1); | 335 std::string first("http://first"); |
| 323 char json_str_format[] = | 336 LoadFromJSONString(GetTestJson({GetSnippetWithUrl(first)})); |
| 324 "{ \"recos\": [ " | 337 EXPECT_THAT(service()->snippets(), ElementsAre(IdEq(first))); |
| 325 "{ \"contentInfo\": {" | |
| 326 "\"url\" : \"%s\"," | |
| 327 "\"title\" : \"Title\"," | |
| 328 "\"snippet\" : \"Snippet\"," | |
| 329 "\"thumbnailUrl\" : \"http://localhost/salient_image\"," | |
| 330 "\"creationTimestampSec\" : \"%s\"," | |
| 331 "\"expiryTimestampSec\" : \"%s\"," | |
| 332 "\"sourceCorpusInfo\" : [{\"corpusId\": \"http://first\"," | |
| 333 "\"publisherData\": {" | |
| 334 "\"sourceName\": \"Source 1\"" | |
| 335 "}," | |
| 336 "\"ampUrl\": \"\"}]" | |
| 337 "}}" | |
| 338 "]}"; | |
| 339 std::string json_str(base::StringPrintf( | |
| 340 json_str_format, "http://first", | |
| 341 NTPSnippet::TimeToJsonString(GetDefaultCreationTime()).c_str(), | |
| 342 NTPSnippet::TimeToJsonString(expiry_time).c_str())); | |
| 343 | 338 |
| 344 LoadFromJSONString(json_str); | 339 std::string second("http://second"); |
| 345 | 340 LoadFromJSONString(GetTestJson({GetSnippetWithUrl(second)})); |
| 346 EXPECT_THAT(service()->snippets(), ElementsAre(IdEq("http://first"))); | |
| 347 | |
| 348 json_str = base::StringPrintf( | |
| 349 json_str_format, "http://second", | |
| 350 NTPSnippet::TimeToJsonString(GetDefaultCreationTime()).c_str(), | |
| 351 NTPSnippet::TimeToJsonString(expiry_time).c_str()); | |
| 352 | |
| 353 LoadFromJSONString(json_str); | |
| 354 | |
| 355 // The snippet loaded last should be at the first position in the list now. | 341 // The snippet loaded last should be at the first position in the list now. |
| 356 EXPECT_THAT(service()->snippets(), | 342 EXPECT_THAT(service()->snippets(), ElementsAre(IdEq(second), IdEq(first))); |
| 357 ElementsAre(IdEq("http://second"), IdEq("http://first"))); | |
| 358 } | 343 } |
| 359 | 344 |
| 360 TEST_F(NTPSnippetsServiceTest, LimitNumSnippets) { | 345 TEST_F(NTPSnippetsServiceTest, LimitNumSnippets) { |
| 361 int max_snippet_count = NTPSnippetsService::GetMaxSnippetCountForTesting(); | 346 int max_snippet_count = NTPSnippetsService::GetMaxSnippetCountForTesting(); |
| 362 int snippets_per_load = max_snippet_count / 2 + 1; | 347 int snippets_per_load = max_snippet_count / 2 + 1; |
| 363 | 348 char url_format[] = "http://localhost/%i"; |
| 364 base::Time expiry_time = base::Time::Now() + base::TimeDelta::FromHours(1); | |
| 365 char json_str_format[] = | |
| 366 "{ \"contentInfo\": {" | |
| 367 "\"url\" : \"http://localhost/%i\"," | |
| 368 "\"title\" : \"Title\"," | |
| 369 "\"snippet\" : \"Snippet\"," | |
| 370 "\"thumbnailUrl\" : \"http://localhost/salient_image\"," | |
| 371 "\"creationTimestampSec\" : \"%s\"," | |
| 372 "\"expiryTimestampSec\" : \"%s\"," | |
| 373 "\"sourceCorpusInfo\" : [{\"corpusId\": \"http://first\"," | |
| 374 "\"publisherData\": {" | |
| 375 "\"sourceName\": \"Source 1\"" | |
| 376 "}," | |
| 377 "\"ampUrl\": \"\"}]" | |
| 378 "}}"; | |
| 379 | 349 |
| 380 std::vector<std::string> snippets1; | 350 std::vector<std::string> snippets1; |
| 381 std::vector<std::string> snippets2; | 351 std::vector<std::string> snippets2; |
| 382 for (int i = 0; i < snippets_per_load; i++) { | 352 for (int i = 0; i < snippets_per_load; i++) { |
| 383 snippets1.push_back(base::StringPrintf( | 353 snippets1.push_back(GetSnippetWithUrl(base::StringPrintf(url_format, i))); |
| 384 json_str_format, i, | 354 snippets2.push_back(GetSnippetWithUrl( |
| 385 NTPSnippet::TimeToJsonString(GetDefaultCreationTime()).c_str(), | 355 base::StringPrintf(url_format, snippets_per_load + i))); |
| 386 NTPSnippet::TimeToJsonString(expiry_time).c_str())); | |
| 387 snippets2.push_back(base::StringPrintf( | |
| 388 json_str_format, snippets_per_load + i, | |
| 389 NTPSnippet::TimeToJsonString(GetDefaultCreationTime()).c_str(), | |
| 390 NTPSnippet::TimeToJsonString(expiry_time).c_str())); | |
| 391 } | 356 } |
| 392 | 357 |
| 393 LoadFromJSONString( | 358 LoadFromJSONString(GetTestJson(snippets1)); |
| 394 "{ \"recos\": [ " + base::JoinString(snippets1, ", ") + "]}"); | |
| 395 ASSERT_THAT(service()->snippets(), SizeIs(snippets1.size())); | 359 ASSERT_THAT(service()->snippets(), SizeIs(snippets1.size())); |
| 396 | 360 |
| 397 LoadFromJSONString( | 361 LoadFromJSONString(GetTestJson(snippets2)); |
| 398 "{ \"recos\": [ " + base::JoinString(snippets2, ", ") + "]}"); | |
| 399 EXPECT_THAT(service()->snippets(), SizeIs(max_snippet_count)); | 362 EXPECT_THAT(service()->snippets(), SizeIs(max_snippet_count)); |
| 400 } | 363 } |
| 401 | 364 |
| 402 TEST_F(NTPSnippetsServiceTest, LoadInvalidJson) { | 365 TEST_F(NTPSnippetsServiceTest, LoadInvalidJson) { |
| 403 LoadFromJSONString(GetInvalidJson()); | 366 LoadFromJSONString(GetTestJson({GetInvalidSnippet()})); |
| 404 EXPECT_THAT(service()->last_status(), StartsWith("Received invalid JSON")); | 367 EXPECT_THAT(service()->last_status(), StartsWith("Received invalid JSON")); |
| 405 EXPECT_THAT(service()->snippets(), IsEmpty()); | 368 EXPECT_THAT(service()->snippets(), IsEmpty()); |
| 406 } | 369 } |
| 407 | 370 |
| 408 TEST_F(NTPSnippetsServiceTest, LoadInvalidJsonWithExistingSnippets) { | 371 TEST_F(NTPSnippetsServiceTest, LoadInvalidJsonWithExistingSnippets) { |
| 409 LoadFromJSONString(GetTestJson()); | 372 LoadFromJSONString(GetTestJson({GetSnippet()})); |
| 410 ASSERT_THAT(service()->snippets(), SizeIs(1)); | 373 ASSERT_THAT(service()->snippets(), SizeIs(1)); |
| 411 ASSERT_EQ("OK", service()->last_status()); | 374 ASSERT_EQ("OK", service()->last_status()); |
| 412 | 375 |
| 413 LoadFromJSONString(GetInvalidJson()); | 376 LoadFromJSONString(GetTestJson({GetInvalidSnippet()})); |
| 414 EXPECT_THAT(service()->last_status(), StartsWith("Received invalid JSON")); | 377 EXPECT_THAT(service()->last_status(), StartsWith("Received invalid JSON")); |
| 415 // This should not have changed the existing snippets. | 378 // This should not have changed the existing snippets. |
| 416 EXPECT_THAT(service()->snippets(), SizeIs(1)); | 379 EXPECT_THAT(service()->snippets(), SizeIs(1)); |
| 417 } | 380 } |
| 418 | 381 |
| 419 TEST_F(NTPSnippetsServiceTest, LoadIncompleteJson) { | 382 TEST_F(NTPSnippetsServiceTest, LoadIncompleteJson) { |
| 420 LoadFromJSONString(GetIncompleteJson()); | 383 LoadFromJSONString(GetTestJson({GetIncompleteSnippet()})); |
| 421 EXPECT_EQ("Invalid / empty list.", service()->last_status()); | 384 EXPECT_EQ("Invalid / empty list.", service()->last_status()); |
| 422 EXPECT_THAT(service()->snippets(), IsEmpty()); | 385 EXPECT_THAT(service()->snippets(), IsEmpty()); |
| 423 } | 386 } |
| 424 | 387 |
| 425 TEST_F(NTPSnippetsServiceTest, LoadIncompleteJsonWithExistingSnippets) { | 388 TEST_F(NTPSnippetsServiceTest, LoadIncompleteJsonWithExistingSnippets) { |
| 426 LoadFromJSONString(GetTestJson()); | 389 LoadFromJSONString(GetTestJson({GetSnippet()})); |
| 427 ASSERT_THAT(service()->snippets(), SizeIs(1)); | 390 ASSERT_THAT(service()->snippets(), SizeIs(1)); |
| 428 | 391 |
| 429 LoadFromJSONString(GetIncompleteJson()); | 392 LoadFromJSONString(GetTestJson({GetIncompleteSnippet()})); |
| 430 EXPECT_EQ("Invalid / empty list.", service()->last_status()); | 393 EXPECT_EQ("Invalid / empty list.", service()->last_status()); |
| 431 // This should not have changed the existing snippets. | 394 // This should not have changed the existing snippets. |
| 432 EXPECT_THAT(service()->snippets(), SizeIs(1)); | 395 EXPECT_THAT(service()->snippets(), SizeIs(1)); |
| 433 } | 396 } |
| 434 | 397 |
| 435 TEST_F(NTPSnippetsServiceTest, Discard) { | 398 TEST_F(NTPSnippetsServiceTest, Discard) { |
| 436 std::vector<std::string> source_urls, publishers, amp_urls; | 399 std::vector<std::string> source_urls, publishers, amp_urls; |
| 437 source_urls.push_back(std::string("http://site.com")); | 400 source_urls.push_back(std::string("http://site.com")); |
| 438 publishers.push_back(std::string("Source 1")); | 401 publishers.push_back(std::string("Source 1")); |
| 439 amp_urls.push_back(std::string()); | 402 amp_urls.push_back(std::string()); |
| 440 std::string json_str( | 403 std::string json_str( |
| 441 GetTestJsonWithSources(source_urls, publishers, amp_urls)); | 404 GetTestJson({GetSnippetWithSources(source_urls, publishers, amp_urls)})); |
| 442 | 405 |
| 443 LoadFromJSONString(json_str); | 406 LoadFromJSONString(json_str); |
| 444 | 407 |
| 445 ASSERT_THAT(service()->snippets(), SizeIs(1)); | 408 ASSERT_THAT(service()->snippets(), SizeIs(1)); |
| 446 | 409 |
| 447 // Discarding a non-existent snippet shouldn't do anything. | 410 // Discarding a non-existent snippet shouldn't do anything. |
| 448 EXPECT_FALSE(service()->DiscardSnippet("http://othersite.com")); | 411 EXPECT_FALSE(service()->DiscardSnippet("http://othersite.com")); |
| 449 EXPECT_THAT(service()->snippets(), SizeIs(1)); | 412 EXPECT_THAT(service()->snippets(), SizeIs(1)); |
| 450 | 413 |
| 451 // Discard the snippet. | 414 // Discard the snippet. |
| 452 EXPECT_TRUE(service()->DiscardSnippet("http://localhost/foobar")); | 415 EXPECT_TRUE(service()->DiscardSnippet(kSnippetUrl)); |
| 453 EXPECT_THAT(service()->snippets(), IsEmpty()); | 416 EXPECT_THAT(service()->snippets(), IsEmpty()); |
| 454 | 417 |
| 455 // Make sure that fetching the same snippet again does not re-add it. | 418 // Make sure that fetching the same snippet again does not re-add it. |
| 456 LoadFromJSONString(json_str); | 419 LoadFromJSONString(json_str); |
| 457 EXPECT_THAT(service()->snippets(), IsEmpty()); | 420 EXPECT_THAT(service()->snippets(), IsEmpty()); |
| 458 | 421 |
| 459 // The snippet should stay discarded even after re-creating the service. | 422 // The snippet should stay discarded even after re-creating the service. |
| 460 EXPECT_CALL(mock_scheduler(), Schedule(_, _, _, _)).Times(1); | 423 EXPECT_CALL(mock_scheduler(), Schedule(_, _, _, _)).Times(1); |
| 461 CreateSnippetsService(/*enabled=*/true); | 424 CreateSnippetsService(/*enabled=*/true); |
| 462 LoadFromJSONString(json_str); | 425 LoadFromJSONString(json_str); |
| 463 EXPECT_THAT(service()->snippets(), IsEmpty()); | 426 EXPECT_THAT(service()->snippets(), IsEmpty()); |
| 464 | 427 |
| 465 // The snippet can be added again after clearing discarded snippets. | 428 // The snippet can be added again after clearing discarded snippets. |
| 466 service()->ClearDiscardedSnippets(); | 429 service()->ClearDiscardedSnippets(); |
| 467 EXPECT_THAT(service()->snippets(), IsEmpty()); | 430 EXPECT_THAT(service()->snippets(), IsEmpty()); |
| 468 LoadFromJSONString(json_str); | 431 LoadFromJSONString(json_str); |
| 469 EXPECT_THAT(service()->snippets(), SizeIs(1)); | 432 EXPECT_THAT(service()->snippets(), SizeIs(1)); |
| 470 } | 433 } |
| 471 | 434 |
| 472 TEST_F(NTPSnippetsServiceTest, GetDiscarded) { | 435 TEST_F(NTPSnippetsServiceTest, GetDiscarded) { |
| 473 LoadFromJSONString(GetTestJson()); | 436 LoadFromJSONString(GetTestJson({GetSnippet()})); |
| 474 | 437 |
| 475 // For the test, we need the snippet to get discarded. | 438 // For the test, we need the snippet to get discarded. |
| 476 ASSERT_TRUE(service()->DiscardSnippet("http://localhost/foobar")); | 439 ASSERT_TRUE(service()->DiscardSnippet(kSnippetUrl)); |
| 477 const NTPSnippetsService::NTPSnippetStorage& snippets = | 440 const NTPSnippetsService::NTPSnippetStorage& snippets = |
| 478 service()->discarded_snippets(); | 441 service()->discarded_snippets(); |
| 479 EXPECT_EQ(1u, snippets.size()); | 442 EXPECT_EQ(1u, snippets.size()); |
| 480 for (auto& snippet : snippets) { | 443 for (auto& snippet : snippets) { |
| 481 EXPECT_EQ("http://localhost/foobar", snippet->id()); | 444 EXPECT_EQ(kSnippetUrl, snippet->id()); |
| 482 } | 445 } |
| 483 | 446 |
| 484 // There should be no discarded snippet after clearing the list. | 447 // There should be no discarded snippet after clearing the list. |
| 485 service()->ClearDiscardedSnippets(); | 448 service()->ClearDiscardedSnippets(); |
| 486 EXPECT_EQ(0u, service()->discarded_snippets().size()); | 449 EXPECT_EQ(0u, service()->discarded_snippets().size()); |
| 487 } | 450 } |
| 488 | 451 |
| 489 TEST_F(NTPSnippetsServiceTest, CreationTimestampParseFail) { | 452 TEST_F(NTPSnippetsServiceTest, CreationTimestampParseFail) { |
| 490 std::string json_str(GetTestJson("aaa1448459205")); | 453 std::string json_str(GetTestJson({GetSnippetWithTimes( |
| 454 "aaa1448459205", | |
| 455 NTPSnippet::TimeToJsonString(GetDefaultExpirationTime()))})); | |
| 491 | 456 |
| 492 LoadFromJSONString(json_str); | 457 LoadFromJSONString(json_str); |
| 493 ASSERT_THAT(service()->snippets(), SizeIs(1)); | 458 ASSERT_THAT(service()->snippets(), SizeIs(1)); |
| 494 const NTPSnippet& snippet = *service()->snippets().front(); | 459 const NTPSnippet& snippet = *service()->snippets().front(); |
| 495 EXPECT_EQ(snippet.id(), "http://localhost/foobar"); | 460 EXPECT_EQ(snippet.id(), kSnippetUrl); |
| 496 EXPECT_EQ(snippet.title(), "Title"); | 461 EXPECT_EQ(snippet.title(), kSnippetTitle); |
| 497 EXPECT_EQ(snippet.snippet(), "Snippet"); | 462 EXPECT_EQ(snippet.snippet(), kSnippetText); |
| 498 EXPECT_EQ(base::Time::UnixEpoch(), snippet.publish_date()); | 463 EXPECT_EQ(base::Time::UnixEpoch(), snippet.publish_date()); |
| 499 } | 464 } |
| 500 | 465 |
| 501 TEST_F(NTPSnippetsServiceTest, RemoveExpiredContent) { | 466 TEST_F(NTPSnippetsServiceTest, RemoveExpiredContent) { |
| 502 std::string json_str(GetTestExpiredJson()); | 467 std::string json_str(GetTestJson({GetExpiredSnippet()})); |
| 503 | 468 |
| 504 LoadFromJSONString(json_str); | 469 LoadFromJSONString(json_str); |
| 505 EXPECT_THAT(service()->snippets(), IsEmpty()); | 470 EXPECT_THAT(service()->snippets(), IsEmpty()); |
| 506 } | 471 } |
| 507 | 472 |
| 508 TEST_F(NTPSnippetsServiceTest, TestSingleSource) { | 473 TEST_F(NTPSnippetsServiceTest, TestSingleSource) { |
| 509 std::vector<std::string> source_urls, publishers, amp_urls; | 474 std::vector<std::string> source_urls, publishers, amp_urls; |
| 510 source_urls.push_back(std::string("http://source1.com")); | 475 source_urls.push_back(std::string("http://source1.com")); |
| 511 publishers.push_back(std::string("Source 1")); | 476 publishers.push_back(std::string("Source 1")); |
| 512 amp_urls.push_back(std::string("http://source1.amp.com")); | 477 amp_urls.push_back(std::string("http://source1.amp.com")); |
| 513 std::string json_str( | 478 std::string json_str( |
| 514 GetTestJsonWithSources(source_urls, publishers, amp_urls)); | 479 GetTestJson({GetSnippetWithSources(source_urls, publishers, amp_urls)})); |
| 515 | 480 |
| 516 LoadFromJSONString(json_str); | 481 LoadFromJSONString(json_str); |
| 517 ASSERT_THAT(service()->snippets(), SizeIs(1)); | 482 ASSERT_THAT(service()->snippets(), SizeIs(1)); |
| 518 const NTPSnippet& snippet = *service()->snippets().front(); | 483 const NTPSnippet& snippet = *service()->snippets().front(); |
| 519 EXPECT_EQ(snippet.sources().size(), 1u); | 484 EXPECT_EQ(snippet.sources().size(), 1u); |
| 520 EXPECT_EQ(snippet.id(), "http://localhost/foobar"); | 485 EXPECT_EQ(snippet.id(), kSnippetUrl); |
| 521 EXPECT_EQ(snippet.best_source().url, GURL("http://source1.com")); | 486 EXPECT_EQ(snippet.best_source().url, GURL("http://source1.com")); |
| 522 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 1")); | 487 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 1")); |
| 523 EXPECT_EQ(snippet.best_source().amp_url, GURL("http://source1.amp.com")); | 488 EXPECT_EQ(snippet.best_source().amp_url, GURL("http://source1.amp.com")); |
| 524 } | 489 } |
| 525 | 490 |
| 526 TEST_F(NTPSnippetsServiceTest, TestSingleSourceWithMalformedUrl) { | 491 TEST_F(NTPSnippetsServiceTest, TestSingleSourceWithMalformedUrl) { |
| 527 std::vector<std::string> source_urls, publishers, amp_urls; | 492 std::vector<std::string> source_urls, publishers, amp_urls; |
| 528 source_urls.push_back(std::string("aaaa")); | 493 source_urls.push_back(std::string("aaaa")); |
| 529 publishers.push_back(std::string("Source 1")); | 494 publishers.push_back(std::string("Source 1")); |
| 530 amp_urls.push_back(std::string("http://source1.amp.com")); | 495 amp_urls.push_back(std::string("http://source1.amp.com")); |
| 531 std::string json_str( | 496 std::string json_str( |
| 532 GetTestJsonWithSources(source_urls, publishers, amp_urls)); | 497 GetTestJson({GetSnippetWithSources(source_urls, publishers, amp_urls)})); |
| 533 | 498 |
| 534 LoadFromJSONString(json_str); | 499 LoadFromJSONString(json_str); |
| 535 EXPECT_THAT(service()->snippets(), IsEmpty()); | 500 EXPECT_THAT(service()->snippets(), IsEmpty()); |
| 536 } | 501 } |
| 537 | 502 |
| 538 TEST_F(NTPSnippetsServiceTest, TestSingleSourceWithMissingData) { | 503 TEST_F(NTPSnippetsServiceTest, TestSingleSourceWithMissingData) { |
| 539 std::vector<std::string> source_urls, publishers, amp_urls; | 504 std::vector<std::string> source_urls, publishers, amp_urls; |
| 540 source_urls.push_back(std::string("http://source1.com")); | 505 source_urls.push_back(std::string("http://source1.com")); |
| 541 publishers.push_back(std::string()); | 506 publishers.push_back(std::string()); |
| 542 amp_urls.push_back(std::string()); | 507 amp_urls.push_back(std::string()); |
| 543 std::string json_str( | 508 std::string json_str( |
| 544 GetTestJsonWithSources(source_urls, publishers, amp_urls)); | 509 GetTestJson({GetSnippetWithSources(source_urls, publishers, amp_urls)})); |
| 545 | 510 |
| 546 LoadFromJSONString(json_str); | 511 LoadFromJSONString(json_str); |
| 547 EXPECT_THAT(service()->snippets(), IsEmpty()); | 512 EXPECT_THAT(service()->snippets(), IsEmpty()); |
| 548 } | 513 } |
| 549 | 514 |
| 550 TEST_F(NTPSnippetsServiceTest, TestMultipleSources) { | 515 TEST_F(NTPSnippetsServiceTest, TestMultipleSources) { |
| 551 std::vector<std::string> source_urls, publishers, amp_urls; | 516 std::vector<std::string> source_urls, publishers, amp_urls; |
| 552 source_urls.push_back(std::string("http://source1.com")); | 517 source_urls.push_back(std::string("http://source1.com")); |
| 553 source_urls.push_back(std::string("http://source2.com")); | 518 source_urls.push_back(std::string("http://source2.com")); |
| 554 publishers.push_back(std::string("Source 1")); | 519 publishers.push_back(std::string("Source 1")); |
| 555 publishers.push_back(std::string("Source 2")); | 520 publishers.push_back(std::string("Source 2")); |
| 556 amp_urls.push_back(std::string("http://source1.amp.com")); | 521 amp_urls.push_back(std::string("http://source1.amp.com")); |
| 557 amp_urls.push_back(std::string("http://source2.amp.com")); | 522 amp_urls.push_back(std::string("http://source2.amp.com")); |
| 558 std::string json_str( | 523 std::string json_str( |
| 559 GetTestJsonWithSources(source_urls, publishers, amp_urls)); | 524 GetTestJson({GetSnippetWithSources(source_urls, publishers, amp_urls)})); |
| 560 | 525 |
| 561 LoadFromJSONString(json_str); | 526 LoadFromJSONString(json_str); |
| 562 ASSERT_THAT(service()->snippets(), SizeIs(1)); | 527 ASSERT_THAT(service()->snippets(), SizeIs(1)); |
| 563 const NTPSnippet& snippet = *service()->snippets().front(); | 528 const NTPSnippet& snippet = *service()->snippets().front(); |
| 564 // Expect the first source to be chosen | 529 // Expect the first source to be chosen |
| 565 EXPECT_EQ(snippet.sources().size(), 2u); | 530 EXPECT_EQ(snippet.sources().size(), 2u); |
| 566 EXPECT_EQ(snippet.id(), "http://localhost/foobar"); | 531 EXPECT_EQ(snippet.id(), kSnippetUrl); |
| 567 EXPECT_EQ(snippet.best_source().url, GURL("http://source1.com")); | 532 EXPECT_EQ(snippet.best_source().url, GURL("http://source1.com")); |
| 568 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 1")); | 533 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 1")); |
| 569 EXPECT_EQ(snippet.best_source().amp_url, GURL("http://source1.amp.com")); | 534 EXPECT_EQ(snippet.best_source().amp_url, GURL("http://source1.amp.com")); |
| 570 } | 535 } |
| 571 | 536 |
| 572 TEST_F(NTPSnippetsServiceTest, TestMultipleIncompleteSources) { | 537 TEST_F(NTPSnippetsServiceTest, TestMultipleIncompleteSources) { |
| 573 // Set Source 2 to have no AMP url, and Source 1 to have no publisher name | 538 // Set Source 2 to have no AMP url, and Source 1 to have no publisher name |
| 574 // Source 2 should win since we favor publisher name over amp url | 539 // Source 2 should win since we favor publisher name over amp url |
| 575 std::vector<std::string> source_urls, publishers, amp_urls; | 540 std::vector<std::string> source_urls, publishers, amp_urls; |
| 576 source_urls.push_back(std::string("http://source1.com")); | 541 source_urls.push_back(std::string("http://source1.com")); |
| 577 source_urls.push_back(std::string("http://source2.com")); | 542 source_urls.push_back(std::string("http://source2.com")); |
| 578 publishers.push_back(std::string()); | 543 publishers.push_back(std::string()); |
| 579 publishers.push_back(std::string("Source 2")); | 544 publishers.push_back(std::string("Source 2")); |
| 580 amp_urls.push_back(std::string("http://source1.amp.com")); | 545 amp_urls.push_back(std::string("http://source1.amp.com")); |
| 581 amp_urls.push_back(std::string()); | 546 amp_urls.push_back(std::string()); |
| 582 std::string json_str( | 547 std::string json_str( |
| 583 GetTestJsonWithSources(source_urls, publishers, amp_urls)); | 548 GetTestJson({GetSnippetWithSources(source_urls, publishers, amp_urls)})); |
| 584 | 549 |
| 585 LoadFromJSONString(json_str); | 550 LoadFromJSONString(json_str); |
| 586 ASSERT_THAT(service()->snippets(), SizeIs(1)); | 551 ASSERT_THAT(service()->snippets(), SizeIs(1)); |
| 587 { | 552 { |
| 588 const NTPSnippet& snippet = *service()->snippets().front(); | 553 const NTPSnippet& snippet = *service()->snippets().front(); |
| 589 EXPECT_EQ(snippet.sources().size(), 2u); | 554 EXPECT_EQ(snippet.sources().size(), 2u); |
| 590 EXPECT_EQ(snippet.id(), "http://localhost/foobar"); | 555 EXPECT_EQ(snippet.id(), kSnippetUrl); |
| 591 EXPECT_EQ(snippet.best_source().url, GURL("http://source2.com")); | 556 EXPECT_EQ(snippet.best_source().url, GURL("http://source2.com")); |
| 592 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 2")); | 557 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 2")); |
| 593 EXPECT_EQ(snippet.best_source().amp_url, GURL()); | 558 EXPECT_EQ(snippet.best_source().amp_url, GURL()); |
| 594 } | 559 } |
| 595 | 560 |
| 596 service()->ClearSnippets(); | 561 service()->ClearSnippets(); |
| 597 // Set Source 1 to have no AMP url, and Source 2 to have no publisher name | 562 // Set Source 1 to have no AMP url, and Source 2 to have no publisher name |
| 598 // Source 1 should win in this case since we prefer publisher name to AMP url | 563 // Source 1 should win in this case since we prefer publisher name to AMP url |
| 599 source_urls.clear(); | 564 source_urls.clear(); |
| 600 source_urls.push_back(std::string("http://source1.com")); | 565 source_urls.push_back(std::string("http://source1.com")); |
| 601 source_urls.push_back(std::string("http://source2.com")); | 566 source_urls.push_back(std::string("http://source2.com")); |
| 602 publishers.clear(); | 567 publishers.clear(); |
| 603 publishers.push_back(std::string("Source 1")); | 568 publishers.push_back(std::string("Source 1")); |
| 604 publishers.push_back(std::string()); | 569 publishers.push_back(std::string()); |
| 605 amp_urls.clear(); | 570 amp_urls.clear(); |
| 606 amp_urls.push_back(std::string()); | 571 amp_urls.push_back(std::string()); |
| 607 amp_urls.push_back(std::string("http://source2.amp.com")); | 572 amp_urls.push_back(std::string("http://source2.amp.com")); |
| 608 json_str = GetTestJsonWithSources(source_urls, publishers, amp_urls); | 573 json_str = |
| 574 GetTestJson({GetSnippetWithSources(source_urls, publishers, amp_urls)}); | |
| 609 | 575 |
| 610 LoadFromJSONString(json_str); | 576 LoadFromJSONString(json_str); |
| 611 ASSERT_THAT(service()->snippets(), SizeIs(1)); | 577 ASSERT_THAT(service()->snippets(), SizeIs(1)); |
| 612 { | 578 { |
| 613 const NTPSnippet& snippet = *service()->snippets().front(); | 579 const NTPSnippet& snippet = *service()->snippets().front(); |
| 614 EXPECT_EQ(snippet.sources().size(), 2u); | 580 EXPECT_EQ(snippet.sources().size(), 2u); |
| 615 EXPECT_EQ(snippet.id(), "http://localhost/foobar"); | 581 EXPECT_EQ(snippet.id(), kSnippetUrl); |
| 616 EXPECT_EQ(snippet.best_source().url, GURL("http://source1.com")); | 582 EXPECT_EQ(snippet.best_source().url, GURL("http://source1.com")); |
| 617 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 1")); | 583 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 1")); |
| 618 EXPECT_EQ(snippet.best_source().amp_url, GURL()); | 584 EXPECT_EQ(snippet.best_source().amp_url, GURL()); |
| 619 } | 585 } |
| 620 | 586 |
| 621 service()->ClearSnippets(); | 587 service()->ClearSnippets(); |
| 622 // Set source 1 to have no AMP url and no source, and source 2 to only have | 588 // Set source 1 to have no AMP url and no source, and source 2 to only have |
| 623 // amp url. There should be no snippets since we only add sources we consider | 589 // amp url. There should be no snippets since we only add sources we consider |
| 624 // complete | 590 // complete |
| 625 source_urls.clear(); | 591 source_urls.clear(); |
| 626 source_urls.push_back(std::string("http://source1.com")); | 592 source_urls.push_back(std::string("http://source1.com")); |
| 627 source_urls.push_back(std::string("http://source2.com")); | 593 source_urls.push_back(std::string("http://source2.com")); |
| 628 publishers.clear(); | 594 publishers.clear(); |
| 629 publishers.push_back(std::string()); | 595 publishers.push_back(std::string()); |
| 630 publishers.push_back(std::string()); | 596 publishers.push_back(std::string()); |
| 631 amp_urls.clear(); | 597 amp_urls.clear(); |
| 632 amp_urls.push_back(std::string()); | 598 amp_urls.push_back(std::string()); |
| 633 amp_urls.push_back(std::string("http://source2.amp.com")); | 599 amp_urls.push_back(std::string("http://source2.amp.com")); |
| 634 json_str = GetTestJsonWithSources(source_urls, publishers, amp_urls); | 600 json_str = |
| 601 GetTestJson({GetSnippetWithSources(source_urls, publishers, amp_urls)}); | |
| 635 | 602 |
| 636 LoadFromJSONString(json_str); | 603 LoadFromJSONString(json_str); |
| 637 EXPECT_THAT(service()->snippets(), IsEmpty()); | 604 EXPECT_THAT(service()->snippets(), IsEmpty()); |
| 638 } | 605 } |
| 639 | 606 |
| 640 TEST_F(NTPSnippetsServiceTest, TestMultipleCompleteSources) { | 607 TEST_F(NTPSnippetsServiceTest, TestMultipleCompleteSources) { |
| 641 // Test 2 complete sources, we should choose the first complete source | 608 // Test 2 complete sources, we should choose the first complete source |
| 642 std::vector<std::string> source_urls, publishers, amp_urls; | 609 std::vector<std::string> source_urls, publishers, amp_urls; |
| 643 source_urls.push_back(std::string("http://source1.com")); | 610 source_urls.push_back(std::string("http://source1.com")); |
| 644 source_urls.push_back(std::string("http://source2.com")); | 611 source_urls.push_back(std::string("http://source2.com")); |
| 645 source_urls.push_back(std::string("http://source3.com")); | 612 source_urls.push_back(std::string("http://source3.com")); |
| 646 publishers.push_back(std::string("Source 1")); | 613 publishers.push_back(std::string("Source 1")); |
| 647 publishers.push_back(std::string()); | 614 publishers.push_back(std::string()); |
| 648 publishers.push_back(std::string("Source 3")); | 615 publishers.push_back(std::string("Source 3")); |
| 649 amp_urls.push_back(std::string("http://source1.amp.com")); | 616 amp_urls.push_back(std::string("http://source1.amp.com")); |
| 650 amp_urls.push_back(std::string("http://source2.amp.com")); | 617 amp_urls.push_back(std::string("http://source2.amp.com")); |
| 651 amp_urls.push_back(std::string("http://source3.amp.com")); | 618 amp_urls.push_back(std::string("http://source3.amp.com")); |
| 652 std::string json_str( | 619 std::string json_str( |
| 653 GetTestJsonWithSources(source_urls, publishers, amp_urls)); | 620 GetTestJson({GetSnippetWithSources(source_urls, publishers, amp_urls)})); |
| 654 | 621 |
| 655 LoadFromJSONString(json_str); | 622 LoadFromJSONString(json_str); |
| 656 ASSERT_THAT(service()->snippets(), SizeIs(1)); | 623 ASSERT_THAT(service()->snippets(), SizeIs(1)); |
| 657 { | 624 { |
| 658 const NTPSnippet& snippet = *service()->snippets().front(); | 625 const NTPSnippet& snippet = *service()->snippets().front(); |
| 659 EXPECT_EQ(snippet.sources().size(), 3u); | 626 EXPECT_EQ(snippet.sources().size(), 3u); |
| 660 EXPECT_EQ(snippet.id(), "http://localhost/foobar"); | 627 EXPECT_EQ(snippet.id(), kSnippetUrl); |
| 661 EXPECT_EQ(snippet.best_source().url, GURL("http://source1.com")); | 628 EXPECT_EQ(snippet.best_source().url, GURL("http://source1.com")); |
| 662 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 1")); | 629 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 1")); |
| 663 EXPECT_EQ(snippet.best_source().amp_url, GURL("http://source1.amp.com")); | 630 EXPECT_EQ(snippet.best_source().amp_url, GURL("http://source1.amp.com")); |
| 664 } | 631 } |
| 665 | 632 |
| 666 // Test 2 complete sources, we should choose the first complete source | 633 // Test 2 complete sources, we should choose the first complete source |
| 667 service()->ClearSnippets(); | 634 service()->ClearSnippets(); |
| 668 source_urls.clear(); | 635 source_urls.clear(); |
| 669 source_urls.push_back(std::string("http://source1.com")); | 636 source_urls.push_back(std::string("http://source1.com")); |
| 670 source_urls.push_back(std::string("http://source2.com")); | 637 source_urls.push_back(std::string("http://source2.com")); |
| 671 source_urls.push_back(std::string("http://source3.com")); | 638 source_urls.push_back(std::string("http://source3.com")); |
| 672 publishers.clear(); | 639 publishers.clear(); |
| 673 publishers.push_back(std::string()); | 640 publishers.push_back(std::string()); |
| 674 publishers.push_back(std::string("Source 2")); | 641 publishers.push_back(std::string("Source 2")); |
| 675 publishers.push_back(std::string("Source 3")); | 642 publishers.push_back(std::string("Source 3")); |
| 676 amp_urls.clear(); | 643 amp_urls.clear(); |
| 677 amp_urls.push_back(std::string("http://source1.amp.com")); | 644 amp_urls.push_back(std::string("http://source1.amp.com")); |
| 678 amp_urls.push_back(std::string("http://source2.amp.com")); | 645 amp_urls.push_back(std::string("http://source2.amp.com")); |
| 679 amp_urls.push_back(std::string("http://source3.amp.com")); | 646 amp_urls.push_back(std::string("http://source3.amp.com")); |
| 680 json_str = GetTestJsonWithSources(source_urls, publishers, amp_urls); | 647 json_str = |
| 648 GetTestJson({GetSnippetWithSources(source_urls, publishers, amp_urls)}); | |
| 681 | 649 |
| 682 LoadFromJSONString(json_str); | 650 LoadFromJSONString(json_str); |
| 683 ASSERT_THAT(service()->snippets(), SizeIs(1)); | 651 ASSERT_THAT(service()->snippets(), SizeIs(1)); |
| 684 { | 652 { |
| 685 const NTPSnippet& snippet = *service()->snippets().front(); | 653 const NTPSnippet& snippet = *service()->snippets().front(); |
| 686 EXPECT_EQ(snippet.sources().size(), 3u); | 654 EXPECT_EQ(snippet.sources().size(), 3u); |
| 687 EXPECT_EQ(snippet.id(), "http://localhost/foobar"); | 655 EXPECT_EQ(snippet.id(), kSnippetUrl); |
| 688 EXPECT_EQ(snippet.best_source().url, GURL("http://source2.com")); | 656 EXPECT_EQ(snippet.best_source().url, GURL("http://source2.com")); |
| 689 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 2")); | 657 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 2")); |
| 690 EXPECT_EQ(snippet.best_source().amp_url, GURL("http://source2.amp.com")); | 658 EXPECT_EQ(snippet.best_source().amp_url, GURL("http://source2.amp.com")); |
| 691 } | 659 } |
| 692 | 660 |
| 693 // Test 3 complete sources, we should choose the first complete source | 661 // Test 3 complete sources, we should choose the first complete source |
| 694 service()->ClearSnippets(); | 662 service()->ClearSnippets(); |
| 695 source_urls.clear(); | 663 source_urls.clear(); |
| 696 source_urls.push_back(std::string("http://source1.com")); | 664 source_urls.push_back(std::string("http://source1.com")); |
| 697 source_urls.push_back(std::string("http://source2.com")); | 665 source_urls.push_back(std::string("http://source2.com")); |
| 698 source_urls.push_back(std::string("http://source3.com")); | 666 source_urls.push_back(std::string("http://source3.com")); |
| 699 publishers.clear(); | 667 publishers.clear(); |
| 700 publishers.push_back(std::string("Source 1")); | 668 publishers.push_back(std::string("Source 1")); |
| 701 publishers.push_back(std::string("Source 2")); | 669 publishers.push_back(std::string("Source 2")); |
| 702 publishers.push_back(std::string("Source 3")); | 670 publishers.push_back(std::string("Source 3")); |
| 703 amp_urls.clear(); | 671 amp_urls.clear(); |
| 704 amp_urls.push_back(std::string()); | 672 amp_urls.push_back(std::string()); |
| 705 amp_urls.push_back(std::string("http://source2.amp.com")); | 673 amp_urls.push_back(std::string("http://source2.amp.com")); |
| 706 amp_urls.push_back(std::string("http://source3.amp.com")); | 674 amp_urls.push_back(std::string("http://source3.amp.com")); |
| 707 json_str = GetTestJsonWithSources(source_urls, publishers, amp_urls); | 675 json_str = |
| 676 GetTestJson({GetSnippetWithSources(source_urls, publishers, amp_urls)}); | |
| 708 | 677 |
| 709 LoadFromJSONString(json_str); | 678 LoadFromJSONString(json_str); |
| 710 ASSERT_THAT(service()->snippets(), SizeIs(1)); | 679 ASSERT_THAT(service()->snippets(), SizeIs(1)); |
| 711 { | 680 { |
| 712 const NTPSnippet& snippet = *service()->snippets().front(); | 681 const NTPSnippet& snippet = *service()->snippets().front(); |
| 713 EXPECT_EQ(snippet.sources().size(), 3u); | 682 EXPECT_EQ(snippet.sources().size(), 3u); |
| 714 EXPECT_EQ(snippet.id(), "http://localhost/foobar"); | 683 EXPECT_EQ(snippet.id(), kSnippetUrl); |
| 715 EXPECT_EQ(snippet.best_source().url, GURL("http://source2.com")); | 684 EXPECT_EQ(snippet.best_source().url, GURL("http://source2.com")); |
| 716 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 2")); | 685 EXPECT_EQ(snippet.best_source().publisher_name, std::string("Source 2")); |
| 717 EXPECT_EQ(snippet.best_source().amp_url, GURL("http://source2.amp.com")); | 686 EXPECT_EQ(snippet.best_source().amp_url, GURL("http://source2.amp.com")); |
| 718 } | 687 } |
| 719 } | 688 } |
| 720 | 689 |
| 721 TEST_F(NTPSnippetsServiceTest, LogNumArticlesHistogram) { | 690 TEST_F(NTPSnippetsServiceTest, LogNumArticlesHistogram) { |
| 722 base::HistogramTester tester; | 691 base::HistogramTester tester; |
| 723 LoadFromJSONString(GetInvalidJson()); | 692 LoadFromJSONString(GetTestJson({GetInvalidSnippet()})); |
| 693 | |
| 724 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticles"), | 694 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticles"), |
| 725 ElementsAre(base::Bucket(/*min=*/0, /*count=*/1))); | 695 ElementsAre(base::Bucket(/*min=*/0, /*count=*/1))); |
| 726 // Invalid JSON shouldn't contribute to NumArticlesFetched. | 696 // Invalid JSON shouldn't contribute to NumArticlesFetched. |
| 727 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticlesFetched"), | 697 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticlesFetched"), |
| 728 IsEmpty()); | 698 IsEmpty()); |
| 729 // Valid JSON with empty list. | 699 // Valid JSON with empty list. |
| 730 LoadFromJSONString("{ \"recos\": []}"); | 700 LoadFromJSONString(GetTestJson({})); |
| 731 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticles"), | 701 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticles"), |
| 732 ElementsAre(base::Bucket(/*min=*/0, /*count=*/2))); | 702 ElementsAre(base::Bucket(/*min=*/0, /*count=*/2))); |
| 733 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticlesFetched"), | 703 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticlesFetched"), |
| 734 ElementsAre(base::Bucket(/*min=*/0, /*count=*/1))); | 704 ElementsAre(base::Bucket(/*min=*/0, /*count=*/1))); |
| 735 // Snippet list should be populated with size 1. | 705 // Snippet list should be populated with size 1. |
| 736 LoadFromJSONString(GetTestJson()); | 706 LoadFromJSONString(GetTestJson({GetSnippet()})); |
| 737 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticles"), | 707 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticles"), |
| 738 ElementsAre(base::Bucket(/*min=*/0, /*count=*/2), | 708 ElementsAre(base::Bucket(/*min=*/0, /*count=*/2), |
| 739 base::Bucket(/*min=*/1, /*count=*/1))); | 709 base::Bucket(/*min=*/1, /*count=*/1))); |
| 740 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticlesFetched"), | 710 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticlesFetched"), |
| 741 ElementsAre(base::Bucket(/*min=*/0, /*count=*/1), | 711 ElementsAre(base::Bucket(/*min=*/0, /*count=*/1), |
| 742 base::Bucket(/*min=*/1, /*count=*/1))); | 712 base::Bucket(/*min=*/1, /*count=*/1))); |
| 743 // Duplicate snippet shouldn't increase the list size. | 713 // Duplicate snippet shouldn't increase the list size. |
| 744 LoadFromJSONString(GetTestJson()); | 714 LoadFromJSONString(GetTestJson({GetSnippet()})); |
| 745 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticles"), | 715 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticles"), |
| 746 ElementsAre(base::Bucket(/*min=*/0, /*count=*/2), | 716 ElementsAre(base::Bucket(/*min=*/0, /*count=*/2), |
| 747 base::Bucket(/*min=*/1, /*count=*/2))); | 717 base::Bucket(/*min=*/1, /*count=*/2))); |
| 748 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticlesFetched"), | 718 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticlesFetched"), |
| 749 ElementsAre(base::Bucket(/*min=*/0, /*count=*/1), | 719 ElementsAre(base::Bucket(/*min=*/0, /*count=*/1), |
| 750 base::Bucket(/*min=*/1, /*count=*/2))); | 720 base::Bucket(/*min=*/1, /*count=*/2))); |
| 751 EXPECT_THAT( | 721 EXPECT_THAT( |
| 752 tester.GetAllSamples("NewTabPage.Snippets.NumArticlesZeroDueToDiscarded"), | 722 tester.GetAllSamples("NewTabPage.Snippets.NumArticlesZeroDueToDiscarded"), |
| 753 IsEmpty()); | 723 IsEmpty()); |
| 754 // Discarding a snippet should decrease the list size. This will only be | 724 // Discarding a snippet should decrease the list size. This will only be |
| 755 // logged after the next fetch. | 725 // logged after the next fetch. |
| 756 EXPECT_TRUE(service()->DiscardSnippet("http://localhost/foobar")); | 726 EXPECT_TRUE(service()->DiscardSnippet(kSnippetUrl)); |
| 757 LoadFromJSONString(GetTestJson()); | 727 LoadFromJSONString(GetTestJson({GetSnippet()})); |
| 758 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticles"), | 728 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticles"), |
| 759 ElementsAre(base::Bucket(/*min=*/0, /*count=*/3), | 729 ElementsAre(base::Bucket(/*min=*/0, /*count=*/3), |
| 760 base::Bucket(/*min=*/1, /*count=*/2))); | 730 base::Bucket(/*min=*/1, /*count=*/2))); |
| 761 // Discarded snippets shouldn't influence NumArticlesFetched. | 731 // Discarded snippets shouldn't influence NumArticlesFetched. |
| 762 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticlesFetched"), | 732 EXPECT_THAT(tester.GetAllSamples("NewTabPage.Snippets.NumArticlesFetched"), |
| 763 ElementsAre(base::Bucket(/*min=*/0, /*count=*/1), | 733 ElementsAre(base::Bucket(/*min=*/0, /*count=*/1), |
| 764 base::Bucket(/*min=*/1, /*count=*/3))); | 734 base::Bucket(/*min=*/1, /*count=*/3))); |
| 765 EXPECT_THAT( | 735 EXPECT_THAT( |
| 766 tester.GetAllSamples("NewTabPage.Snippets.NumArticlesZeroDueToDiscarded"), | 736 tester.GetAllSamples("NewTabPage.Snippets.NumArticlesZeroDueToDiscarded"), |
| 767 ElementsAre(base::Bucket(/*min=*/1, /*count=*/1))); | 737 ElementsAre(base::Bucket(/*min=*/1, /*count=*/1))); |
| 768 // Recreating the service and loading from prefs shouldn't count as fetched | 738 // Recreating the service and loading from prefs shouldn't count as fetched |
| 769 // articles. | 739 // articles. |
| 770 EXPECT_CALL(mock_scheduler(), Schedule(_, _, _, _)).Times(1); | 740 EXPECT_CALL(mock_scheduler(), Schedule(_, _, _, _)).Times(1); |
| 771 CreateSnippetsService(/*enabled=*/true); | 741 CreateSnippetsService(/*enabled=*/true); |
| 772 tester.ExpectTotalCount("NewTabPage.Snippets.NumArticlesFetched", 4); | 742 tester.ExpectTotalCount("NewTabPage.Snippets.NumArticlesFetched", 4); |
| 773 } | 743 } |
| 774 } // namespace ntp_snippets | 744 } // namespace ntp_snippets |
| OLD | NEW |