Home | History | Annotate | Download | only in integration
      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
      3 // found in the LICENSE file.
      4 
      5 #include "base/prefs/pref_member.h"
      6 #include "base/prefs/pref_service.h"
      7 #include "chrome/browser/sync/profile_sync_service.h"
      8 #include "chrome/browser/sync/test/integration/bookmarks_helper.h"
      9 #include "chrome/browser/sync/test/integration/passwords_helper.h"
     10 #include "chrome/browser/sync/test/integration/profile_sync_service_harness.h"
     11 #include "chrome/browser/sync/test/integration/single_client_status_change_checker.h"
     12 #include "chrome/browser/sync/test/integration/sync_integration_test_util.h"
     13 #include "chrome/browser/sync/test/integration/sync_test.h"
     14 #include "chrome/common/pref_names.h"
     15 #include "google_apis/gaia/google_service_auth_error.h"
     16 #include "sync/protocol/sync_protocol_error.h"
     17 
     18 using bookmarks_helper::AddFolder;
     19 using bookmarks_helper::SetTitle;
     20 using sync_integration_test_util::AwaitCommitActivityCompletion;
     21 
     22 namespace {
     23 
     24 class SyncDisabledChecker : public SingleClientStatusChangeChecker {
     25  public:
     26   explicit SyncDisabledChecker(ProfileSyncService* service)
     27       : SingleClientStatusChangeChecker(service) {}
     28 
     29   virtual bool IsExitConditionSatisfied() OVERRIDE {
     30     return !service()->setup_in_progress() &&
     31            !service()->HasSyncSetupCompleted();
     32   }
     33 
     34   virtual std::string GetDebugMessage() const OVERRIDE {
     35     return "Sync Disabled";
     36   }
     37 };
     38 
     39 bool AwaitSyncDisabled(ProfileSyncService* service) {
     40   SyncDisabledChecker checker(service);
     41   checker.Wait();
     42   return !checker.TimedOut();
     43 }
     44 
     45 class SyncErrorTest : public SyncTest {
     46  public:
     47   SyncErrorTest() : SyncTest(SINGLE_CLIENT) {}
     48   virtual ~SyncErrorTest() {}
     49 
     50  private:
     51   DISALLOW_COPY_AND_ASSIGN(SyncErrorTest);
     52 };
     53 
     54 // TODO(pvalenzuela): Remove this class when all tests here are converted to
     55 // use FakeServer.
     56 class LegacySyncErrorTest : public SyncTest {
     57  public:
     58   LegacySyncErrorTest() : SyncTest(SINGLE_CLIENT_LEGACY) {}
     59   virtual ~LegacySyncErrorTest() {}
     60 
     61  private:
     62   DISALLOW_COPY_AND_ASSIGN(LegacySyncErrorTest);
     63 };
     64 
     65 // Helper class that waits until the sync engine has hit an actionable error.
     66 class ActionableErrorChecker : public SingleClientStatusChangeChecker {
     67  public:
     68   explicit ActionableErrorChecker(ProfileSyncService* service)
     69       : SingleClientStatusChangeChecker(service) {}
     70 
     71   virtual ~ActionableErrorChecker() {}
     72 
     73   // Checks if an actionable error has been hit. Called repeatedly each time PSS
     74   // notifies observers of a state change.
     75   virtual bool IsExitConditionSatisfied() OVERRIDE {
     76     ProfileSyncService::Status status;
     77     service()->QueryDetailedSyncStatus(&status);
     78     return (status.sync_protocol_error.action != syncer::UNKNOWN_ACTION &&
     79             service()->HasUnrecoverableError());
     80   }
     81 
     82   virtual std::string GetDebugMessage() const OVERRIDE {
     83     return "ActionableErrorChecker";
     84   }
     85 
     86  private:
     87   DISALLOW_COPY_AND_ASSIGN(ActionableErrorChecker);
     88 };
     89 
     90 IN_PROC_BROWSER_TEST_F(SyncErrorTest, BirthdayErrorTest) {
     91   ASSERT_TRUE(SetupSync()) << "SetupSync() failed.";
     92 
     93   // Add an item, wait for sync, and trigger a birthday error on the server.
     94   const BookmarkNode* node1 = AddFolder(0, 0, "title1");
     95   SetTitle(0, node1, "new_title1");
     96   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService((0))));
     97   ASSERT_TRUE(GetFakeServer()->SetNewStoreBirthday("new store birthday"));
     98 
     99   // Now make one more change so we will do another sync.
    100   const BookmarkNode* node2 = AddFolder(0, 0, "title2");
    101   SetTitle(0, node2, "new_title2");
    102   ASSERT_TRUE(AwaitSyncDisabled(GetSyncService((0))));
    103 }
    104 
    105 IN_PROC_BROWSER_TEST_F(LegacySyncErrorTest, ActionableErrorTest) {
    106   ASSERT_TRUE(SetupSync()) << "SetupSync() failed.";
    107 
    108   const BookmarkNode* node1 = AddFolder(0, 0, "title1");
    109   SetTitle(0, node1, "new_title1");
    110   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService((0))));
    111 
    112   syncer::SyncProtocolError protocol_error;
    113   protocol_error.error_type = syncer::TRANSIENT_ERROR;
    114   protocol_error.action = syncer::UPGRADE_CLIENT;
    115   protocol_error.error_description = "Not My Fault";
    116   protocol_error.url = "www.google.com";
    117   TriggerSyncError(protocol_error, SyncTest::ERROR_FREQUENCY_ALWAYS);
    118 
    119   // Now make one more change so we will do another sync.
    120   const BookmarkNode* node2 = AddFolder(0, 0, "title2");
    121   SetTitle(0, node2, "new_title2");
    122 
    123   // Wait until an actionable error is encountered.
    124   ActionableErrorChecker actionable_error_checker(GetSyncService((0)));
    125   actionable_error_checker.Wait();
    126   ASSERT_FALSE(actionable_error_checker.TimedOut());
    127 
    128   ProfileSyncService::Status status;
    129   GetSyncService((0))->QueryDetailedSyncStatus(&status);
    130   ASSERT_EQ(status.sync_protocol_error.error_type, protocol_error.error_type);
    131   ASSERT_EQ(status.sync_protocol_error.action, protocol_error.action);
    132   ASSERT_EQ(status.sync_protocol_error.url, protocol_error.url);
    133   ASSERT_EQ(status.sync_protocol_error.error_description,
    134       protocol_error.error_description);
    135 }
    136 
    137 // Disabled, http://crbug.com/351160 .
    138 IN_PROC_BROWSER_TEST_F(LegacySyncErrorTest, DISABLED_ErrorWhileSettingUp) {
    139   ASSERT_TRUE(SetupClients());
    140 
    141   syncer::SyncProtocolError protocol_error;
    142   protocol_error.error_type = syncer::TRANSIENT_ERROR;
    143   protocol_error.error_description = "Not My Fault";
    144   protocol_error.url = "www.google.com";
    145 
    146   if (GetSyncService(0)->auto_start_enabled()) {
    147     // In auto start enabled platforms like chrome os we should be
    148     // able to set up even if the first sync while setting up fails.
    149     // Trigger error on every 2 out of 3 requests.
    150     TriggerSyncError(protocol_error, SyncTest::ERROR_FREQUENCY_TWO_THIRDS);
    151     // Now setup sync and it should succeed.
    152     ASSERT_TRUE(SetupSync()) << "SetupSync() failed.";
    153   } else {
    154     // In Non auto start enabled environments if the setup sync fails then
    155     // the setup would fail. So setup sync normally.
    156     ASSERT_TRUE(SetupSync()) << "Setup sync failed";
    157     ASSERT_TRUE(GetClient(0)->DisableSyncForDatatype(syncer::AUTOFILL));
    158 
    159     // Trigger error on every 2 out of 3 requests.
    160     TriggerSyncError(protocol_error, SyncTest::ERROR_FREQUENCY_TWO_THIRDS);
    161 
    162     // Now enable a datatype, whose first 2 syncs would fail, but we should
    163     // recover and setup succesfully on the third attempt.
    164     ASSERT_TRUE(GetClient(0)->EnableSyncForDatatype(syncer::AUTOFILL));
    165   }
    166 }
    167 
    168 IN_PROC_BROWSER_TEST_F(LegacySyncErrorTest,
    169     BirthdayErrorUsingActionableErrorTest) {
    170   ASSERT_TRUE(SetupSync()) << "SetupSync() failed.";
    171 
    172   const BookmarkNode* node1 = AddFolder(0, 0, "title1");
    173   SetTitle(0, node1, "new_title1");
    174   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService((0))));
    175 
    176   syncer::SyncProtocolError protocol_error;
    177   protocol_error.error_type = syncer::NOT_MY_BIRTHDAY;
    178   protocol_error.action = syncer::DISABLE_SYNC_ON_CLIENT;
    179   protocol_error.error_description = "Not My Fault";
    180   protocol_error.url = "www.google.com";
    181   TriggerSyncError(protocol_error, SyncTest::ERROR_FREQUENCY_ALWAYS);
    182 
    183   // Now make one more change so we will do another sync.
    184   const BookmarkNode* node2 = AddFolder(0, 0, "title2");
    185   SetTitle(0, node2, "new_title2");
    186   ASSERT_TRUE(AwaitSyncDisabled(GetSyncService((0))));
    187   ProfileSyncService::Status status;
    188   GetSyncService((0))->QueryDetailedSyncStatus(&status);
    189   ASSERT_EQ(status.sync_protocol_error.error_type, protocol_error.error_type);
    190   ASSERT_EQ(status.sync_protocol_error.action, protocol_error.action);
    191   ASSERT_EQ(status.sync_protocol_error.url, protocol_error.url);
    192   ASSERT_EQ(status.sync_protocol_error.error_description,
    193       protocol_error.error_description);
    194 }
    195 
    196 // TODO(lipalani): Fix the typed_url dtc so this test case can pass.
    197 IN_PROC_BROWSER_TEST_F(LegacySyncErrorTest,
    198                        DISABLED_DisableDatatypeWhileRunning) {
    199   ASSERT_TRUE(SetupSync()) << "SetupSync() failed.";
    200   syncer::ModelTypeSet synced_datatypes =
    201       GetSyncService((0))->GetPreferredDataTypes();
    202   ASSERT_TRUE(synced_datatypes.Has(syncer::TYPED_URLS));
    203   GetProfile(0)->GetPrefs()->SetBoolean(
    204       prefs::kSavingBrowserHistoryDisabled, true);
    205 
    206   synced_datatypes = GetSyncService((0))->GetPreferredDataTypes();
    207   ASSERT_FALSE(synced_datatypes.Has(syncer::TYPED_URLS));
    208 
    209   const BookmarkNode* node1 = AddFolder(0, 0, "title1");
    210   SetTitle(0, node1, "new_title1");
    211   ASSERT_TRUE(AwaitCommitActivityCompletion(GetSyncService((0))));
    212   // TODO(lipalani)" Verify initial sync ended for typed url is false.
    213 }
    214 
    215 }  // namespace
    216