OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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 <string> | 5 #include <string> |
6 #include <vector> | 6 #include <vector> |
7 | 7 |
8 #include "base/memory/scoped_ptr.h" | 8 #include "base/memory/scoped_ptr.h" |
9 #include "base/message_loop.h" | 9 #include "base/message_loop.h" |
10 #include "base/string_number_conversions.h" | |
11 #include "chrome/browser/sessions/session_types.h" | 10 #include "chrome/browser/sessions/session_types.h" |
12 #include "chrome/browser/sessions/session_types_test_helper.h" | 11 #include "chrome/browser/sessions/session_types_test_helper.h" |
13 #include "chrome/browser/sync/glue/session_model_associator.h" | 12 #include "chrome/browser/sync/glue/session_model_associator.h" |
14 #include "chrome/browser/sync/glue/synced_tab_delegate.h" | 13 #include "chrome/browser/sync/glue/synced_tab_delegate.h" |
15 #include "chrome/browser/sync/profile_sync_service_mock.h" | 14 #include "chrome/browser/sync/profile_sync_service_mock.h" |
16 #include "chrome/common/chrome_notification_types.h" | 15 #include "chrome/common/chrome_notification_types.h" |
17 #include "chrome/common/url_constants.h" | 16 #include "chrome/common/url_constants.h" |
18 #include "chrome/test/base/profile_mock.h" | 17 #include "chrome/test/base/profile_mock.h" |
19 #include "content/public/browser/navigation_entry.h" | 18 #include "content/public/browser/navigation_entry.h" |
20 #include "content/public/browser/notification_details.h" | 19 #include "content/public/browser/notification_details.h" |
21 #include "content/public/browser/notification_service.h" | 20 #include "content/public/browser/notification_service.h" |
22 #include "content/public/common/page_transition_types.h" | 21 #include "content/public/common/page_transition_types.h" |
23 #include "content/public/test/test_browser_thread.h" | 22 #include "content/public/test/test_browser_thread.h" |
| 23 #include "googleurl/src/gurl.h" |
24 #include "sync/protocol/session_specifics.pb.h" | 24 #include "sync/protocol/session_specifics.pb.h" |
25 #include "sync/util/time.h" | 25 #include "sync/util/time.h" |
26 #include "testing/gmock/include/gmock/gmock.h" | 26 #include "testing/gmock/include/gmock/gmock.h" |
27 #include "testing/gtest/include/gtest/gtest.h" | 27 #include "testing/gtest/include/gtest/gtest.h" |
28 | 28 |
29 using content::BrowserThread; | 29 using content::BrowserThread; |
30 using testing::NiceMock; | 30 using testing::NiceMock; |
31 using testing::Return; | 31 using testing::Return; |
| 32 using testing::StrictMock; |
32 using testing::_; | 33 using testing::_; |
33 | 34 |
34 namespace browser_sync { | 35 namespace browser_sync { |
35 | 36 |
36 class SyncSessionModelAssociatorTest : public testing::Test { | 37 class SyncSessionModelAssociatorTest : public testing::Test { |
37 public: | 38 protected: |
38 SyncSessionModelAssociatorTest() | 39 SyncSessionModelAssociatorTest() |
39 : ui_thread_(BrowserThread::UI, &message_loop_), | 40 : ui_thread_(BrowserThread::UI, &message_loop_), |
40 sync_service_(&profile_), | 41 sync_service_(&profile_), |
41 model_associator_(&sync_service_, true) {} | 42 model_associator_(&sync_service_, true) {} |
42 | 43 |
43 // Helper methods to avoid having to friend individual tests. | 44 // Helper methods to avoid having to friend individual tests. |
44 bool GetFavicon(std::string page_url, std::string* favicon) { | 45 bool GetFavicon(std::string page_url, std::string* favicon) { |
45 return model_associator_.GetSyncedFaviconForPageURL(page_url, favicon); | 46 return model_associator_.GetSyncedFaviconForPageURL(page_url, favicon); |
46 } | 47 } |
47 | 48 |
48 void LoadTabFavicon(const sync_pb::SessionTab& tab) { | 49 void LoadTabFavicon(const sync_pb::SessionTab& tab) { |
49 model_associator_.LoadForeignTabFavicon(tab); | 50 model_associator_.LoadForeignTabFavicon(tab); |
50 } | 51 } |
51 | 52 |
52 size_t NumFavicons() { | 53 size_t NumFavicons() { |
53 return model_associator_.NumFaviconsForTesting(); | 54 return model_associator_.NumFaviconsForTesting(); |
54 } | 55 } |
55 | 56 |
56 void DecrementFavicon(std::string url) { | 57 void DecrementFavicon(std::string url) { |
57 model_associator_.DecrementAndCleanFaviconForURL(url); | 58 model_associator_.DecrementAndCleanFaviconForURL(url); |
58 } | 59 } |
59 | 60 |
60 void AssociateTabContents(const SyncedWindowDelegate& window, | 61 static GURL GetCurrentVirtualURL(const SyncedTabDelegate& tab_delegate) { |
61 const SyncedTabDelegate& new_tab, | 62 return SessionModelAssociator::GetCurrentVirtualURL(tab_delegate); |
62 SessionTab* prev_tab, | |
63 sync_pb::SessionTab* sync_tab, | |
64 GURL* new_url) { | |
65 model_associator_.AssociateTabContents(window, | |
66 new_tab, | |
67 prev_tab, | |
68 sync_tab, | |
69 new_url); | |
70 } | 63 } |
71 | 64 |
72 protected: | 65 static void UpdateSessionTabFromDelegate( |
| 66 const SyncedTabDelegate& tab_delegate, |
| 67 base::Time mtime, |
| 68 base::Time default_navigation_timestamp, |
| 69 SessionTab* session_tab) { |
| 70 SessionModelAssociator::UpdateSessionTabFromDelegate( |
| 71 tab_delegate, |
| 72 mtime, |
| 73 default_navigation_timestamp, |
| 74 session_tab); |
| 75 } |
| 76 |
| 77 private: |
73 MessageLoopForUI message_loop_; | 78 MessageLoopForUI message_loop_; |
74 content::TestBrowserThread ui_thread_; | 79 content::TestBrowserThread ui_thread_; |
75 NiceMock<ProfileMock> profile_; | 80 NiceMock<ProfileMock> profile_; |
76 NiceMock<ProfileSyncServiceMock> sync_service_; | 81 NiceMock<ProfileSyncServiceMock> sync_service_; |
| 82 |
| 83 protected: |
77 SessionModelAssociator model_associator_; | 84 SessionModelAssociator model_associator_; |
78 }; | 85 }; |
79 | 86 |
| 87 namespace { |
| 88 |
80 TEST_F(SyncSessionModelAssociatorTest, SessionWindowHasNoTabsToSync) { | 89 TEST_F(SyncSessionModelAssociatorTest, SessionWindowHasNoTabsToSync) { |
81 SessionWindow win; | 90 SessionWindow win; |
82 ASSERT_TRUE(SessionWindowHasNoTabsToSync(win)); | 91 ASSERT_TRUE(SessionWindowHasNoTabsToSync(win)); |
83 scoped_ptr<SessionTab> tab(new SessionTab()); | 92 scoped_ptr<SessionTab> tab(new SessionTab()); |
84 win.tabs.push_back(tab.release()); | 93 win.tabs.push_back(tab.release()); |
85 ASSERT_TRUE(SessionWindowHasNoTabsToSync(win)); | 94 ASSERT_TRUE(SessionWindowHasNoTabsToSync(win)); |
86 TabNavigation nav = | 95 TabNavigation nav = |
87 SessionTypesTestHelper::CreateNavigation("about:bubba", "title"); | 96 SessionTypesTestHelper::CreateNavigation("about:bubba", "title"); |
88 win.tabs[0]->navigations.push_back(nav); | 97 win.tabs[0]->navigations.push_back(nav); |
89 ASSERT_FALSE(SessionWindowHasNoTabsToSync(win)); | 98 ASSERT_FALSE(SessionWindowHasNoTabsToSync(win)); |
(...skipping 20 matching lines...) Expand all Loading... |
110 SessionTab tab; | 119 SessionTab tab; |
111 ASSERT_FALSE(ShouldSyncSessionTab(tab)); | 120 ASSERT_FALSE(ShouldSyncSessionTab(tab)); |
112 TabNavigation nav = | 121 TabNavigation nav = |
113 SessionTypesTestHelper::CreateNavigation( | 122 SessionTypesTestHelper::CreateNavigation( |
114 std::string(chrome::kChromeUINewTabURL) + "#bookmarks", "title"); | 123 std::string(chrome::kChromeUINewTabURL) + "#bookmarks", "title"); |
115 tab.navigations.push_back(nav); | 124 tab.navigations.push_back(nav); |
116 // NewTab does not count as valid if it's the only navigation. | 125 // NewTab does not count as valid if it's the only navigation. |
117 ASSERT_FALSE(ShouldSyncSessionTab(tab)); | 126 ASSERT_FALSE(ShouldSyncSessionTab(tab)); |
118 } | 127 } |
119 | 128 |
| 129 } // namespace |
| 130 |
120 TEST_F(SyncSessionModelAssociatorTest, PopulateSessionHeader) { | 131 TEST_F(SyncSessionModelAssociatorTest, PopulateSessionHeader) { |
121 sync_pb::SessionHeader header_s; | 132 sync_pb::SessionHeader header_s; |
122 header_s.set_client_name("Client 1"); | 133 header_s.set_client_name("Client 1"); |
123 header_s.set_device_type(sync_pb::SessionHeader_DeviceType_TYPE_WIN); | 134 header_s.set_device_type(sync_pb::SessionHeader_DeviceType_TYPE_WIN); |
124 | 135 |
125 SyncedSession session; | 136 SyncedSession session; |
126 base::Time time = base::Time::Now(); | 137 base::Time time = base::Time::Now(); |
127 SessionModelAssociator::PopulateSessionHeaderFromSpecifics( | 138 SessionModelAssociator::PopulateSessionHeaderFromSpecifics( |
128 header_s, time, &session); | 139 header_s, time, &session); |
129 ASSERT_EQ("Client 1", session.session_name); | 140 ASSERT_EQ("Client 1", session.session_name); |
(...skipping 13 matching lines...) Expand all Loading... |
143 tracker.PutWindowInSession(tag, 0); | 154 tracker.PutWindowInSession(tag, 0); |
144 SessionModelAssociator::PopulateSessionWindowFromSpecifics( | 155 SessionModelAssociator::PopulateSessionWindowFromSpecifics( |
145 tag, window_s, base::Time(), session->windows[0], &tracker); | 156 tag, window_s, base::Time(), session->windows[0], &tracker); |
146 ASSERT_EQ(1U, session->windows[0]->tabs.size()); | 157 ASSERT_EQ(1U, session->windows[0]->tabs.size()); |
147 ASSERT_EQ(1, session->windows[0]->selected_tab_index); | 158 ASSERT_EQ(1, session->windows[0]->selected_tab_index); |
148 ASSERT_EQ(1, session->windows[0]->type); | 159 ASSERT_EQ(1, session->windows[0]->type); |
149 ASSERT_EQ(1U, tracker.num_synced_sessions()); | 160 ASSERT_EQ(1U, tracker.num_synced_sessions()); |
150 ASSERT_EQ(1U, tracker.num_synced_tabs(std::string("tag"))); | 161 ASSERT_EQ(1U, tracker.num_synced_tabs(std::string("tag"))); |
151 } | 162 } |
152 | 163 |
153 TEST_F(SyncSessionModelAssociatorTest, PopulateSessionTab) { | |
154 sync_pb::SessionTab tab_s; | |
155 tab_s.set_tab_id(5); | |
156 tab_s.set_tab_visual_index(13); | |
157 tab_s.set_current_navigation_index(3); | |
158 tab_s.set_pinned(true); | |
159 tab_s.set_extension_app_id("app_id"); | |
160 for (int i = 0; i < 5; ++i) { | |
161 sync_pb::TabNavigation* navigation = tab_s.add_navigation(); | |
162 navigation->set_virtual_url("http://foo/" + base::IntToString(i)); | |
163 navigation->set_referrer("referrer"); | |
164 navigation->set_title("title"); | |
165 navigation->set_page_transition(sync_pb::SyncEnums_PageTransition_TYPED); | |
166 } | |
167 | |
168 SessionTab tab; | |
169 tab.tab_id.set_id(5); // Expected to be set by the SyncedSessionTracker. | |
170 SessionModelAssociator::PopulateSessionTabFromSpecifics( | |
171 tab_s, base::Time(), &tab); | |
172 ASSERT_EQ(5, tab.tab_id.id()); | |
173 ASSERT_EQ(13, tab.tab_visual_index); | |
174 ASSERT_EQ(3, tab.current_navigation_index); | |
175 ASSERT_TRUE(tab.pinned); | |
176 ASSERT_EQ("app_id", tab.extension_app_id); | |
177 ASSERT_EQ(5u, tab.navigations.size()); | |
178 for (int i = 0; i < 5; ++i) { | |
179 ASSERT_EQ(i, tab.navigations[i].index()); | |
180 ASSERT_EQ(GURL("referrer"), | |
181 SessionTypesTestHelper::GetReferrer(tab.navigations[i]).url); | |
182 ASSERT_EQ(string16(ASCIIToUTF16("title")), tab.navigations[i].title()); | |
183 ASSERT_EQ(content::PAGE_TRANSITION_TYPED, | |
184 SessionTypesTestHelper::GetTransitionType(tab.navigations[i])); | |
185 ASSERT_EQ(GURL("http://foo/" + base::IntToString(i)), | |
186 tab.navigations[i].virtual_url()); | |
187 } | |
188 } | |
189 | |
190 TEST_F(SyncSessionModelAssociatorTest, TabNodePool) { | 164 TEST_F(SyncSessionModelAssociatorTest, TabNodePool) { |
191 SessionModelAssociator::TabNodePool pool(NULL); | 165 SessionModelAssociator::TabNodePool pool(NULL); |
192 pool.set_machine_tag("tag"); | 166 pool.set_machine_tag("tag"); |
193 ASSERT_TRUE(pool.empty()); | 167 ASSERT_TRUE(pool.empty()); |
194 ASSERT_TRUE(pool.full()); | 168 ASSERT_TRUE(pool.full()); |
195 ASSERT_EQ(0U, pool.capacity()); | 169 ASSERT_EQ(0U, pool.capacity()); |
196 pool.AddTabNode(5); | 170 pool.AddTabNode(5); |
197 pool.AddTabNode(10); | 171 pool.AddTabNode(10); |
198 ASSERT_FALSE(pool.empty()); | 172 ASSERT_FALSE(pool.empty()); |
199 ASSERT_TRUE(pool.full()); | 173 ASSERT_TRUE(pool.full()); |
(...skipping 30 matching lines...) Expand all Loading... |
230 ASSERT_TRUE(pool.full()); | 204 ASSERT_TRUE(pool.full()); |
231 ASSERT_EQ(2U, pool.capacity()); | 205 ASSERT_EQ(2U, pool.capacity()); |
232 pool.clear(); | 206 pool.clear(); |
233 ASSERT_TRUE(pool.empty()); | 207 ASSERT_TRUE(pool.empty()); |
234 ASSERT_TRUE(pool.full()); | 208 ASSERT_TRUE(pool.full()); |
235 ASSERT_EQ(0U, pool.capacity()); | 209 ASSERT_EQ(0U, pool.capacity()); |
236 } | 210 } |
237 | 211 |
238 namespace { | 212 namespace { |
239 | 213 |
240 class SyncedWindowDelegateMock : public SyncedWindowDelegate { | |
241 public: | |
242 SyncedWindowDelegateMock() {} | |
243 virtual ~SyncedWindowDelegateMock() {} | |
244 MOCK_CONST_METHOD0(HasWindow, bool()); | |
245 MOCK_CONST_METHOD0(GetSessionId, SessionID::id_type()); | |
246 MOCK_CONST_METHOD0(GetTabCount, int()); | |
247 MOCK_CONST_METHOD0(GetActiveIndex, int()); | |
248 MOCK_CONST_METHOD0(IsApp, bool()); | |
249 MOCK_CONST_METHOD0(IsTypeTabbed, bool()); | |
250 MOCK_CONST_METHOD0(IsTypePopup, bool()); | |
251 MOCK_CONST_METHOD1(IsTabPinned, bool(const SyncedTabDelegate* tab)); | |
252 MOCK_CONST_METHOD1(GetTabAt, SyncedTabDelegate*(int index)); | |
253 MOCK_CONST_METHOD1(GetTabIdAt, SessionID::id_type(int index)); | |
254 MOCK_CONST_METHOD0(IsSessionRestoreInProgress, bool()); | |
255 }; | |
256 | |
257 class SyncedTabDelegateMock : public SyncedTabDelegate { | 214 class SyncedTabDelegateMock : public SyncedTabDelegate { |
258 public: | 215 public: |
259 SyncedTabDelegateMock() {} | 216 SyncedTabDelegateMock() {} |
260 virtual ~SyncedTabDelegateMock() {} | 217 virtual ~SyncedTabDelegateMock() {} |
261 | 218 |
262 MOCK_CONST_METHOD0(GetWindowId, SessionID::id_type()); | 219 MOCK_CONST_METHOD0(GetWindowId, SessionID::id_type()); |
263 MOCK_CONST_METHOD0(GetSessionId, SessionID::id_type()); | 220 MOCK_CONST_METHOD0(GetSessionId, SessionID::id_type()); |
264 MOCK_CONST_METHOD0(IsBeingDestroyed, bool()); | 221 MOCK_CONST_METHOD0(IsBeingDestroyed, bool()); |
265 MOCK_CONST_METHOD0(profile, Profile*()); | 222 MOCK_CONST_METHOD0(profile, Profile*()); |
266 MOCK_CONST_METHOD0(HasExtensionAppId, bool()); | 223 MOCK_CONST_METHOD0(GetExtensionAppId, std::string()); |
267 MOCK_CONST_METHOD0(GetExtensionAppId, const std::string&()); | |
268 MOCK_CONST_METHOD0(GetCurrentEntryIndex, int()); | 224 MOCK_CONST_METHOD0(GetCurrentEntryIndex, int()); |
269 MOCK_CONST_METHOD0(GetEntryCount, int()); | 225 MOCK_CONST_METHOD0(GetEntryCount, int()); |
270 MOCK_CONST_METHOD0(GetPendingEntryIndex, int()); | 226 MOCK_CONST_METHOD0(GetPendingEntryIndex, int()); |
271 MOCK_CONST_METHOD0(GetPendingEntry, content::NavigationEntry*()); | 227 MOCK_CONST_METHOD0(GetPendingEntry, content::NavigationEntry*()); |
272 MOCK_CONST_METHOD1(GetEntryAtIndex, content::NavigationEntry*(int i)); | 228 MOCK_CONST_METHOD1(GetEntryAtIndex, content::NavigationEntry*(int i)); |
273 MOCK_CONST_METHOD0(GetActiveEntry, content::NavigationEntry*()); | 229 MOCK_CONST_METHOD0(GetActiveEntry, content::NavigationEntry*()); |
| 230 MOCK_CONST_METHOD0(IsPinned, bool()); |
274 }; | 231 }; |
275 | 232 |
276 class SyncRefreshListener : public content::NotificationObserver { | 233 class SyncRefreshListener : public content::NotificationObserver { |
277 public: | 234 public: |
278 SyncRefreshListener() : notified_of_refresh_(false) { | 235 SyncRefreshListener() : notified_of_refresh_(false) { |
279 registrar_.Add(this, chrome::NOTIFICATION_SYNC_REFRESH_LOCAL, | 236 registrar_.Add(this, chrome::NOTIFICATION_SYNC_REFRESH_LOCAL, |
280 content::NotificationService::AllSources()); | 237 content::NotificationService::AllSources()); |
281 } | 238 } |
282 | 239 |
283 void Observe(int type, | 240 void Observe(int type, |
284 const content::NotificationSource& source, | 241 const content::NotificationSource& source, |
285 const content::NotificationDetails& details) { | 242 const content::NotificationDetails& details) { |
286 if (type == chrome::NOTIFICATION_SYNC_REFRESH_LOCAL) { | 243 if (type == chrome::NOTIFICATION_SYNC_REFRESH_LOCAL) { |
287 notified_of_refresh_ = true; | 244 notified_of_refresh_ = true; |
288 } | 245 } |
289 } | 246 } |
290 | 247 |
291 bool notified_of_refresh() const { return notified_of_refresh_; } | 248 bool notified_of_refresh() const { return notified_of_refresh_; } |
292 | 249 |
293 private: | 250 private: |
294 bool notified_of_refresh_; | 251 bool notified_of_refresh_; |
295 content::NotificationRegistrar registrar_; | 252 content::NotificationRegistrar registrar_; |
296 }; | 253 }; |
297 | 254 |
298 } // namespace. | |
299 | |
300 // Test that AttemptSessionsDataRefresh() triggers the | 255 // Test that AttemptSessionsDataRefresh() triggers the |
301 // NOTIFICATION_SYNC_REFRESH_LOCAL notification. | 256 // NOTIFICATION_SYNC_REFRESH_LOCAL notification. |
302 TEST_F(SyncSessionModelAssociatorTest, TriggerSessionRefresh) { | 257 TEST_F(SyncSessionModelAssociatorTest, TriggerSessionRefresh) { |
303 SyncRefreshListener refresh_listener; | 258 SyncRefreshListener refresh_listener; |
304 | 259 |
305 EXPECT_FALSE(refresh_listener.notified_of_refresh()); | 260 EXPECT_FALSE(refresh_listener.notified_of_refresh()); |
306 model_associator_.AttemptSessionsDataRefresh(); | 261 model_associator_.AttemptSessionsDataRefresh(); |
307 EXPECT_TRUE(refresh_listener.notified_of_refresh()); | 262 EXPECT_TRUE(refresh_listener.notified_of_refresh()); |
308 } | 263 } |
309 | 264 |
(...skipping 245 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
555 synced_favicon.clear(); | 510 synced_favicon.clear(); |
556 EXPECT_FALSE(GetFavicon(page_url, &synced_favicon)); | 511 EXPECT_FALSE(GetFavicon(page_url, &synced_favicon)); |
557 EXPECT_TRUE(synced_favicon.empty()); | 512 EXPECT_TRUE(synced_favicon.empty()); |
558 EXPECT_EQ(0U, NumFavicons()); | 513 EXPECT_EQ(0U, NumFavicons()); |
559 synced_favicon.clear(); | 514 synced_favicon.clear(); |
560 EXPECT_FALSE(GetFavicon(page_url2, &synced_favicon)); | 515 EXPECT_FALSE(GetFavicon(page_url2, &synced_favicon)); |
561 EXPECT_TRUE(synced_favicon.empty()); | 516 EXPECT_TRUE(synced_favicon.empty()); |
562 EXPECT_EQ(0U, NumFavicons()); | 517 EXPECT_EQ(0U, NumFavicons()); |
563 } | 518 } |
564 | 519 |
565 // Ensure new tabs have the current timestamp set for the current navigation, | 520 // TODO(akalin): We should really use a fake for SyncedTabDelegate. |
566 // while other navigations have timestamp zero. | |
567 TEST_F(SyncSessionModelAssociatorTest, AssociateNewTab) { | |
568 NiceMock<SyncedWindowDelegateMock> window_mock; | |
569 EXPECT_CALL(window_mock, IsTabPinned(_)).WillRepeatedly(Return(false)); | |
570 | 521 |
| 522 // Make sure GetCurrentVirtualURL() returns the virtual URL of the pending |
| 523 // entry if the current entry is pending. |
| 524 TEST_F(SyncSessionModelAssociatorTest, GetCurrentVirtualURLPending) { |
| 525 StrictMock<SyncedTabDelegateMock> tab_mock; |
| 526 scoped_ptr<content::NavigationEntry> entry( |
| 527 content::NavigationEntry::Create()); |
| 528 entry->SetVirtualURL(GURL("http://www.google.com")); |
| 529 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillOnce(Return(0)); |
| 530 EXPECT_CALL(tab_mock, GetPendingEntryIndex()).WillOnce(Return(0)); |
| 531 EXPECT_CALL(tab_mock, GetPendingEntry()).WillOnce(Return(entry.get())); |
| 532 EXPECT_EQ(entry->GetVirtualURL(), GetCurrentVirtualURL(tab_mock)); |
| 533 } |
| 534 |
| 535 // Make sure GetCurrentVirtualURL() returns the virtual URL of the current |
| 536 // entry if the current entry is non-pending. |
| 537 TEST_F(SyncSessionModelAssociatorTest, GetCurrentVirtualURLNonPending) { |
| 538 StrictMock<SyncedTabDelegateMock> tab_mock; |
| 539 scoped_ptr<content::NavigationEntry> entry( |
| 540 content::NavigationEntry::Create()); |
| 541 entry->SetVirtualURL(GURL("http://www.google.com")); |
| 542 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillOnce(Return(0)); |
| 543 EXPECT_CALL(tab_mock, GetPendingEntryIndex()).WillOnce(Return(-1)); |
| 544 EXPECT_CALL(tab_mock, GetEntryAtIndex(0)).WillOnce(Return(entry.get())); |
| 545 EXPECT_EQ(entry->GetVirtualURL(), GetCurrentVirtualURL(tab_mock)); |
| 546 } |
| 547 |
| 548 const base::Time kTime1 = base::Time::FromInternalValue(100); |
| 549 const base::Time kTime2 = base::Time::FromInternalValue(105); |
| 550 const base::Time kTime3 = base::Time::FromInternalValue(110); |
| 551 const base::Time kTime4 = base::Time::FromInternalValue(120); |
| 552 const base::Time kTime5 = base::Time::FromInternalValue(150); |
| 553 const base::Time kTime6 = base::Time::FromInternalValue(200); |
| 554 const base::Time kTime7 = base::Time::FromInternalValue(500); |
| 555 const base::Time kTime8 = base::Time::FromInternalValue(1000); |
| 556 |
| 557 // Ensure new tabs have the current timestamp set for the current |
| 558 // navigation, while other navigations have null timestamps. |
| 559 TEST_F(SyncSessionModelAssociatorTest, UpdateNewTab) { |
571 // Create a tab with three valid entries. | 560 // Create a tab with three valid entries. |
572 NiceMock<SyncedTabDelegateMock> tab_mock; | 561 NiceMock<SyncedTabDelegateMock> tab_mock; |
573 EXPECT_CALL(tab_mock, GetSessionId()).WillRepeatedly(Return(0)); | 562 EXPECT_CALL(tab_mock, GetSessionId()).WillRepeatedly(Return(0)); |
574 scoped_ptr<content::NavigationEntry> entry1( | 563 scoped_ptr<content::NavigationEntry> entry1( |
575 content::NavigationEntry::Create()); | 564 content::NavigationEntry::Create()); |
576 entry1->SetVirtualURL(GURL("http://www.google.com")); | 565 entry1->SetVirtualURL(GURL("http://www.google.com")); |
577 scoped_ptr<content::NavigationEntry> entry2( | 566 scoped_ptr<content::NavigationEntry> entry2( |
578 content::NavigationEntry::Create()); | 567 content::NavigationEntry::Create()); |
579 entry2->SetVirtualURL(GURL("http://www.noodle.com")); | 568 entry2->SetVirtualURL(GURL("http://www.noodle.com")); |
580 scoped_ptr<content::NavigationEntry> entry3( | 569 scoped_ptr<content::NavigationEntry> entry3( |
581 content::NavigationEntry::Create()); | 570 content::NavigationEntry::Create()); |
582 entry3->SetVirtualURL(GURL("http://www.doodle.com")); | 571 entry3->SetVirtualURL(GURL("http://www.doodle.com")); |
583 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillRepeatedly(Return(2)); | 572 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillRepeatedly(Return(2)); |
584 EXPECT_CALL(tab_mock, GetEntryAtIndex(0)).WillRepeatedly( | 573 EXPECT_CALL(tab_mock, GetEntryAtIndex(0)).WillRepeatedly( |
585 Return(entry1.get())); | 574 Return(entry1.get())); |
586 EXPECT_CALL(tab_mock, GetEntryAtIndex(1)).WillRepeatedly( | 575 EXPECT_CALL(tab_mock, GetEntryAtIndex(1)).WillRepeatedly( |
587 Return(entry2.get())); | 576 Return(entry2.get())); |
588 EXPECT_CALL(tab_mock, GetEntryAtIndex(2)).WillRepeatedly( | 577 EXPECT_CALL(tab_mock, GetEntryAtIndex(2)).WillRepeatedly( |
589 Return(entry3.get())); | 578 Return(entry3.get())); |
590 EXPECT_CALL(tab_mock, GetEntryCount()).WillRepeatedly(Return(3)); | 579 EXPECT_CALL(tab_mock, GetEntryCount()).WillRepeatedly(Return(3)); |
591 EXPECT_CALL(tab_mock, GetPendingEntryIndex()).WillRepeatedly(Return(-1)); | 580 EXPECT_CALL(tab_mock, GetPendingEntryIndex()).WillRepeatedly(Return(-1)); |
592 | 581 |
593 // This tab is new, so prev_tab is the default SyncedSessionTab object. | 582 SessionTab session_tab; |
594 SessionTab prev_tab; | 583 UpdateSessionTabFromDelegate(tab_mock, kTime1, kTime2, &session_tab); |
595 prev_tab.tab_id.set_id(0); | |
596 | 584 |
597 sync_pb::SessionTab sync_tab; | 585 EXPECT_EQ(0, session_tab.window_id.id()); |
598 GURL new_url; | 586 EXPECT_EQ(0, session_tab.tab_id.id()); |
599 int64 now = syncer::TimeToProtoTime(base::Time::Now()); | 587 EXPECT_EQ(0, session_tab.tab_visual_index); |
600 AssociateTabContents(window_mock, tab_mock, &prev_tab, &sync_tab, &new_url); | 588 EXPECT_EQ(2, session_tab.current_navigation_index); |
601 | 589 EXPECT_FALSE(session_tab.pinned); |
602 EXPECT_EQ(new_url, entry3->GetVirtualURL()); | 590 EXPECT_TRUE(session_tab.extension_app_id.empty()); |
603 ASSERT_EQ(3, sync_tab.navigation_size()); | 591 EXPECT_TRUE(session_tab.user_agent_override.empty()); |
604 EXPECT_EQ(entry1->GetVirtualURL().spec(), | 592 EXPECT_EQ(kTime1, session_tab.timestamp); |
605 sync_tab.navigation(0).virtual_url()); | 593 ASSERT_EQ(3u, session_tab.navigations.size()); |
606 EXPECT_EQ(entry2->GetVirtualURL().spec(), | 594 EXPECT_EQ(entry1->GetVirtualURL(), |
607 sync_tab.navigation(1).virtual_url()); | 595 session_tab.navigations[0].virtual_url()); |
608 EXPECT_EQ(entry3->GetVirtualURL().spec(), | 596 EXPECT_EQ(entry2->GetVirtualURL(), |
609 sync_tab.navigation(2).virtual_url()); | 597 session_tab.navigations[1].virtual_url()); |
610 EXPECT_EQ(2, sync_tab.current_navigation_index()); | 598 EXPECT_EQ(entry3->GetVirtualURL(), |
611 EXPECT_LE(0, sync_tab.navigation(0).timestamp()); | 599 session_tab.navigations[2].virtual_url()); |
612 EXPECT_LE(0, sync_tab.navigation(1).timestamp()); | 600 EXPECT_EQ(2, session_tab.current_navigation_index); |
613 EXPECT_LE(now, sync_tab.navigation(2).timestamp()); | 601 EXPECT_TRUE(session_tab.navigations[0].timestamp().is_null()); |
| 602 EXPECT_TRUE(session_tab.navigations[1].timestamp().is_null()); |
| 603 EXPECT_EQ(kTime2, session_tab.navigations[2].timestamp()); |
| 604 EXPECT_TRUE(session_tab.session_storage_persistent_id.empty()); |
614 } | 605 } |
615 | 606 |
616 // Ensure we preserve old timestamps when the entries don't change. | 607 // Ensure we preserve old timestamps when the entries don't change. |
617 TEST_F(SyncSessionModelAssociatorTest, AssociateExistingTab) { | 608 TEST_F(SyncSessionModelAssociatorTest, UpdateExistingTab) { |
618 NiceMock<SyncedWindowDelegateMock> window_mock; | |
619 EXPECT_CALL(window_mock, IsTabPinned(_)).WillRepeatedly(Return(false)); | |
620 | |
621 // Create a tab with three valid entries. | 609 // Create a tab with three valid entries. |
622 NiceMock<SyncedTabDelegateMock> tab_mock; | 610 NiceMock<SyncedTabDelegateMock> tab_mock; |
623 EXPECT_CALL(tab_mock, GetSessionId()).WillRepeatedly(Return(0)); | 611 EXPECT_CALL(tab_mock, GetSessionId()).WillRepeatedly(Return(0)); |
624 scoped_ptr<content::NavigationEntry> entry1( | 612 scoped_ptr<content::NavigationEntry> entry1( |
625 content::NavigationEntry::Create()); | 613 content::NavigationEntry::Create()); |
626 entry1->SetVirtualURL(GURL("http://www.google.com")); | 614 entry1->SetVirtualURL(GURL("http://www.google.com")); |
627 scoped_ptr<content::NavigationEntry> entry2( | 615 scoped_ptr<content::NavigationEntry> entry2( |
628 content::NavigationEntry::Create()); | 616 content::NavigationEntry::Create()); |
629 entry2->SetVirtualURL(GURL("http://www.noodle.com")); | 617 entry2->SetVirtualURL(GURL("http://www.noodle.com")); |
630 scoped_ptr<content::NavigationEntry> entry3( | 618 scoped_ptr<content::NavigationEntry> entry3( |
631 content::NavigationEntry::Create()); | 619 content::NavigationEntry::Create()); |
632 entry3->SetVirtualURL(GURL("http://www.doodle.com")); | 620 entry3->SetVirtualURL(GURL("http://www.doodle.com")); |
633 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillRepeatedly(Return(2)); | 621 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillRepeatedly(Return(2)); |
634 EXPECT_CALL(tab_mock, GetEntryAtIndex(0)).WillRepeatedly( | 622 EXPECT_CALL(tab_mock, GetEntryAtIndex(0)).WillRepeatedly( |
635 Return(entry1.get())); | 623 Return(entry1.get())); |
636 EXPECT_CALL(tab_mock, GetEntryAtIndex(1)).WillRepeatedly( | 624 EXPECT_CALL(tab_mock, GetEntryAtIndex(1)).WillRepeatedly( |
637 Return(entry2.get())); | 625 Return(entry2.get())); |
638 EXPECT_CALL(tab_mock, GetEntryAtIndex(2)).WillRepeatedly( | 626 EXPECT_CALL(tab_mock, GetEntryAtIndex(2)).WillRepeatedly( |
639 Return(entry3.get())); | 627 Return(entry3.get())); |
640 EXPECT_CALL(tab_mock, GetEntryCount()).WillRepeatedly(Return(3)); | 628 EXPECT_CALL(tab_mock, GetEntryCount()).WillRepeatedly(Return(3)); |
641 EXPECT_CALL(tab_mock, GetPendingEntryIndex()).WillRepeatedly(Return(-1)); | 629 EXPECT_CALL(tab_mock, GetPendingEntryIndex()).WillRepeatedly(Return(-1)); |
| 630 EXPECT_CALL(tab_mock, IsPinned()).WillRepeatedly(Return(true)); |
642 | 631 |
643 // This tab is new, so prev_tab is the default SyncedSessionTab object. | 632 // The initial UpdateSessionTabFromDelegate call builds the session_tab. |
644 SessionTab prev_tab; | 633 SessionTab session_tab; |
645 prev_tab.tab_id.set_id(0); | 634 UpdateSessionTabFromDelegate(tab_mock, kTime1, kTime2, &session_tab); |
646 | 635 |
647 // The initial AssociateTabContents call builds the prev_tab. | 636 // Tweak the timestamps a bit. |
648 sync_pb::SessionTab sync_tab; | 637 ASSERT_EQ(3u, session_tab.navigations.size()); |
649 GURL new_url; | 638 SessionTypesTestHelper::SetTimestamp(&session_tab.navigations[0], kTime3); |
650 AssociateTabContents(window_mock, tab_mock, &prev_tab, &sync_tab, &new_url); | 639 SessionTypesTestHelper::SetTimestamp(&session_tab.navigations[1], kTime4); |
651 | 640 SessionTypesTestHelper::SetTimestamp(&session_tab.navigations[2], kTime5); |
652 ASSERT_EQ(3u, prev_tab.navigations.size()); | |
653 | 641 |
654 // Now re-associate with the same data. | 642 // Now re-associate with the same data. |
655 AssociateTabContents(window_mock, tab_mock, &prev_tab, &sync_tab, &new_url); | 643 UpdateSessionTabFromDelegate(tab_mock, kTime3, kTime4, &session_tab); |
656 | 644 |
657 EXPECT_EQ(new_url, entry3->GetVirtualURL()); | 645 EXPECT_TRUE(session_tab.pinned); |
658 ASSERT_EQ(3, sync_tab.navigation_size()); | 646 EXPECT_EQ(kTime3, session_tab.timestamp); |
659 EXPECT_EQ(entry1->GetVirtualURL().spec(), | 647 EXPECT_EQ(entry1->GetVirtualURL(), |
660 sync_tab.navigation(0).virtual_url()); | 648 session_tab.navigations[0].virtual_url()); |
661 EXPECT_EQ(entry2->GetVirtualURL().spec(), | 649 EXPECT_EQ(entry2->GetVirtualURL(), |
662 sync_tab.navigation(1).virtual_url()); | 650 session_tab.navigations[1].virtual_url()); |
663 EXPECT_EQ(entry3->GetVirtualURL().spec(), | 651 EXPECT_EQ(entry3->GetVirtualURL(), |
664 sync_tab.navigation(2).virtual_url()); | 652 session_tab.navigations[2].virtual_url()); |
665 EXPECT_EQ(2, sync_tab.current_navigation_index()); | 653 EXPECT_EQ(2, session_tab.current_navigation_index); |
666 EXPECT_EQ(syncer::TimeToProtoTime(prev_tab.navigations[0].timestamp()), | 654 EXPECT_EQ(kTime3, session_tab.navigations[0].timestamp()); |
667 sync_tab.navigation(0).timestamp()); | 655 EXPECT_EQ(kTime4, session_tab.navigations[1].timestamp()); |
668 EXPECT_EQ(syncer::TimeToProtoTime(prev_tab.navigations[1].timestamp()), | 656 EXPECT_EQ(kTime5, session_tab.navigations[2].timestamp()); |
669 sync_tab.navigation(1).timestamp()); | |
670 EXPECT_EQ(syncer::TimeToProtoTime(prev_tab.navigations[2].timestamp()), | |
671 sync_tab.navigation(2).timestamp()); | |
672 EXPECT_EQ(3U, prev_tab.navigations.size()); | |
673 } | 657 } |
674 | 658 |
675 // Ensure we add a fresh timestamp for new entries appended to the end. | 659 // Ensure we add a fresh timestamp for new entries appended to the end. |
676 TEST_F(SyncSessionModelAssociatorTest, AssociateAppendedTab) { | 660 TEST_F(SyncSessionModelAssociatorTest, UpdateAppendedTab) { |
677 NiceMock<SyncedWindowDelegateMock> window_mock; | |
678 EXPECT_CALL(window_mock, IsTabPinned(_)).WillRepeatedly(Return(false)); | |
679 | |
680 // Create a tab with three valid entries. | 661 // Create a tab with three valid entries. |
681 NiceMock<SyncedTabDelegateMock> tab_mock; | 662 NiceMock<SyncedTabDelegateMock> tab_mock; |
682 EXPECT_CALL(tab_mock, GetSessionId()).WillRepeatedly(Return(0)); | 663 EXPECT_CALL(tab_mock, GetSessionId()).WillRepeatedly(Return(0)); |
683 scoped_ptr<content::NavigationEntry> entry1( | 664 scoped_ptr<content::NavigationEntry> entry1( |
684 content::NavigationEntry::Create()); | 665 content::NavigationEntry::Create()); |
685 entry1->SetVirtualURL(GURL("http://www.google.com")); | 666 entry1->SetVirtualURL(GURL("http://www.google.com")); |
686 scoped_ptr<content::NavigationEntry> entry2( | 667 scoped_ptr<content::NavigationEntry> entry2( |
687 content::NavigationEntry::Create()); | 668 content::NavigationEntry::Create()); |
688 entry2->SetVirtualURL(GURL("http://www.noodle.com")); | 669 entry2->SetVirtualURL(GURL("http://www.noodle.com")); |
689 scoped_ptr<content::NavigationEntry> entry3( | 670 scoped_ptr<content::NavigationEntry> entry3( |
690 content::NavigationEntry::Create()); | 671 content::NavigationEntry::Create()); |
691 entry3->SetVirtualURL(GURL("http://www.doodle.com")); | 672 entry3->SetVirtualURL(GURL("http://www.doodle.com")); |
692 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillRepeatedly(Return(2)); | 673 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillRepeatedly(Return(2)); |
693 EXPECT_CALL(tab_mock, GetEntryAtIndex(0)).WillRepeatedly( | 674 EXPECT_CALL(tab_mock, GetEntryAtIndex(0)).WillRepeatedly( |
694 Return(entry1.get())); | 675 Return(entry1.get())); |
695 EXPECT_CALL(tab_mock, GetEntryAtIndex(1)).WillRepeatedly( | 676 EXPECT_CALL(tab_mock, GetEntryAtIndex(1)).WillRepeatedly( |
696 Return(entry2.get())); | 677 Return(entry2.get())); |
697 EXPECT_CALL(tab_mock, GetEntryAtIndex(2)).WillRepeatedly( | 678 EXPECT_CALL(tab_mock, GetEntryAtIndex(2)).WillRepeatedly( |
698 Return(entry3.get())); | 679 Return(entry3.get())); |
699 EXPECT_CALL(tab_mock, GetEntryCount()).WillRepeatedly(Return(3)); | 680 EXPECT_CALL(tab_mock, GetEntryCount()).WillRepeatedly(Return(3)); |
700 EXPECT_CALL(tab_mock, GetPendingEntryIndex()).WillRepeatedly(Return(-1)); | 681 EXPECT_CALL(tab_mock, GetPendingEntryIndex()).WillRepeatedly(Return(-1)); |
701 | 682 |
702 // This tab is new, so prev_tab is the default SyncedSessionTab object. | 683 // The initial UpdateSessionTabFromDelegate call builds the session_tab. |
703 SessionTab prev_tab; | 684 SessionTab session_tab; |
704 prev_tab.tab_id.set_id(0); | 685 UpdateSessionTabFromDelegate(tab_mock, kTime1, kTime2, &session_tab); |
705 | |
706 // The initial AssociateTabContents call builds the prev_tab. | |
707 sync_pb::SessionTab sync_tab; | |
708 GURL new_url; | |
709 AssociateTabContents(window_mock, tab_mock, &prev_tab, &sync_tab, &new_url); | |
710 | |
711 ASSERT_EQ(3u, prev_tab.navigations.size()); | |
712 | 686 |
713 // Add a new entry and change the current navigation index. | 687 // Add a new entry and change the current navigation index. |
714 scoped_ptr<content::NavigationEntry> entry4( | 688 scoped_ptr<content::NavigationEntry> entry4( |
715 content::NavigationEntry::Create()); | 689 content::NavigationEntry::Create()); |
716 entry4->SetVirtualURL(GURL("http://www.poodle.com")); | 690 entry4->SetVirtualURL(GURL("http://www.poodle.com")); |
717 EXPECT_CALL(tab_mock, GetEntryAtIndex(3)).WillRepeatedly( | 691 EXPECT_CALL(tab_mock, GetEntryAtIndex(3)).WillRepeatedly( |
718 Return(entry4.get())); | 692 Return(entry4.get())); |
719 EXPECT_CALL(tab_mock, GetEntryCount()).WillRepeatedly(Return(4)); | 693 EXPECT_CALL(tab_mock, GetEntryCount()).WillRepeatedly(Return(4)); |
720 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillRepeatedly(Return(3)); | 694 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillRepeatedly(Return(3)); |
721 | 695 |
722 // The new entry should have a timestamp later than this. | 696 // Now re-associate with the new version. |
723 int64 now = syncer::TimeToProtoTime(base::Time::Now()); | 697 UpdateSessionTabFromDelegate(tab_mock, kTime3, kTime4, &session_tab); |
724 | 698 |
725 // Now re-associate with the new version. | 699 ASSERT_EQ(4u, session_tab.navigations.size()); |
726 AssociateTabContents(window_mock, tab_mock, &prev_tab, &sync_tab, &new_url); | 700 EXPECT_EQ(entry1->GetVirtualURL(), |
727 | 701 session_tab.navigations[0].virtual_url()); |
728 EXPECT_EQ(new_url, entry4->GetVirtualURL()); | 702 EXPECT_EQ(entry2->GetVirtualURL(), |
729 ASSERT_EQ(4, sync_tab.navigation_size()); | 703 session_tab.navigations[1].virtual_url()); |
730 EXPECT_EQ(entry1->GetVirtualURL().spec(), | 704 EXPECT_EQ(entry3->GetVirtualURL(), |
731 sync_tab.navigation(0).virtual_url()); | 705 session_tab.navigations[2].virtual_url()); |
732 EXPECT_EQ(entry2->GetVirtualURL().spec(), | 706 EXPECT_EQ(entry4->GetVirtualURL(), |
733 sync_tab.navigation(1).virtual_url()); | 707 session_tab.navigations[3].virtual_url()); |
734 EXPECT_EQ(entry3->GetVirtualURL().spec(), | 708 EXPECT_EQ(3, session_tab.current_navigation_index); |
735 sync_tab.navigation(2).virtual_url()); | 709 EXPECT_TRUE(session_tab.navigations[0].timestamp().is_null()); |
736 EXPECT_EQ(entry4->GetVirtualURL().spec(), | 710 EXPECT_TRUE(session_tab.navigations[1].timestamp().is_null()); |
737 sync_tab.navigation(3).virtual_url()); | 711 EXPECT_EQ(kTime2, session_tab.navigations[2].timestamp()); |
738 EXPECT_EQ(3, sync_tab.current_navigation_index()); | 712 EXPECT_EQ(kTime4, session_tab.navigations[3].timestamp()); |
739 EXPECT_EQ(syncer::TimeToProtoTime(prev_tab.navigations[0].timestamp()), | |
740 sync_tab.navigation(0).timestamp()); | |
741 EXPECT_EQ(syncer::TimeToProtoTime(prev_tab.navigations[1].timestamp()), | |
742 sync_tab.navigation(1).timestamp()); | |
743 EXPECT_EQ(syncer::TimeToProtoTime(prev_tab.navigations[2].timestamp()), | |
744 sync_tab.navigation(2).timestamp()); | |
745 EXPECT_LE(now, sync_tab.navigation(3).timestamp()); | |
746 EXPECT_EQ(4U, prev_tab.navigations.size()); | |
747 } | 713 } |
748 | 714 |
749 // We shouldn't get confused when old/new entries from the previous tab have | 715 // We shouldn't get confused when old/new entries from the previous tab have |
750 // been pruned in the new tab. Timestamps for old entries we move back to in the | 716 // been pruned in the new tab. Timestamps for old entries we move back to in the |
751 // navigation stack should be refreshed. | 717 // navigation stack should be refreshed. |
752 TEST_F(SyncSessionModelAssociatorTest, AssociatePrunedTab) { | 718 TEST_F(SyncSessionModelAssociatorTest, UpdatePrunedTab) { |
753 NiceMock<SyncedWindowDelegateMock> window_mock; | |
754 EXPECT_CALL(window_mock, IsTabPinned(_)).WillRepeatedly(Return(false)); | |
755 | |
756 // Create a tab with four valid entries. | 719 // Create a tab with four valid entries. |
757 NiceMock<SyncedTabDelegateMock> tab_mock; | 720 NiceMock<SyncedTabDelegateMock> tab_mock; |
758 EXPECT_CALL(tab_mock, GetSessionId()).WillRepeatedly(Return(0)); | 721 EXPECT_CALL(tab_mock, GetSessionId()).WillRepeatedly(Return(0)); |
759 scoped_ptr<content::NavigationEntry> entry1( | 722 scoped_ptr<content::NavigationEntry> entry1( |
760 content::NavigationEntry::Create()); | 723 content::NavigationEntry::Create()); |
761 entry1->SetVirtualURL(GURL("http://www.google.com")); | 724 entry1->SetVirtualURL(GURL("http://www.google.com")); |
762 scoped_ptr<content::NavigationEntry> entry2( | 725 scoped_ptr<content::NavigationEntry> entry2( |
763 content::NavigationEntry::Create()); | 726 content::NavigationEntry::Create()); |
764 entry2->SetVirtualURL(GURL("http://www.noodle.com")); | 727 entry2->SetVirtualURL(GURL("http://www.noodle.com")); |
765 scoped_ptr<content::NavigationEntry> entry3( | 728 scoped_ptr<content::NavigationEntry> entry3( |
766 content::NavigationEntry::Create()); | 729 content::NavigationEntry::Create()); |
767 entry3->SetVirtualURL(GURL("http://www.doodle.com")); | 730 entry3->SetVirtualURL(GURL("http://www.doodle.com")); |
768 scoped_ptr<content::NavigationEntry> entry4( | 731 scoped_ptr<content::NavigationEntry> entry4( |
769 content::NavigationEntry::Create()); | 732 content::NavigationEntry::Create()); |
770 entry4->SetVirtualURL(GURL("http://www.poodle.com")); | 733 entry4->SetVirtualURL(GURL("http://www.poodle.com")); |
771 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillRepeatedly(Return(3)); | 734 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillRepeatedly(Return(3)); |
772 EXPECT_CALL(tab_mock, GetEntryAtIndex(0)).WillRepeatedly( | 735 EXPECT_CALL(tab_mock, GetEntryAtIndex(0)).WillRepeatedly( |
773 Return(entry1.get())); | 736 Return(entry1.get())); |
774 EXPECT_CALL(tab_mock, GetEntryAtIndex(1)).WillRepeatedly( | 737 EXPECT_CALL(tab_mock, GetEntryAtIndex(1)).WillRepeatedly( |
775 Return(entry2.get())); | 738 Return(entry2.get())); |
776 EXPECT_CALL(tab_mock, GetEntryAtIndex(2)).WillRepeatedly( | 739 EXPECT_CALL(tab_mock, GetEntryAtIndex(2)).WillRepeatedly( |
777 Return(entry3.get())); | 740 Return(entry3.get())); |
778 EXPECT_CALL(tab_mock, GetEntryAtIndex(3)).WillRepeatedly( | 741 EXPECT_CALL(tab_mock, GetEntryAtIndex(3)).WillRepeatedly( |
779 Return(entry4.get())); | 742 Return(entry4.get())); |
780 EXPECT_CALL(tab_mock, GetEntryCount()).WillRepeatedly(Return(4)); | 743 EXPECT_CALL(tab_mock, GetEntryCount()).WillRepeatedly(Return(4)); |
781 EXPECT_CALL(tab_mock, GetPendingEntryIndex()).WillRepeatedly(Return(-1)); | 744 EXPECT_CALL(tab_mock, GetPendingEntryIndex()).WillRepeatedly(Return(-1)); |
782 | 745 |
783 // This tab is new, so prev_tab is the default SyncedSessionTab object. | 746 // The initial UpdateSessionTabFromDelegate call builds the session_tab. |
784 SessionTab prev_tab; | 747 SessionTab session_tab; |
785 prev_tab.tab_id.set_id(0); | 748 UpdateSessionTabFromDelegate(tab_mock, kTime1, kTime2, &session_tab); |
786 | |
787 // The initial AssociateTabContents call builds the prev_tab. | |
788 sync_pb::SessionTab sync_tab; | |
789 GURL new_url; | |
790 AssociateTabContents(window_mock, tab_mock, &prev_tab, &sync_tab, &new_url); | |
791 | |
792 ASSERT_EQ(4u, prev_tab.navigations.size()); | |
793 | 749 |
794 // Reset new tab to have the oldest entry pruned, the current navigation | 750 // Reset new tab to have the oldest entry pruned, the current navigation |
795 // set to entry3, and a new entry added in place of entry4. | 751 // set to entry3, and a new entry added in place of entry4. |
796 testing::Mock::VerifyAndClearExpectations(&tab_mock); | 752 testing::Mock::VerifyAndClearExpectations(&tab_mock); |
797 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillRepeatedly(Return(1)); | 753 EXPECT_CALL(tab_mock, GetCurrentEntryIndex()).WillRepeatedly(Return(1)); |
798 EXPECT_CALL(tab_mock, GetEntryAtIndex(0)).WillRepeatedly( | 754 EXPECT_CALL(tab_mock, GetEntryAtIndex(0)).WillRepeatedly( |
799 Return(entry2.get())); | 755 Return(entry2.get())); |
800 EXPECT_CALL(tab_mock, GetEntryAtIndex(1)).WillRepeatedly( | 756 EXPECT_CALL(tab_mock, GetEntryAtIndex(1)).WillRepeatedly( |
801 Return(entry3.get())); | 757 Return(entry3.get())); |
802 scoped_ptr<content::NavigationEntry> entry5( | 758 scoped_ptr<content::NavigationEntry> entry5( |
803 content::NavigationEntry::Create()); | 759 content::NavigationEntry::Create()); |
804 entry5->SetVirtualURL(GURL("http://www.noogle.com")); | 760 entry5->SetVirtualURL(GURL("http://www.noogle.com")); |
805 EXPECT_CALL(tab_mock, GetEntryAtIndex(2)).WillRepeatedly( | 761 EXPECT_CALL(tab_mock, GetEntryAtIndex(2)).WillRepeatedly( |
806 Return(entry5.get())); | 762 Return(entry5.get())); |
807 EXPECT_CALL(tab_mock, GetEntryCount()).WillRepeatedly(Return(3)); | 763 EXPECT_CALL(tab_mock, GetEntryCount()).WillRepeatedly(Return(3)); |
808 EXPECT_CALL(tab_mock, GetPendingEntryIndex()).WillRepeatedly(Return(-1)); | 764 EXPECT_CALL(tab_mock, GetPendingEntryIndex()).WillRepeatedly(Return(-1)); |
809 | 765 |
810 // The new entry should have a timestamp later than this. | 766 // Tweak the timestamps a bit. |
811 int64 now = syncer::TimeToProtoTime(base::Time::Now()); | 767 ASSERT_EQ(4u, session_tab.navigations.size()); |
| 768 SessionTypesTestHelper::SetTimestamp(&session_tab.navigations[0], kTime3); |
| 769 SessionTypesTestHelper::SetTimestamp(&session_tab.navigations[1], kTime4); |
| 770 SessionTypesTestHelper::SetTimestamp(&session_tab.navigations[2], kTime5); |
| 771 SessionTypesTestHelper::SetTimestamp(&session_tab.navigations[3], kTime6); |
812 | 772 |
813 // Now re-associate with the new version. | 773 // Now re-associate with the new version. |
814 AssociateTabContents(window_mock, tab_mock, &prev_tab, &sync_tab, &new_url); | 774 UpdateSessionTabFromDelegate(tab_mock, kTime7, kTime8, &session_tab); |
815 | 775 |
816 // Only entry2's timestamp should be preserved. The new entry should have a | 776 // Only entry2's and entry3's timestamps should be preserved. The new |
817 // new timestamp. | 777 // entry should have a new timestamp. |
818 EXPECT_EQ(new_url, entry3->GetVirtualURL()); | 778 ASSERT_EQ(3u, session_tab.navigations.size()); |
819 ASSERT_EQ(3, sync_tab.navigation_size()); | 779 EXPECT_EQ(entry2->GetVirtualURL(), |
820 EXPECT_EQ(entry2->GetVirtualURL().spec(), | 780 session_tab.navigations[0].virtual_url()); |
821 sync_tab.navigation(0).virtual_url()); | 781 EXPECT_EQ(entry3->GetVirtualURL(), |
822 EXPECT_EQ(entry3->GetVirtualURL().spec(), | 782 session_tab.navigations[1].virtual_url()); |
823 sync_tab.navigation(1).virtual_url()); | 783 EXPECT_EQ(entry5->GetVirtualURL(), |
824 EXPECT_EQ(entry5->GetVirtualURL().spec(), | 784 session_tab.navigations[2].virtual_url()); |
825 sync_tab.navigation(2).virtual_url()); | 785 EXPECT_EQ(1, session_tab.current_navigation_index); |
826 EXPECT_EQ(1, sync_tab.current_navigation_index()); | 786 EXPECT_EQ(kTime4, session_tab.navigations[0].timestamp()); |
827 EXPECT_EQ(syncer::TimeToProtoTime(prev_tab.navigations[0].timestamp()), | 787 EXPECT_EQ(kTime5, session_tab.navigations[1].timestamp()); |
828 sync_tab.navigation(0).timestamp()); | 788 EXPECT_EQ(kTime8, session_tab.navigations[2].timestamp()); |
829 EXPECT_LE(now, sync_tab.navigation(1).timestamp()); | |
830 EXPECT_LE(now, sync_tab.navigation(2).timestamp()); | |
831 EXPECT_EQ(3U, prev_tab.navigations.size()); | |
832 } | 789 } |
833 | 790 |
| 791 } // namespace |
| 792 |
834 } // namespace browser_sync | 793 } // namespace browser_sync |
OLD | NEW |