Home | History | Annotate | Download | only in sync_file_system
      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/json/json_reader.h"
      6 #include "base/run_loop.h"
      7 #include "base/thread_task_runner_handle.h"
      8 #include "base/values.h"
      9 #include "chrome/browser/apps/app_browsertest_util.h"
     10 #include "chrome/browser/drive/fake_drive_service.h"
     11 #include "chrome/browser/extensions/extension_service.h"
     12 #include "chrome/browser/signin/fake_signin_manager.h"
     13 #include "chrome/browser/sync_file_system/drive_backend/sync_engine.h"
     14 #include "chrome/browser/sync_file_system/local/local_file_sync_service.h"
     15 #include "chrome/browser/sync_file_system/sync_file_system_service.h"
     16 #include "chrome/browser/sync_file_system/sync_file_system_service_factory.h"
     17 #include "extensions/test/extension_test_message_listener.h"
     18 #include "extensions/test/result_catcher.h"
     19 #include "storage/browser/quota/quota_manager.h"
     20 #include "third_party/leveldatabase/src/helpers/memenv/memenv.h"
     21 #include "third_party/leveldatabase/src/include/leveldb/env.h"
     22 
     23 namespace sync_file_system {
     24 
     25 namespace {
     26 
     27 class FakeDriveServiceFactory
     28     : public drive_backend::SyncEngine::DriveServiceFactory {
     29  public:
     30   explicit FakeDriveServiceFactory(
     31       drive::FakeDriveService::ChangeObserver* change_observer)
     32       : change_observer_(change_observer) {}
     33   virtual ~FakeDriveServiceFactory() {}
     34 
     35   virtual scoped_ptr<drive::DriveServiceInterface> CreateDriveService(
     36       OAuth2TokenService* oauth2_token_service,
     37       net::URLRequestContextGetter* url_request_context_getter,
     38       base::SequencedTaskRunner* blocking_task_runner) OVERRIDE {
     39     scoped_ptr<drive::FakeDriveService> drive_service(
     40         new drive::FakeDriveService);
     41     drive_service->AddChangeObserver(change_observer_);
     42     return drive_service.PassAs<drive::DriveServiceInterface>();
     43   }
     44 
     45  private:
     46   drive::FakeDriveService::ChangeObserver* change_observer_;
     47 
     48   DISALLOW_COPY_AND_ASSIGN(FakeDriveServiceFactory);
     49 };
     50 
     51 }  // namespace
     52 
     53 class SyncFileSystemTest : public extensions::PlatformAppBrowserTest,
     54                            public drive::FakeDriveService::ChangeObserver {
     55  public:
     56   SyncFileSystemTest()
     57       : fake_drive_service_(NULL),
     58         local_service_(NULL),
     59         remote_service_(NULL) {
     60   }
     61 
     62   virtual void SetUpInProcessBrowserTestFixture() OVERRIDE {
     63     ExtensionApiTest::SetUpInProcessBrowserTestFixture();
     64     real_minimum_preserved_space_ =
     65         storage::QuotaManager::kMinimumPreserveForSystem;
     66     storage::QuotaManager::kMinimumPreserveForSystem = 0;
     67   }
     68 
     69   virtual void TearDownInProcessBrowserTestFixture() OVERRIDE {
     70     storage::QuotaManager::kMinimumPreserveForSystem =
     71         real_minimum_preserved_space_;
     72     ExtensionApiTest::TearDownInProcessBrowserTestFixture();
     73   }
     74 
     75   scoped_refptr<base::SequencedTaskRunner> MakeSequencedTaskRunner() {
     76     scoped_refptr<base::SequencedWorkerPool> worker_pool =
     77         content::BrowserThread::GetBlockingPool();
     78 
     79     return worker_pool->GetSequencedTaskRunnerWithShutdownBehavior(
     80         worker_pool->GetSequenceToken(),
     81         base::SequencedWorkerPool::SKIP_ON_SHUTDOWN);
     82   }
     83 
     84   virtual void SetUpOnMainThread() OVERRIDE {
     85     ASSERT_TRUE(base_dir_.CreateUniqueTempDir());
     86 
     87     SyncFileSystemServiceFactory* factory =
     88         SyncFileSystemServiceFactory::GetInstance();
     89 
     90     content::BrowserContext* context = browser()->profile();
     91     ExtensionServiceInterface* extension_service =
     92         extensions::ExtensionSystem::Get(context)->extension_service();
     93 
     94     scoped_ptr<drive_backend::SyncEngine::DriveServiceFactory>
     95         drive_service_factory(new FakeDriveServiceFactory(this));
     96 
     97     fake_signin_manager_.reset(new FakeSigninManagerForTesting(
     98         browser()->profile()));
     99 
    100     remote_service_ = new drive_backend::SyncEngine(
    101         base::ThreadTaskRunnerHandle::Get(),  // ui_task_runner
    102         MakeSequencedTaskRunner(),
    103         MakeSequencedTaskRunner(),
    104         base_dir_.path(),
    105         NULL,  // task_logger
    106         NULL,  // notification_manager
    107         extension_service,
    108         fake_signin_manager_.get(),  // signin_manager
    109         NULL,  // token_service
    110         NULL,  // request_context
    111         drive_service_factory.Pass(),
    112         in_memory_env_.get());
    113     remote_service_->SetSyncEnabled(true);
    114     factory->set_mock_remote_file_service(
    115         scoped_ptr<RemoteFileSyncService>(remote_service_));
    116   }
    117 
    118   // drive::FakeDriveService::ChangeObserver override.
    119   virtual void OnNewChangeAvailable() OVERRIDE {
    120     sync_engine()->OnNotificationReceived();
    121   }
    122 
    123   SyncFileSystemService* sync_file_system_service() {
    124     return SyncFileSystemServiceFactory::GetForProfile(browser()->profile());
    125   }
    126 
    127   drive_backend::SyncEngine* sync_engine() {
    128     return static_cast<drive_backend::SyncEngine*>(
    129         sync_file_system_service()->remote_service_.get());
    130   }
    131 
    132   LocalFileSyncService* local_file_sync_service() {
    133     return sync_file_system_service()->local_service_.get();
    134   }
    135 
    136   void SignIn() {
    137     fake_signin_manager_->SetAuthenticatedUsername("tester");
    138     sync_engine()->GoogleSigninSucceeded("test_account", "tester", "testing");
    139   }
    140 
    141   void SetSyncEnabled(bool enabled) {
    142     sync_file_system_service()->SetSyncEnabledForTesting(enabled);
    143   }
    144 
    145   void WaitUntilIdle() {
    146     base::RunLoop run_loop;
    147     sync_file_system_service()->CallOnIdleForTesting(run_loop.QuitClosure());
    148     run_loop.Run();
    149   }
    150 
    151  private:
    152   base::ScopedTempDir base_dir_;
    153   scoped_ptr<leveldb::Env> in_memory_env_;
    154 
    155   scoped_ptr<FakeSigninManagerForTesting> fake_signin_manager_;
    156 
    157   drive::FakeDriveService* fake_drive_service_;
    158   LocalFileSyncService* local_service_;
    159   drive_backend::SyncEngine* remote_service_;
    160 
    161   int64 real_minimum_preserved_space_;
    162 
    163   DISALLOW_COPY_AND_ASSIGN(SyncFileSystemTest);
    164 };
    165 
    166 IN_PROC_BROWSER_TEST_F(SyncFileSystemTest, AuthorizationTest) {
    167   ExtensionTestMessageListener open_failure(
    168       "checkpoint: Failed to get syncfs", true);
    169   ExtensionTestMessageListener bar_created(
    170       "checkpoint: \"/bar\" created", true);
    171   ExtensionTestMessageListener foo_created(
    172       "checkpoint: \"/foo\" created", true);
    173   extensions::ResultCatcher catcher;
    174 
    175   LoadAndLaunchPlatformApp("sync_file_system/authorization_test", "Launched");
    176 
    177   // Application sync is disabled at the initial state.  Thus first
    178   // syncFilesystem.requestFileSystem call should fail.
    179   ASSERT_TRUE(open_failure.WaitUntilSatisfied());
    180 
    181   // Enable Application sync and let the app retry.
    182   SignIn();
    183   SetSyncEnabled(true);
    184 
    185   open_failure.Reply("resume");
    186 
    187   ASSERT_TRUE(foo_created.WaitUntilSatisfied());
    188 
    189   // The app creates a file "/foo", that should successfully sync to the remote
    190   // service.  Wait for the completion and resume the app.
    191   WaitUntilIdle();
    192 
    193   sync_engine()->GoogleSignedOut("test_account", std::string());
    194   foo_created.Reply("resume");
    195 
    196   ASSERT_TRUE(bar_created.WaitUntilSatisfied());
    197 
    198   // The app creates anohter file "/bar".  Since the user signed out from chrome
    199   // The synchronization should fail and the service state should be
    200   // AUTHENTICATION_REQUIRED.
    201 
    202   WaitUntilIdle();
    203   EXPECT_EQ(REMOTE_SERVICE_AUTHENTICATION_REQUIRED,
    204             sync_engine()->GetCurrentState());
    205 
    206   sync_engine()->GoogleSigninSucceeded("test_account", "tester", "testing");
    207   WaitUntilIdle();
    208 
    209   bar_created.Reply("resume");
    210 
    211   EXPECT_TRUE(catcher.GetNextResult());
    212 }
    213 
    214 }  // namespace sync_file_system
    215