Upstream version 10.39.225.0
[platform/framework/web/crosswalk.git] / src / chrome / browser / sync / test / integration / single_client_backup_rollback_test.cc
1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "base/command_line.h"
6 #include "base/files/file_util.h"
7 #include "base/message_loop/message_loop.h"
8 #include "base/prefs/pref_service.h"
9 #include "base/run_loop.h"
10 #include "base/test/test_timeouts.h"
11 #include "chrome/browser/browsing_data/browsing_data_remover.h"
12 #include "chrome/browser/profiles/profile.h"
13 #include "chrome/browser/sync/profile_sync_service.h"
14 #include "chrome/browser/sync/test/integration/bookmarks_helper.h"
15 #include "chrome/browser/sync/test/integration/preferences_helper.h"
16 #include "chrome/browser/sync/test/integration/sync_integration_test_util.h"
17 #include "chrome/browser/sync/test/integration/sync_test.h"
18 #include "chrome/common/chrome_switches.h"
19 #include "chrome/common/pref_names.h"
20 #include "components/bookmarks/browser/bookmark_model.h"
21 #include "sync/internal_api/public/util/sync_db_util.h"
22 #include "sync/test/fake_server/fake_server_verifier.h"
23 #include "sync/util/time.h"
24
25 using bookmarks_helper::AddFolder;
26 using bookmarks_helper::AddURL;
27 using bookmarks_helper::GetOtherNode;
28 using bookmarks_helper::ModelMatchesVerifier;
29 using bookmarks_helper::Move;
30 using bookmarks_helper::Remove;
31 using sync_integration_test_util::AwaitCommitActivityCompletion;
32
33 namespace {
34 const char kUrl1[] = "http://www.google.com";
35 const char kUrl2[] = "http://map.google.com";
36 const char kUrl3[] = "http://plus.google.com";
37 }  // anonymous namespace
38
39 class SingleClientBackupRollbackTest : public SyncTest {
40  public:
41   SingleClientBackupRollbackTest() : SyncTest(SINGLE_CLIENT) {}
42   virtual ~SingleClientBackupRollbackTest() {}
43
44   void DisableBackup() {
45     CommandLine::ForCurrentProcess()->AppendSwitch(
46           switches::kSyncDisableBackup);
47   }
48
49   void DisableRollback() {
50     CommandLine::ForCurrentProcess()->AppendSwitch(
51           switches::kSyncDisableRollback);
52   }
53
54   base::Time GetBackupDbLastModified() {
55     base::RunLoop run_loop;
56
57     base::Time backup_time;
58     syncer::CheckSyncDbLastModifiedTime(
59         GetProfile(0)->GetPath().Append(FILE_PATH_LITERAL("Sync Data Backup")),
60         base::MessageLoopProxy::current(),
61         base::Bind(&SingleClientBackupRollbackTest::CheckDbCallback,
62                    base::Unretained(this), &backup_time));
63     base::MessageLoopProxy::current()->PostTask(
64         FROM_HERE, run_loop.QuitClosure());
65     run_loop.Run();
66     return backup_time;
67   }
68
69  private:
70   void CheckDbCallback(base::Time* time_out, base::Time time_in) {
71     *time_out = syncer::ProtoTimeToTime(syncer::TimeToProtoTime(time_in));
72   }
73
74   DISALLOW_COPY_AND_ASSIGN(SingleClientBackupRollbackTest);
75 };
76
77 // Waits until the ProfileSyncService's backend is in IDLE mode.
78 class SyncBackendStoppedChecker : public ProfileSyncServiceBase::Observer {
79  public:
80   explicit SyncBackendStoppedChecker(ProfileSyncService* service)
81       : pss_(service),
82         timeout_(TestTimeouts::action_max_timeout()),
83         done_(false) {}
84
85   virtual void OnStateChanged() OVERRIDE {
86     if (ProfileSyncService::IDLE == pss_->backend_mode()) {
87       done_ = true;
88       run_loop_.Quit();
89     }
90   }
91
92   bool Wait() {
93     pss_->AddObserver(this);
94     if (ProfileSyncService::IDLE == pss_->backend_mode())
95       return true;
96     base::MessageLoop::current()->PostDelayedTask(
97         FROM_HERE,
98         run_loop_.QuitClosure(),
99         timeout_);
100     run_loop_.Run();
101     pss_->RemoveObserver(this);
102     return done_;
103   }
104
105  private:
106
107   ProfileSyncService* const pss_;
108   const base::TimeDelta timeout_;
109   base::RunLoop run_loop_;
110   bool done_;
111 };
112
113 // Waits until a rollback finishes.
114 class SyncRollbackChecker : public ProfileSyncServiceBase::Observer,
115                             public BrowsingDataRemover::Observer {
116  public:
117   explicit SyncRollbackChecker(ProfileSyncService* service)
118       : pss_(service),
119         timeout_(TestTimeouts::action_max_timeout()),
120         rollback_started_(false),
121         clear_done_(false) {}
122
123   // ProfileSyncServiceBase::Observer implementation.
124   virtual void OnStateChanged() OVERRIDE {
125     if (ProfileSyncService::ROLLBACK == pss_->backend_mode()) {
126       rollback_started_ = true;
127       if (clear_done_)
128         run_loop_.Quit();
129     }
130   }
131
132   // BrowsingDataRemoverObserver::Observer implementation.
133   virtual void OnBrowsingDataRemoverDone() OVERRIDE {
134     clear_done_ = true;
135     if (rollback_started_) {
136       run_loop_.Quit();
137     }
138   }
139
140   bool Wait() {
141     pss_->AddObserver(this);
142     pss_->SetBrowsingDataRemoverObserverForTesting(this);
143     base::MessageLoop::current()->PostDelayedTask(
144         FROM_HERE,
145         run_loop_.QuitClosure(),
146         timeout_);
147     run_loop_.Run();
148     pss_->RemoveObserver(this);
149     return rollback_started_ && clear_done_;
150   }
151
152   ProfileSyncService* const pss_;
153   const base::TimeDelta timeout_;
154   base::RunLoop run_loop_;
155   bool rollback_started_;
156   bool clear_done_;
157 };
158
159 #if defined(ENABLE_PRE_SYNC_BACKUP)
160 #define MAYBE_TestBackup TestBackup
161 #else
162 #define MAYBE_TestBackup DISABLED_TestBackup
163 #endif
164 IN_PROC_BROWSER_TEST_F(SingleClientBackupRollbackTest,
165                        MAYBE_TestBackup) {
166   ASSERT_TRUE(SetupClients()) << "SetupClients() failed.";
167
168   // Setup sync, wait for its completion, and make sure changes were synced.
169   ASSERT_TRUE(SetupSync()) << "SetupSync() failed.";
170   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService(0)));
171   ASSERT_TRUE(ModelMatchesVerifier(0));
172
173   // Verify backup DB is created and backup time is set on device info.
174   base::Time backup_time = GetBackupDbLastModified();
175   ASSERT_FALSE(backup_time.is_null());
176   ASSERT_EQ(backup_time, GetSyncService(0)->GetDeviceBackupTimeForTesting());
177 }
178
179 #if defined(ENABLE_PRE_SYNC_BACKUP)
180 #define MAYBE_TestBackupDisabled TestBackupDisabled
181 #else
182 #define MAYBE_TestBackupDisabled DISABLED_TestBackupDisabled
183 #endif
184 IN_PROC_BROWSER_TEST_F(SingleClientBackupRollbackTest,
185                        MAYBE_TestBackupDisabled) {
186   DisableBackup();
187
188   // Setup sync, wait for its completion, and make sure changes were synced.
189   ASSERT_TRUE(SetupSync()) << "SetupSync() failed.";
190   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService(0)));
191   ASSERT_TRUE(ModelMatchesVerifier(0));
192
193   // Verify backup DB is not created and backup time is not set on device info.
194   ASSERT_FALSE(base::PathExists(
195       GetProfile(0)->GetPath().Append(FILE_PATH_LITERAL("Sync Data Backup"))));
196   ASSERT_TRUE(GetSyncService(0)->GetDeviceBackupTimeForTesting().is_null());
197 }
198
199 #if defined(ENABLE_PRE_SYNC_BACKUP)
200 #define MAYBE_TestRollback TestRollback
201 #else
202 #define MAYBE_TestRollback DISABLED_TestRollback
203 #endif
204 IN_PROC_BROWSER_TEST_F(SingleClientBackupRollbackTest,
205                        MAYBE_TestRollback) {
206   ASSERT_TRUE(SetupClients()) << "SetupClients() failed.";
207
208   // Starting state:
209   // other_node
210   //    -> top
211   //      -> tier1_a
212   //        -> http://mail.google.com  "tier1_a_url0"
213   //      -> tier1_b
214   //        -> http://www.nhl.com "tier1_b_url0"
215   const BookmarkNode* top = AddFolder(0, GetOtherNode(0), 0, "top");
216   const BookmarkNode* tier1_a = AddFolder(0, top, 0, "tier1_a");
217   const BookmarkNode* tier1_b = AddFolder(0, top, 1, "tier1_b");
218   ASSERT_TRUE(AddURL(0, tier1_a, 0, "tier1_a_url0",
219                      GURL("http://mail.google.com")));
220   ASSERT_TRUE(AddURL(0, tier1_b, 0, "tier1_b_url0",
221                      GURL("http://www.nhl.com")));
222
223   // Setup sync, wait for its completion, and make sure changes were synced.
224   ASSERT_TRUE(SetupSync()) << "SetupSync() failed.";
225   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService(0)));
226   ASSERT_TRUE(ModelMatchesVerifier(0));
227
228   // Made bookmark changes while sync is on.
229   Move(0, tier1_a->GetChild(0), tier1_b, 1);
230   Remove(0, tier1_b, 0);
231   ASSERT_TRUE(AddFolder(0, tier1_b, 1, "tier2_c"));
232   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService(0)));
233   ASSERT_TRUE(ModelMatchesVerifier(0));
234
235   // Let server to return rollback command on next sync request.
236   GetFakeServer()->TriggerError(sync_pb::SyncEnums::USER_ROLLBACK);
237
238   // Make another change to trigger downloading of rollback command.
239   Remove(0, tier1_b, 0);
240
241   // Wait for rollback to finish and sync backend is completely shut down.
242   SyncRollbackChecker rollback_checker(GetSyncService(0));
243   ASSERT_TRUE(rollback_checker.Wait());
244   SyncBackendStoppedChecker shutdown_checker(GetSyncService(0));
245   ASSERT_TRUE(shutdown_checker.Wait());
246
247   // Verify bookmarks are restored.
248   ASSERT_EQ(1, tier1_a->child_count());
249   const BookmarkNode* url1 = tier1_a->GetChild(0);
250   ASSERT_EQ(GURL("http://mail.google.com"), url1->url());
251
252   ASSERT_EQ(1, tier1_b->child_count());
253   const BookmarkNode* url2 = tier1_b->GetChild(0);
254   ASSERT_EQ(GURL("http://www.nhl.com"), url2->url());
255 }
256
257 #if defined(ENABLE_PRE_SYNC_BACKUP)
258 #define MAYBE_TestRollbackDisabled TestRollbackDisabled
259 #else
260 #define MAYBE_TestRollbackDisabled DISABLED_TestRollbackDisabled
261 #endif
262 IN_PROC_BROWSER_TEST_F(SingleClientBackupRollbackTest,
263                        MAYBE_TestRollbackDisabled) {
264   DisableRollback();
265
266   ASSERT_TRUE(SetupClients()) << "SetupClients() failed.";
267
268   // Starting state:
269   // other_node
270   //    -> http://mail.google.com  "url0"
271   //    -> http://www.nhl.com "url1"
272   ASSERT_TRUE(AddURL(0, GetOtherNode(0), 0, "url0",
273                      GURL("http://mail.google.com")));
274   ASSERT_TRUE(AddURL(0, GetOtherNode(0), 1, "url1",
275                      GURL("http://www.nhl.com")));
276
277   // Setup sync, wait for its completion, and make sure changes were synced.
278   ASSERT_TRUE(SetupSync()) << "SetupSync() failed.";
279   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService(0)));
280   ASSERT_TRUE(ModelMatchesVerifier(0));
281
282   // Made bookmark changes while sync is on.
283   Remove(0, GetOtherNode(0), 1);
284   ASSERT_TRUE(AddURL(0, GetOtherNode(0), 1, "url2",
285                      GURL("http://www.yahoo.com")));
286   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService((0))));
287   ASSERT_TRUE(ModelMatchesVerifier(0));
288
289   // Let server to return rollback command on next sync request.
290   GetFakeServer()->TriggerError(sync_pb::SyncEnums::USER_ROLLBACK);
291
292   // Make another change to trigger downloading of rollback command.
293   Remove(0, GetOtherNode(0), 0);
294
295   // Wait for sync backend is completely shut down.
296   SyncBackendStoppedChecker shutdown_checker(GetSyncService(0));
297   ASSERT_TRUE(shutdown_checker.Wait());
298
299   // With rollback disabled, bookmarks in backup DB should not be restored.
300   // Only bookmark added during sync is present.
301   ASSERT_EQ(1, GetOtherNode(0)->child_count());
302   ASSERT_EQ(GURL("http://www.yahoo.com"),
303             GetOtherNode(0)->GetChild(0)->url());
304 }
305
306 #if defined(ENABLE_PRE_SYNC_BACKUP)
307 #define MAYBE_TestSyncDisabled TestSyncDisabled
308 #else
309 #define MAYBE_TestSyncDisabled DISABLED_TestSyncDisabled
310 #endif
311 IN_PROC_BROWSER_TEST_F(SingleClientBackupRollbackTest,
312                        MAYBE_TestSyncDisabled) {
313   ASSERT_TRUE(SetupClients()) << "SetupClients() failed.";
314
315   // Starting state:
316   // other_node
317   //    -> http://mail.google.com  "url0"
318   //    -> http://www.nhl.com "url1"
319   ASSERT_TRUE(AddURL(0, GetOtherNode(0), 0, "url0",
320                      GURL("http://mail.google.com")));
321   ASSERT_TRUE(AddURL(0, GetOtherNode(0), 1, "url1",
322                      GURL("http://www.nhl.com")));
323
324   // Setup sync, wait for its completion, and make sure changes were synced.
325   ASSERT_TRUE(SetupSync()) << "SetupSync() failed.";
326   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService(0)));
327   ASSERT_TRUE(ModelMatchesVerifier(0));
328
329   // Made bookmark changes while sync is on.
330   Remove(0, GetOtherNode(0), 1);
331   ASSERT_TRUE(AddURL(0, GetOtherNode(0), 1, "url2",
332                      GURL("http://www.yahoo.com")));
333   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService((0))));
334   ASSERT_TRUE(ModelMatchesVerifier(0));
335
336   // Let server to return birthday error on next sync request.
337   GetFakeServer()->TriggerError(sync_pb::SyncEnums::NOT_MY_BIRTHDAY);
338
339   // Make another change to trigger downloading of rollback command.
340   Remove(0, GetOtherNode(0), 0);
341
342   // Wait sync backend is completely shut down.
343   SyncBackendStoppedChecker shutdown_checker(GetSyncService(0));
344   ASSERT_TRUE(shutdown_checker.Wait());
345
346   // Shouldn't restore bookmarks with sign-out only.
347   ASSERT_EQ(1, GetOtherNode(0)->child_count());
348   ASSERT_EQ(GURL("http://www.yahoo.com"),
349             GetOtherNode(0)->GetChild(0)->url());
350 }
351
352 #if defined(ENABLE_PRE_SYNC_BACKUP)
353 #define MAYBE_RollbackNoBackup RollbackNoBackup
354 #else
355 #define MAYBE_RollbackNoBackup DISABLED_RollbackNoBackup
356 #endif
357 IN_PROC_BROWSER_TEST_F(SingleClientBackupRollbackTest,
358                        MAYBE_RollbackNoBackup) {
359   ASSERT_TRUE(SetupClients()) << "SetupClients() failed.";
360
361   // Starting state:
362   // other_node
363   //    -> http://mail.google.com  "url0"
364   //    -> http://www.nhl.com "url1"
365   ASSERT_TRUE(AddURL(0, GetOtherNode(0), 0, "url0",
366                      GURL("http://mail.google.com")));
367
368   // Setup sync, wait for its completion, and make sure changes were synced.
369   ASSERT_TRUE(SetupSync()) << "SetupSync() failed.";
370   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService((0))));
371   ASSERT_TRUE(ModelMatchesVerifier(0));
372
373   ASSERT_TRUE(AddURL(0, GetOtherNode(0), 1, "url1",
374                      GURL("http://www.nhl.com")));
375
376   // Delete backup DB.
377   base::DeleteFile(
378       GetProfile(0)->GetPath().Append(FILE_PATH_LITERAL("Sync Data Backup")),
379       true);
380
381   // Let server to return rollback command on next sync request.
382   GetFakeServer()->TriggerError(sync_pb::SyncEnums::USER_ROLLBACK);
383
384   // Make another change to trigger downloading of rollback command.
385   Remove(0, GetOtherNode(0), 0);
386
387   // Wait for rollback to finish and sync backend is completely shut down.
388   SyncRollbackChecker rollback_checker(GetSyncService(0));
389   ASSERT_TRUE(rollback_checker.Wait());
390   SyncBackendStoppedChecker checker(GetSyncService(0));
391   ASSERT_TRUE(checker.Wait());
392
393   // Without backup DB, bookmarks remain at the state when sync stops.
394   ASSERT_EQ(1, GetOtherNode(0)->child_count());
395   ASSERT_EQ(GURL("http://www.nhl.com"),
396             GetOtherNode(0)->GetChild(0)->url());
397 }
398
399 #if defined(ENABLE_PRE_SYNC_BACKUP)
400 #define MAYBE_DontChangeBookmarkOrdering DontChangeBookmarkOrdering
401 #else
402 #define MAYBE_DontChangeBookmarkOrdering DISABLED_DontChangeBookmarkOrdering
403 #endif
404 IN_PROC_BROWSER_TEST_F(SingleClientBackupRollbackTest,
405                        MAYBE_DontChangeBookmarkOrdering) {
406   ASSERT_TRUE(SetupClients()) << "SetupClients() failed.";
407
408   const BookmarkNode* sub_folder = AddFolder(0, GetOtherNode(0), 0, "test");
409   ASSERT_TRUE(AddURL(0, sub_folder, 0, "", GURL(kUrl1)));
410   ASSERT_TRUE(AddURL(0, sub_folder, 1, "", GURL(kUrl2)));
411   ASSERT_TRUE(AddURL(0, sub_folder, 2, "", GURL(kUrl3)));
412
413   // Setup sync, wait for its completion, and make sure changes were synced.
414   ASSERT_TRUE(SetupSync()) << "SetupSync() failed.";
415   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService(0)));
416   ASSERT_TRUE(ModelMatchesVerifier(0));
417
418   // Made bookmark changes while sync is on.
419   Remove(0, sub_folder, 0);
420   Remove(0, sub_folder, 0);
421   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService(0)));
422   ASSERT_TRUE(ModelMatchesVerifier(0));
423
424   // Let server to return rollback command on next sync request.
425   GetFakeServer()->TriggerError(sync_pb::SyncEnums::USER_ROLLBACK);
426
427   // Make another change to trigger downloading of rollback command.
428   Remove(0, sub_folder, 0);
429
430   // Wait for rollback to finish and sync backend is completely shut down.
431   SyncRollbackChecker rollback_checker(GetSyncService(0));
432   ASSERT_TRUE(rollback_checker.Wait());
433   SyncBackendStoppedChecker shutdown_checker(GetSyncService(0));
434   ASSERT_TRUE(shutdown_checker.Wait());
435
436   // Verify bookmarks are unchanged.
437   ASSERT_EQ(3, sub_folder->child_count());
438   ASSERT_EQ(GURL(kUrl1), sub_folder->GetChild(0)->url());
439   ASSERT_EQ(GURL(kUrl2), sub_folder->GetChild(1)->url());
440   ASSERT_EQ(GURL(kUrl3), sub_folder->GetChild(2)->url());
441 }