1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #include "base/basictypes.h" 6 #include "base/string_piece.h" 7 #include "base/utf_string_conversions.h" 8 #include "chrome/browser/history/history_types.h" 9 #include "chrome/browser/sync/glue/typed_url_model_associator.h" 10 #include "chrome/browser/sync/protocol/typed_url_specifics.pb.h" 11 #include "googleurl/src/gurl.h" 12 #include "testing/gtest/include/gtest/gtest.h" 13 14 using browser_sync::TypedUrlModelAssociator; 15 16 class TypedUrlModelAssociatorTest : public testing::Test { 17 public: 18 static history::URLRow MakeTypedUrlRow(const char* url, 19 const char* title, 20 int typed_count, 21 int64 last_visit, 22 bool hidden, 23 history::VisitVector* visits) { 24 GURL gurl(url); 25 history::URLRow history_url(gurl); 26 history_url.set_title(UTF8ToUTF16(title)); 27 history_url.set_typed_count(typed_count); 28 history_url.set_last_visit( 29 base::Time::FromInternalValue(last_visit)); 30 history_url.set_hidden(hidden); 31 visits->push_back(history::VisitRow( 32 history_url.id(), history_url.last_visit(), 0, 0, 0)); 33 history_url.set_visit_count(visits->size()); 34 return history_url; 35 } 36 37 static sync_pb::TypedUrlSpecifics MakeTypedUrlSpecifics(const char* url, 38 const char* title, 39 int typed_count, 40 int64 last_visit, 41 bool hidden) { 42 sync_pb::TypedUrlSpecifics typed_url; 43 typed_url.set_url(url); 44 typed_url.set_title(title); 45 typed_url.set_typed_count(typed_count); 46 typed_url.set_hidden(hidden); 47 typed_url.add_visit(last_visit); 48 return typed_url; 49 } 50 51 static bool URLsEqual(history::URLRow& lhs, history::URLRow& rhs) { 52 return (lhs.url().spec().compare(rhs.url().spec()) == 0) && 53 (lhs.title().compare(rhs.title()) == 0) && 54 (lhs.visit_count() == rhs.visit_count()) && 55 (lhs.typed_count() == rhs.typed_count()) && 56 (lhs.hidden() == rhs.hidden()); 57 } 58 }; 59 60 TEST_F(TypedUrlModelAssociatorTest, MergeUrls) { 61 history::VisitVector visits1; 62 history::URLRow row1(MakeTypedUrlRow("http://pie.com/", "pie", 63 2, 3, false, &visits1)); 64 sync_pb::TypedUrlSpecifics specs1(MakeTypedUrlSpecifics("http://pie.com/", 65 "pie", 66 2, 3, false)); 67 history::URLRow new_row1(GURL("http://pie.com/")); 68 std::vector<base::Time> new_visits1; 69 EXPECT_EQ(TypedUrlModelAssociator::DIFF_NONE, 70 TypedUrlModelAssociator::MergeUrls(specs1, row1, &visits1, 71 &new_row1, &new_visits1)); 72 73 history::VisitVector visits2; 74 history::URLRow row2(MakeTypedUrlRow("http://pie.com/", "pie", 75 2, 3, false, &visits2)); 76 sync_pb::TypedUrlSpecifics specs2(MakeTypedUrlSpecifics("http://pie.com/", 77 "pie", 78 2, 3, true)); 79 history::VisitVector expected_visits2; 80 history::URLRow expected2(MakeTypedUrlRow("http://pie.com/", "pie", 81 2, 3, true, &expected_visits2)); 82 history::URLRow new_row2(GURL("http://pie.com/")); 83 std::vector<base::Time> new_visits2; 84 EXPECT_EQ(TypedUrlModelAssociator::DIFF_ROW_CHANGED, 85 TypedUrlModelAssociator::MergeUrls(specs2, row2, &visits2, 86 &new_row2, &new_visits2)); 87 EXPECT_TRUE(URLsEqual(new_row2, expected2)); 88 89 history::VisitVector visits3; 90 history::URLRow row3(MakeTypedUrlRow("http://pie.com/", "pie", 91 2, 3, false, &visits3)); 92 sync_pb::TypedUrlSpecifics specs3(MakeTypedUrlSpecifics("http://pie.com/", 93 "pie2", 94 2, 3, true)); 95 history::VisitVector expected_visits3; 96 history::URLRow expected3(MakeTypedUrlRow("http://pie.com/", "pie2", 97 2, 3, true, &expected_visits3)); 98 history::URLRow new_row3(GURL("http://pie.com/")); 99 std::vector<base::Time> new_visits3; 100 EXPECT_EQ(TypedUrlModelAssociator::DIFF_ROW_CHANGED | 101 TypedUrlModelAssociator::DIFF_TITLE_CHANGED, 102 TypedUrlModelAssociator::MergeUrls(specs3, row3, &visits3, 103 &new_row3, &new_visits3)); 104 EXPECT_TRUE(URLsEqual(new_row3, expected3)); 105 106 history::VisitVector visits4; 107 history::URLRow row4(MakeTypedUrlRow("http://pie.com/", "pie", 108 2, 4, false, &visits4)); 109 sync_pb::TypedUrlSpecifics specs4(MakeTypedUrlSpecifics("http://pie.com/", 110 "pie2", 111 2, 3, true)); 112 history::VisitVector expected_visits4; 113 history::URLRow expected4(MakeTypedUrlRow("http://pie.com/", "pie", 114 2, 3, false, &expected_visits4)); 115 history::URLRow new_row4(GURL("http://pie.com/")); 116 std::vector<base::Time> new_visits4; 117 EXPECT_EQ(TypedUrlModelAssociator::DIFF_NODE_CHANGED | 118 TypedUrlModelAssociator::DIFF_VISITS_ADDED, 119 TypedUrlModelAssociator::MergeUrls(specs4, row4, &visits4, 120 &new_row4, &new_visits4)); 121 EXPECT_TRUE(URLsEqual(new_row4, expected4)); 122 123 history::VisitVector visits5; 124 history::URLRow row5(MakeTypedUrlRow("http://pie.com/", "pie", 125 1, 4, false, &visits5)); 126 sync_pb::TypedUrlSpecifics specs5(MakeTypedUrlSpecifics("http://pie.com/", 127 "pie", 128 2, 3, false)); 129 history::VisitVector expected_visits5; 130 history::URLRow expected5(MakeTypedUrlRow("http://pie.com/", "pie", 131 2, 3, false, &expected_visits5)); 132 history::URLRow new_row5(GURL("http://pie.com/")); 133 std::vector<base::Time> new_visits5; 134 EXPECT_EQ(TypedUrlModelAssociator::DIFF_ROW_CHANGED | 135 TypedUrlModelAssociator::DIFF_VISITS_ADDED, 136 TypedUrlModelAssociator::MergeUrls(specs5, row5, &visits5, 137 &new_row5, &new_visits5)); 138 EXPECT_TRUE(URLsEqual(new_row5, expected5)); 139 140 } 141 142 TEST_F(TypedUrlModelAssociatorTest, DiffVisitsSame) { 143 history::VisitVector old_visits; 144 sync_pb::TypedUrlSpecifics new_url; 145 146 const int64 visits[] = { 1024, 2065, 65534, 1237684 }; 147 148 for (size_t c = 0; c < arraysize(visits); ++c) { 149 old_visits.push_back(history::VisitRow( 150 0, base::Time::FromInternalValue(visits[c]), 0, 0, 0)); 151 new_url.add_visit(visits[c]); 152 } 153 154 std::vector<base::Time> new_visits; 155 history::VisitVector removed_visits; 156 157 TypedUrlModelAssociator::DiffVisits(old_visits, new_url, 158 &new_visits, &removed_visits); 159 EXPECT_TRUE(new_visits.empty()); 160 EXPECT_TRUE(removed_visits.empty()); 161 } 162 163 TEST_F(TypedUrlModelAssociatorTest, DiffVisitsRemove) { 164 history::VisitVector old_visits; 165 sync_pb::TypedUrlSpecifics new_url; 166 167 const int64 visits_left[] = { 1, 1024, 1500, 2065, 6000, 168 65534, 1237684, 2237684 }; 169 const int64 visits_right[] = { 1024, 2065, 65534, 1237684 }; 170 171 const int64 visits_removed[] = { 1, 1500, 6000, 2237684 }; 172 173 for (size_t c = 0; c < arraysize(visits_left); ++c) { 174 old_visits.push_back(history::VisitRow( 175 0, base::Time::FromInternalValue(visits_left[c]), 0, 0, 0)); 176 } 177 178 for (size_t c = 0; c < arraysize(visits_right); ++c) { 179 new_url.add_visit(visits_right[c]); 180 } 181 182 std::vector<base::Time> new_visits; 183 history::VisitVector removed_visits; 184 185 TypedUrlModelAssociator::DiffVisits(old_visits, new_url, 186 &new_visits, &removed_visits); 187 EXPECT_TRUE(new_visits.empty()); 188 ASSERT_TRUE(removed_visits.size() == arraysize(visits_removed)); 189 for (size_t c = 0; c < arraysize(visits_removed); ++c) { 190 EXPECT_EQ(removed_visits[c].visit_time.ToInternalValue(), 191 visits_removed[c]); 192 } 193 } 194 195 TEST_F(TypedUrlModelAssociatorTest, DiffVisitsAdd) { 196 history::VisitVector old_visits; 197 sync_pb::TypedUrlSpecifics new_url; 198 199 const int64 visits_left[] = { 1024, 2065, 65534, 1237684 }; 200 const int64 visits_right[] = { 1, 1024, 1500, 2065, 6000, 201 65534, 1237684, 2237684 }; 202 203 const int64 visits_added[] = { 1, 1500, 6000, 2237684 }; 204 205 for (size_t c = 0; c < arraysize(visits_left); ++c) { 206 old_visits.push_back(history::VisitRow( 207 0, base::Time::FromInternalValue(visits_left[c]), 0, 0, 0)); 208 } 209 210 for (size_t c = 0; c < arraysize(visits_right); ++c) { 211 new_url.add_visit(visits_right[c]); 212 } 213 214 std::vector<base::Time> new_visits; 215 history::VisitVector removed_visits; 216 217 TypedUrlModelAssociator::DiffVisits(old_visits, new_url, 218 &new_visits, &removed_visits); 219 EXPECT_TRUE(removed_visits.empty()); 220 ASSERT_TRUE(new_visits.size() == arraysize(visits_added)); 221 for (size_t c = 0; c < arraysize(visits_added); ++c) { 222 EXPECT_EQ(new_visits[c].ToInternalValue(), 223 visits_added[c]); 224 } 225 } 226