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 <vector> | 5 #include <vector> |
| 6 | 6 |
| 7 #include "base/macros.h" | 7 #include "base/macros.h" |
| 8 #include "base/memory/scoped_ptr.h" | |
| 8 #include "base/strings/utf_string_conversions.h" | 9 #include "base/strings/utf_string_conversions.h" |
| 9 #include "chrome/browser/android/most_visited_sites.h" | 10 #include "chrome/browser/android/most_visited_sites.h" |
| 10 #include "testing/gtest/include/gtest/gtest.h" | 11 #include "testing/gtest/include/gtest/gtest.h" |
| 11 | 12 |
| 12 namespace { | 13 namespace { |
| 13 | 14 |
| 14 struct TitleURL { | 15 struct TitleURL { |
| 15 TitleURL(const std::string& title, | 16 TitleURL(const std::string& title, const std::string& url) |
| 16 const std::string& url, | 17 : title(base::UTF8ToUTF16(title)), url(url) {} |
| 17 const std::string& source) | 18 TitleURL(const base::string16& title, const std::string& url) |
| 18 : title(base::UTF8ToUTF16(title)), url(url), source(source) {} | 19 : title(title), url(url) {} |
| 19 | 20 |
| 20 base::string16 title; | 21 base::string16 title; |
| 21 std::string url; | 22 std::string url; |
| 22 std::string source; | 23 |
| 24 bool operator==(const TitleURL& other) const { | |
| 25 return title == other.title && url == other.url; | |
| 26 } | |
| 27 | |
| 28 scoped_ptr<MostVisitedSites::Suggestion> GetSuggestion( | |
| 29 bool is_personal) const { | |
| 30 return make_scoped_ptr(new MostVisitedSites::Suggestion( | |
| 31 title, url, | |
| 32 is_personal ? MostVisitedSites::TOP_SITES : MostVisitedSites::POPULAR)); | |
| 33 } | |
| 23 }; | 34 }; |
| 24 | 35 |
| 25 std::vector<base::string16> GetTitles(const std::vector<TitleURL>& data) { | 36 static const size_t kNumSites = 4; |
| 26 std::vector<base::string16> titles; | |
| 27 for (const TitleURL& item : data) | |
| 28 titles.push_back(item.title); | |
| 29 return titles; | |
| 30 } | |
| 31 | |
| 32 std::vector<std::string> GetURLs(const std::vector<TitleURL>& data) { | |
| 33 std::vector<std::string> urls; | |
| 34 for (const TitleURL& item : data) | |
| 35 urls.push_back(item.url); | |
| 36 return urls; | |
| 37 } | |
| 38 | |
| 39 std::vector<std::string> GetSources(const std::vector<TitleURL>& data) { | |
| 40 std::vector<std::string> sources; | |
| 41 for (const TitleURL& item : data) | |
| 42 sources.push_back(item.source); | |
| 43 return sources; | |
| 44 } | |
| 45 | |
| 46 static const int kNumSites = 4; | |
| 47 | 37 |
| 48 } // namespace | 38 } // namespace |
| 49 | 39 |
| 40 // This a test for MostVisitedSites::MergeSuggestions(...) method, and thus has | |
| 41 // the same scope as the method itself. This includes: | |
| 42 // + Merge popular suggestions with personal suggestions. | |
| 43 // + Order the suggestions correctly based on the previous ordering. | |
| 44 // More importantly things out of the scope of testing presently: | |
| 45 // - Removing blacklisted suggestions. | |
| 46 // - Storing the current suggestion ordering. | |
| 47 // - Retrieving the previous ordering. | |
| 48 // - Correct Host extraction from the URL. | |
| 49 // - Ensuring personal suggestions are not duplicated in popular suggestions. | |
| 50 class MostVisitedSitesTest : public testing::Test { | 50 class MostVisitedSitesTest : public testing::Test { |
| 51 protected: | 51 protected: |
| 52 void Check(const std::vector<TitleURL>& popular, | 52 void Check(const std::vector<TitleURL>& popular_sites, |
| 53 const std::vector<TitleURL>& personal, | 53 const std::vector<TitleURL>& personal_sites, |
| 54 const std::vector<TitleURL>& expected) { | 54 const std::vector<std::string>& old_sites_url, |
| 55 std::vector<base::string16> titles(GetTitles(personal)); | 55 const std::vector<bool>& old_sites_is_personal, |
| 56 std::vector<std::string> urls(GetURLs(personal)); | 56 const std::vector<bool>& expected_sites_is_personal, |
| 57 std::vector<std::string> sources(GetSources(personal)); | 57 const std::vector<TitleURL>& expected_sites) { |
| 58 | 58 ScopedVector<MostVisitedSites::Suggestion> personal_suggestions; |
| 59 std::vector<base::string16> popular_titles(GetTitles(popular)); | 59 personal_suggestions.reserve(personal_sites.size()); |
| 60 std::vector<std::string> popular_urls(GetURLs(popular)); | 60 for (const auto& site : personal_sites) |
|
Bernhard Bauer
2015/09/08 15:44:25
Use the actual type instead of auto?
knn
2015/09/09 09:35:38
Done.
| |
| 61 | 61 personal_suggestions.push_back(site.GetSuggestion(true)); |
| 62 MostVisitedSites::AddPopularSitesImpl( | 62 ScopedVector<MostVisitedSites::Suggestion> popular_suggestions; |
| 63 kNumSites, popular_titles, popular_urls, &titles, &urls, &sources); | 63 popular_suggestions.reserve(popular_sites.size()); |
| 64 | 64 for (const auto& site : popular_sites) |
| 65 EXPECT_EQ(GetTitles(expected), titles); | 65 popular_suggestions.push_back(site.GetSuggestion(false)); |
| 66 EXPECT_EQ(GetURLs(expected), urls); | 66 ScopedVector<MostVisitedSites::Suggestion> result_suggestions = |
| 67 EXPECT_EQ(GetSources(expected), sources); | 67 MostVisitedSites::MergeSuggestions(&personal_suggestions, |
| 68 &popular_suggestions, old_sites_url, | |
| 69 old_sites_is_personal); | |
| 70 std::vector<TitleURL> result_sites; | |
| 71 std::vector<bool> result_is_personal; | |
| 72 result_sites.reserve(result_suggestions.size()); | |
| 73 result_is_personal.reserve(result_suggestions.size()); | |
| 74 for (const auto suggestion : result_suggestions) { | |
| 75 result_sites.push_back(TitleURL(suggestion->title, suggestion->url)); | |
| 76 result_is_personal.push_back(suggestion->source != | |
| 77 MostVisitedSites::POPULAR); | |
| 78 } | |
| 79 EXPECT_EQ(result_is_personal, expected_sites_is_personal); | |
| 80 EXPECT_EQ(result_sites, expected_sites); | |
| 68 } | 81 } |
| 69 }; | 82 }; |
| 70 | 83 |
| 71 TEST_F(MostVisitedSitesTest, PopularSitesAppend) { | 84 TEST_F(MostVisitedSitesTest, PersonalSitesDefaultOrder) { |
| 72 TitleURL popular[] = { | 85 TitleURL personal[] = { |
| 73 TitleURL("Site 1", "https://www.site1.com/", "popular"), | 86 TitleURL("Site 1", "https://www.site1.com/"), |
| 74 TitleURL("Site 2", "https://www.site2.com/", "popular"), | 87 TitleURL("Site 2", "https://www.site2.com/"), |
| 75 }; | 88 TitleURL("Site 3", "https://www.site3.com/"), |
| 76 TitleURL personal[] = { | 89 TitleURL("Site 4", "https://www.site4.com/"), |
| 77 TitleURL("Site 3", "https://www.site3.com/", "server8"), | 90 }; |
| 78 TitleURL("Site 4", "https://www.site4.com/", "server8"), | 91 std::vector<TitleURL> personal_sites(personal, |
| 79 }; | 92 personal + arraysize(personal)); |
| 80 // Popular suggestions should keep their positions, with personal suggestions | 93 std::vector<std::string> old_sites_url; |
| 81 // appended at the end. | 94 std::vector<bool> old_sites_source; |
| 82 TitleURL expected[] = { | 95 // Without any previous ordering or popular suggestions, the result after |
| 83 TitleURL("Site 1", "https://www.site1.com/", "popular"), | 96 // merge should be the personal suggestions themselves. |
| 84 TitleURL("Site 2", "https://www.site2.com/", "popular"), | 97 std::vector<bool> expected_sites_source(kNumSites, true /*personal source*/); |
| 85 TitleURL("Site 3", "https://www.site3.com/", "server8"), | 98 Check(std::vector<TitleURL>(), personal_sites, old_sites_url, |
| 86 TitleURL("Site 4", "https://www.site4.com/", "server8"), | 99 old_sites_source, expected_sites_source, personal_sites); |
| 87 }; | 100 } |
| 88 | 101 |
| 102 TEST_F(MostVisitedSitesTest, PersonalSitesDefinedOrder) { | |
| 103 TitleURL personal[] = { | |
| 104 TitleURL("Site 1", "https://www.site1.com/"), | |
| 105 TitleURL("Site 2", "https://www.site2.com/"), | |
| 106 TitleURL("Site 3", "https://www.site3.com/"), | |
| 107 TitleURL("Site 4", "https://www.site4.com/"), | |
| 108 }; | |
| 109 std::string old[] = { | |
| 110 "https://www.site4.com/", "https://www.site2.com/", | |
| 111 }; | |
| 112 std::vector<bool> old_sites_source(arraysize(old), true /*personal source*/); | |
| 113 TitleURL expected[] = { | |
| 114 TitleURL("Site 4", "https://www.site4.com/"), | |
| 115 TitleURL("Site 2", "https://www.site2.com/"), | |
| 116 TitleURL("Site 1", "https://www.site1.com/"), | |
| 117 TitleURL("Site 3", "https://www.site3.com/"), | |
| 118 }; | |
| 119 std::vector<bool> expected_sites_source(kNumSites, true /*personal source*/); | |
| 120 Check(std::vector<TitleURL>(), | |
| 121 std::vector<TitleURL>(personal, personal + arraysize(personal)), | |
| 122 std::vector<std::string>(old, old + arraysize(old)), old_sites_source, | |
| 123 expected_sites_source, | |
| 124 std::vector<TitleURL>(expected, expected + arraysize(expected))); | |
| 125 } | |
| 126 | |
| 127 TEST_F(MostVisitedSitesTest, PopularSitesDefaultOrder) { | |
| 128 TitleURL popular[] = { | |
| 129 TitleURL("Site 1", "https://www.site1.com/"), | |
| 130 TitleURL("Site 2", "https://www.site2.com/"), | |
| 131 TitleURL("Site 3", "https://www.site3.com/"), | |
| 132 TitleURL("Site 4", "https://www.site4.com/"), | |
| 133 }; | |
| 134 std::vector<TitleURL> popular_sites(popular, popular + arraysize(popular)); | |
| 135 std::vector<std::string> old_sites_url; | |
| 136 std::vector<bool> old_sites_source; | |
| 137 // Without any previous ordering or personal suggestions, the result after | |
| 138 // merge should be the popular suggestions themselves. | |
| 139 std::vector<bool> expected_sites_source(kNumSites, false /*popular source*/); | |
| 140 Check(popular_sites, std::vector<TitleURL>(), old_sites_url, old_sites_source, | |
| 141 expected_sites_source, popular_sites); | |
| 142 } | |
| 143 | |
| 144 TEST_F(MostVisitedSitesTest, PopularSitesDefinedOrder) { | |
| 145 TitleURL popular[] = { | |
| 146 TitleURL("Site 1", "https://www.site1.com/"), | |
| 147 TitleURL("Site 2", "https://www.site2.com/"), | |
| 148 TitleURL("Site 3", "https://www.site3.com/"), | |
| 149 TitleURL("Site 4", "https://www.site4.com/"), | |
| 150 }; | |
| 151 std::string old[] = { | |
| 152 "https://www.site4.com/", "https://www.site2.com/", | |
| 153 }; | |
| 154 std::vector<bool> old_sites_source(arraysize(old), false /*popular source*/); | |
| 155 TitleURL expected[] = { | |
| 156 TitleURL("Site 4", "https://www.site4.com/"), | |
| 157 TitleURL("Site 2", "https://www.site2.com/"), | |
| 158 TitleURL("Site 1", "https://www.site1.com/"), | |
| 159 TitleURL("Site 3", "https://www.site3.com/"), | |
| 160 }; | |
| 161 std::vector<bool> expected_sites_source(kNumSites, false /*popular source*/); | |
| 162 Check(std::vector<TitleURL>(popular, popular + arraysize(popular)), | |
| 163 std::vector<TitleURL>(), | |
| 164 std::vector<std::string>(old, old + arraysize(old)), old_sites_source, | |
| 165 expected_sites_source, | |
| 166 std::vector<TitleURL>(expected, expected + arraysize(expected))); | |
| 167 } | |
| 168 | |
| 169 TEST_F(MostVisitedSitesTest, PopularAndPersonalDefaultOrder) { | |
| 170 TitleURL popular[] = { | |
| 171 TitleURL("Site 1", "https://www.site1.com/"), | |
| 172 TitleURL("Site 2", "https://www.site2.com/"), | |
| 173 }; | |
| 174 TitleURL personal[] = { | |
| 175 TitleURL("Site 3", "https://www.site3.com/"), | |
| 176 TitleURL("Site 4", "https://www.site4.com/"), | |
| 177 }; | |
| 178 // Without an explicit ordering, personal suggestions precede popular | |
| 179 // suggestions. | |
| 180 TitleURL expected[] = { | |
| 181 TitleURL("Site 3", "https://www.site3.com/"), | |
| 182 TitleURL("Site 4", "https://www.site4.com/"), | |
| 183 TitleURL("Site 1", "https://www.site1.com/"), | |
| 184 TitleURL("Site 2", "https://www.site2.com/"), | |
| 185 }; | |
| 186 bool expected_source_is_personal[] = {true, true, false, false}; | |
| 89 Check(std::vector<TitleURL>(popular, popular + arraysize(popular)), | 187 Check(std::vector<TitleURL>(popular, popular + arraysize(popular)), |
| 90 std::vector<TitleURL>(personal, personal + arraysize(personal)), | 188 std::vector<TitleURL>(personal, personal + arraysize(personal)), |
| 91 std::vector<TitleURL>(expected, expected + arraysize(expected))); | 189 std::vector<std::string>(), std::vector<bool>(), |
| 92 } | 190 std::vector<bool>(expected_source_is_personal, |
| 93 | 191 expected_source_is_personal + |
| 94 TEST_F(MostVisitedSitesTest, PopularSitesOverflow) { | 192 arraysize(expected_source_is_personal)), |
| 95 TitleURL popular[] = { | 193 std::vector<TitleURL>(expected, expected + arraysize(expected))); |
| 96 TitleURL("Site 1", "https://www.site1.com/", "popular"), | 194 } |
| 97 TitleURL("Site 2", "https://www.site2.com/", "popular"), | 195 |
| 98 TitleURL("Site 3", "https://www.site3.com/", "popular"), | 196 TEST_F(MostVisitedSitesTest, PopularAndPersonalDefinedOrder) { |
| 99 }; | 197 TitleURL popular[] = { |
| 100 TitleURL personal[] = { | 198 TitleURL("Site 1", "https://www.site1.com/"), |
| 101 TitleURL("Site 4", "https://www.site4.com/", "server8"), | 199 TitleURL("Site 2", "https://www.site2.com/"), |
| 102 TitleURL("Site 5", "https://www.site5.com/", "server8"), | 200 }; |
| 103 }; | 201 TitleURL personal[] = { |
| 104 // When there are more total suggestions than slots, the personal suggestions | 202 TitleURL("Site 3", "https://www.site3.com/"), |
| 105 // should win, with the remaining popular suggestions still retaining their | 203 TitleURL("Site 4", "https://www.site4.com/"), |
| 106 // positions. | 204 }; |
| 107 TitleURL expected[] = { | 205 std::string old[] = { |
| 108 TitleURL("Site 1", "https://www.site1.com/", "popular"), | 206 "https://www.site2.com/", "https://www.unknownsite.com/", |
| 109 TitleURL("Site 2", "https://www.site2.com/", "popular"), | 207 "https://www.site4.com/", |
| 110 TitleURL("Site 4", "https://www.site4.com/", "server8"), | 208 }; |
| 111 TitleURL("Site 5", "https://www.site5.com/", "server8"), | 209 std::vector<bool> old_sites_source(arraysize(old), false /*popular source*/); |
| 112 }; | 210 // Keep the order constant for previous suggestions, else personal suggestions |
| 113 | 211 // precede popular suggestions. |
| 212 TitleURL expected[] = { | |
| 213 TitleURL("Site 2", "https://www.site2.com/"), | |
| 214 TitleURL("Site 3", "https://www.site3.com/"), | |
| 215 TitleURL("Site 4", "https://www.site4.com/"), | |
| 216 TitleURL("Site 1", "https://www.site1.com/"), | |
| 217 }; | |
| 218 bool expected_source_is_personal[] = {false, true, true, false}; | |
| 114 Check(std::vector<TitleURL>(popular, popular + arraysize(popular)), | 219 Check(std::vector<TitleURL>(popular, popular + arraysize(popular)), |
| 115 std::vector<TitleURL>(personal, personal + arraysize(personal)), | 220 std::vector<TitleURL>(personal, personal + arraysize(personal)), |
| 116 std::vector<TitleURL>(expected, expected + arraysize(expected))); | 221 std::vector<std::string>(old, old + arraysize(old)), old_sites_source, |
| 117 } | 222 std::vector<bool>(expected_source_is_personal, |
| 118 | 223 expected_source_is_personal + |
| 119 TEST_F(MostVisitedSitesTest, PopularSitesOverwrite) { | 224 arraysize(expected_source_is_personal)), |
| 120 TitleURL popular[] = { | 225 std::vector<TitleURL>(expected, expected + arraysize(expected))); |
| 121 TitleURL("Site 1", "https://www.site1.com/", "popular"), | 226 } |
| 122 TitleURL("Site 2", "https://www.site2.com/", "popular"), | |
| 123 TitleURL("Site 3", "https://www.site3.com/", "popular"), | |
| 124 }; | |
| 125 TitleURL personal[] = { | |
| 126 TitleURL("Site 2 subpage", "https://www.site2.com/path", "server8"), | |
| 127 }; | |
| 128 // When a personal suggestions matches the host of a popular one, it should | |
| 129 // overwrite that suggestion (in its original position). | |
| 130 TitleURL expected[] = { | |
| 131 TitleURL("Site 1", "https://www.site1.com/", "popular"), | |
| 132 TitleURL("Site 2 subpage", "https://www.site2.com/path", "server8"), | |
| 133 TitleURL("Site 3", "https://www.site3.com/", "popular"), | |
| 134 }; | |
| 135 | |
| 136 Check(std::vector<TitleURL>(popular, popular + arraysize(popular)), | |
| 137 std::vector<TitleURL>(personal, personal + arraysize(personal)), | |
| 138 std::vector<TitleURL>(expected, expected + arraysize(expected))); | |
| 139 } | |
| 140 | |
| 141 TEST_F(MostVisitedSitesTest, PopularSitesOrdering) { | |
| 142 TitleURL popular[] = { | |
| 143 TitleURL("Site 1", "https://www.site1.com/", "popular"), | |
| 144 TitleURL("Site 2", "https://www.site2.com/", "popular"), | |
| 145 TitleURL("Site 3", "https://www.site3.com/", "popular"), | |
| 146 TitleURL("Site 4", "https://www.site4.com/", "popular"), | |
| 147 }; | |
| 148 TitleURL personal[] = { | |
| 149 TitleURL("Site 3", "https://www.site3.com/", "server8"), | |
| 150 TitleURL("Site 4", "https://www.site4.com/", "server8"), | |
| 151 TitleURL("Site 1", "https://www.site1.com/", "server8"), | |
| 152 TitleURL("Site 2", "https://www.site2.com/", "server8"), | |
| 153 }; | |
| 154 // The personal sites should replace the popular ones, but the order of the | |
| 155 // popular sites should win (since presumably they were there first). | |
| 156 TitleURL expected[] = { | |
| 157 TitleURL("Site 1", "https://www.site1.com/", "server8"), | |
| 158 TitleURL("Site 2", "https://www.site2.com/", "server8"), | |
| 159 TitleURL("Site 3", "https://www.site3.com/", "server8"), | |
| 160 TitleURL("Site 4", "https://www.site4.com/", "server8"), | |
| 161 }; | |
| 162 | |
| 163 Check(std::vector<TitleURL>(popular, popular + arraysize(popular)), | |
| 164 std::vector<TitleURL>(personal, personal + arraysize(personal)), | |
| 165 std::vector<TitleURL>(expected, expected + arraysize(expected))); | |
| 166 } | |
| 167 | |
| 168 TEST_F(MostVisitedSitesTest, PopularSitesComplex) { | |
| 169 TitleURL popular[] = { | |
| 170 TitleURL("Site 1", "https://www.site1.com/", "popular"), | |
| 171 TitleURL("Site 2", "https://www.site2.com/", "popular"), | |
| 172 TitleURL("Site 3", "https://www.site3.com/", "popular"), | |
| 173 }; | |
| 174 TitleURL personal[] = { | |
| 175 TitleURL("Site 3 subpage", "https://www.site3.com/path", "server8"), | |
| 176 TitleURL("Site 1 subpage", "https://www.site1.com/path", "server8"), | |
| 177 TitleURL("Site 5", "https://www.site5.com/", "server8"), | |
| 178 TitleURL("Site 6", "https://www.site6.com/", "server8"), | |
| 179 }; | |
| 180 // Combination of behaviors: Personal suggestions replace matching popular | |
| 181 // ones while keeping the position of the popular suggestion. Remaining | |
| 182 // personal suggestions evict popular ones and retain their relative order. | |
| 183 TitleURL expected[] = { | |
| 184 TitleURL("Site 1 subpage", "https://www.site1.com/path", "server8"), | |
| 185 TitleURL("Site 5", "https://www.site5.com/", "server8"), | |
| 186 TitleURL("Site 3 subpage", "https://www.site3.com/path", "server8"), | |
| 187 TitleURL("Site 6", "https://www.site6.com/", "server8"), | |
| 188 }; | |
| 189 | |
| 190 Check(std::vector<TitleURL>(popular, popular + arraysize(popular)), | |
| 191 std::vector<TitleURL>(personal, personal + arraysize(personal)), | |
| 192 std::vector<TitleURL>(expected, expected + arraysize(expected))); | |
| 193 } | |
| OLD | NEW |