Home | History | Annotate | Download | only in sync_driver
      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 "components/sync_driver/shared_change_processor.h"
      6 
      7 #include <cstddef>
      8 
      9 #include "base/bind.h"
     10 #include "base/bind_helpers.h"
     11 #include "base/compiler_specific.h"
     12 #include "base/message_loop/message_loop.h"
     13 #include "base/threading/thread.h"
     14 #include "components/sync_driver/data_type_error_handler_mock.h"
     15 #include "components/sync_driver/generic_change_processor.h"
     16 #include "components/sync_driver/generic_change_processor_factory.h"
     17 #include "components/sync_driver/sync_api_component_factory.h"
     18 #include "sync/api/attachments/attachment_service_impl.h"
     19 #include "sync/api/fake_syncable_service.h"
     20 #include "testing/gmock/include/gmock/gmock.h"
     21 #include "testing/gtest/include/gtest/gtest.h"
     22 
     23 namespace browser_sync {
     24 
     25 namespace {
     26 
     27 using ::testing::NiceMock;
     28 using ::testing::StrictMock;
     29 
     30 class SyncSharedChangeProcessorTest :
     31     public testing::Test,
     32     public browser_sync::SyncApiComponentFactory {
     33  public:
     34   SyncSharedChangeProcessorTest() : backend_thread_("dbthread"),
     35                                     did_connect_(false) {}
     36 
     37   virtual ~SyncSharedChangeProcessorTest() {
     38     EXPECT_FALSE(db_syncable_service_.get());
     39   }
     40 
     41   virtual base::WeakPtr<syncer::SyncableService> GetSyncableServiceForType(
     42       syncer::ModelType type) OVERRIDE {
     43     return db_syncable_service_->AsWeakPtr();
     44   }
     45 
     46   virtual scoped_ptr<syncer::AttachmentService> CreateAttachmentService(
     47       syncer::AttachmentService::Delegate* delegate) OVERRIDE {
     48     return syncer::AttachmentServiceImpl::CreateForTest();
     49   }
     50 
     51  protected:
     52   virtual void SetUp() OVERRIDE {
     53     shared_change_processor_ = new SharedChangeProcessor();
     54     ASSERT_TRUE(backend_thread_.Start());
     55     ASSERT_TRUE(backend_thread_.message_loop_proxy()->PostTask(
     56         FROM_HERE,
     57         base::Bind(&SyncSharedChangeProcessorTest::SetUpDBSyncableService,
     58                    base::Unretained(this))));
     59   }
     60 
     61   virtual void TearDown() OVERRIDE {
     62     EXPECT_TRUE(backend_thread_.message_loop_proxy()->PostTask(
     63         FROM_HERE,
     64         base::Bind(&SyncSharedChangeProcessorTest::TearDownDBSyncableService,
     65                    base::Unretained(this))));
     66     // This must happen before the DB thread is stopped since
     67     // |shared_change_processor_| may post tasks to delete its members
     68     // on the correct thread.
     69     //
     70     // TODO(akalin): Write deterministic tests for the destruction of
     71     // |shared_change_processor_| on the UI and DB threads.
     72     shared_change_processor_ = NULL;
     73     backend_thread_.Stop();
     74 
     75     // Note: Stop() joins the threads, and that barrier prevents this read
     76     // from being moved (e.g by compiler optimization) in such a way that it
     77     // would race with the write in ConnectOnDBThread (because by this time,
     78     // everything that could have run on |backend_thread_| has done so).
     79     ASSERT_TRUE(did_connect_);
     80   }
     81 
     82   // Connect |shared_change_processor_| on the DB thread.
     83   void Connect() {
     84     EXPECT_TRUE(backend_thread_.message_loop_proxy()->PostTask(
     85         FROM_HERE,
     86         base::Bind(&SyncSharedChangeProcessorTest::ConnectOnDBThread,
     87                    base::Unretained(this),
     88                    shared_change_processor_)));
     89   }
     90 
     91  private:
     92   // Used by SetUp().
     93   void SetUpDBSyncableService() {
     94     DCHECK(backend_thread_.message_loop_proxy()->BelongsToCurrentThread());
     95     DCHECK(!db_syncable_service_.get());
     96     db_syncable_service_.reset(new syncer::FakeSyncableService());
     97   }
     98 
     99   // Used by TearDown().
    100   void TearDownDBSyncableService() {
    101     DCHECK(backend_thread_.message_loop_proxy()->BelongsToCurrentThread());
    102     DCHECK(db_syncable_service_.get());
    103     db_syncable_service_.reset();
    104   }
    105 
    106   // Used by Connect().  The SharedChangeProcessor is passed in
    107   // because we modify |shared_change_processor_| on the main thread
    108   // (in TearDown()).
    109   void ConnectOnDBThread(
    110       const scoped_refptr<SharedChangeProcessor>& shared_change_processor) {
    111     DCHECK(backend_thread_.message_loop_proxy()->BelongsToCurrentThread());
    112     syncer::UserShare share;
    113     EXPECT_TRUE(shared_change_processor->Connect(
    114         this,
    115         &processor_factory_,
    116         &share,
    117         &error_handler_,
    118         syncer::AUTOFILL,
    119         base::WeakPtr<syncer::SyncMergeResult>()));
    120     did_connect_ = true;
    121   }
    122 
    123   base::MessageLoop frontend_loop_;
    124   base::Thread backend_thread_;
    125 
    126   scoped_refptr<SharedChangeProcessor> shared_change_processor_;
    127   StrictMock<DataTypeErrorHandlerMock> error_handler_;
    128 
    129   GenericChangeProcessorFactory processor_factory_;
    130   bool did_connect_;
    131 
    132   // Used only on DB thread.
    133   scoped_ptr<syncer::FakeSyncableService> db_syncable_service_;
    134 };
    135 
    136 // Simply connect the shared change processor.  It should succeed, and
    137 // nothing further should happen.
    138 TEST_F(SyncSharedChangeProcessorTest, Basic) {
    139   Connect();
    140 }
    141 
    142 }  // namespace
    143 
    144 }  // namespace browser_sync
    145