Upstream version 10.39.225.0
[platform/framework/web/crosswalk.git] / src / chrome / browser / sync_file_system / drive_backend / remote_to_local_syncer.h
1 // Copyright 2013 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 #ifndef CHROME_BROWSER_SYNC_FILE_SYSTEM_DRIVE_BACKEND_REMOTE_TO_LOCAL_SYNCER_H_
6 #define CHROME_BROWSER_SYNC_FILE_SYSTEM_DRIVE_BACKEND_REMOTE_TO_LOCAL_SYNCER_H_
7
8 #include <string>
9 #include <vector>
10
11 #include "base/memory/scoped_vector.h"
12 #include "base/memory/weak_ptr.h"
13 #include "chrome/browser/sync_file_system/drive_backend/metadata_database.pb.h"
14 #include "chrome/browser/sync_file_system/drive_backend/sync_task.h"
15 #include "chrome/browser/sync_file_system/drive_backend/sync_task_manager.h"
16 #include "chrome/browser/sync_file_system/remote_change_processor.h"
17 #include "chrome/browser/sync_file_system/sync_action.h"
18 #include "chrome/browser/sync_file_system/sync_callbacks.h"
19 #include "chrome/browser/sync_file_system/sync_file_metadata.h"
20 #include "google_apis/drive/gdata_errorcode.h"
21 #include "storage/browser/fileapi/file_system_url.h"
22
23 namespace drive {
24 class DriveServiceInterface;
25 }
26
27 namespace google_apis {
28 class FileList;
29 class FileResource;
30 class ResourceEntry;
31 }
32
33 namespace storage {
34 class ScopedFile;
35 }
36
37 namespace sync_file_system {
38 namespace drive_backend {
39
40 class MetadataDatabase;
41 class SyncEngineContext;
42
43 class RemoteToLocalSyncer : public SyncTask {
44  public:
45   typedef SyncTaskManager::Continuation Continuation;
46
47   // Conflicting trackers will have low priority for RemoteToLocalSyncer so that
48   // it should be resolved by LocatToRemoteSyncer.
49   explicit RemoteToLocalSyncer(SyncEngineContext* sync_context);
50   virtual ~RemoteToLocalSyncer();
51
52   virtual void RunPreflight(scoped_ptr<SyncTaskToken> token) OVERRIDE;
53   void RunExclusive(scoped_ptr<SyncTaskToken> token);
54
55   const storage::FileSystemURL& url() const { return url_; }
56   SyncAction sync_action() const { return sync_action_; }
57
58   bool is_sync_root_deletion() const { return sync_root_deletion_; }
59
60  private:
61   typedef std::vector<std::string> FileIDList;
62
63   // TODO(tzik): Update documentation here.
64   //
65   // Dispatches remote change to handlers or to SyncCompleted() directly.
66   // This function uses information only in MetadataDatabase.
67   //
68   // If the tracker doesn't have remote metadata:
69   //   # The file is listed in a folder right before this operation.
70   //   - Dispatch to HandleMissingRemoteMetadata to fetch remote metadata.
71   // Else, if the tracker is not active or the dominating app-root is disabled:
72   //   # Assume the file has remote metadata.
73   //   - Update the tracker with |missing| flag and empty |md5|.
74   //   Note: MetadataDatabase may activate the tracker if possible.
75   // Else, if the tracker doesn't have synced metadata:
76   //   # Assume the tracker has remote metadata and the tracker is active.
77   //   # The tracker is not yet synced ever.
78   //   - If the file is remotely deleted, do nothing to local file and dispatch
79   //     directly to SyncCompleted().
80   //   - Else, if the file is a regular file, dispatch to HandleNewFile().
81   //   - Else, if the file is a folder, dispatch to HandleFolderUpdate().
82   //   - Else, the file should be an unsupported active file. This should not
83   //     happen.
84   // Else, if the remote metadata is marked as deleted:
85   //   # Most of the remote metadata is missing including title, kind and md5.
86   //   - Dispatch to HandleDeletion().
87   // Else, if the tracker has different titles between its synced metadata and
88   // remote metadata:
89   //   # Assume the tracker is active and has remote metetadata and synced
90   //     metadata.
91   //   # The file is remotely renamed.
92   //   # Maybe, this can be decomposed to delete and update.
93   //   - Dispatch to HandleRemoteRename().
94   // Else, if the tracker's parent is not a parent of the remote metadata:
95   //   # The file has reorganized.
96   //   # Maybe, this can be decomposed to delete and update.
97   //   - Dispatch to HandreReorganize().
98   // Else, if the folder is a regular file and the md5 in remote metadata does
99   // not match the md5 in synced metadata:
100   //   # The file is modified remotely.
101   //   - Dispatch to HandleContentUpdate().
102   // Else, if the tracker is a folder and it has needs_folder_listing flag:
103   //   - Dispatch to HandleFolderContentListing()
104   // Else, there should be no change to sync.
105   //   - Dispatch to HandleOfflineSolvable()
106   void ResolveRemoteChange(scoped_ptr<SyncTaskToken> token);
107
108   void MoveToBackground(scoped_ptr<SyncTaskToken> token,
109                         const Continuation& continuation);
110   void ContinueAsBackgroundTask(const Continuation& continuation,
111                                 scoped_ptr<SyncTaskToken> token);
112
113   // Handles missing remote metadata case.
114   // Fetches remote metadata and updates MetadataDatabase by that.  The sync
115   // operation itself will be deferred to the next sync round.
116   // Note: if the file is not found, it should be handled as if deleted.
117   void HandleMissingRemoteMetadata(scoped_ptr<SyncTaskToken> token);
118   void DidGetRemoteMetadata(scoped_ptr<SyncTaskToken> token,
119                             google_apis::GDataErrorCode error,
120                             scoped_ptr<google_apis::FileResource> entry);
121
122   // This implements the body of the HandleNewFile and HandleContentUpdate.
123   // If the file doesn't have corresponding local file:
124   //   - Dispatch to DownloadFile.
125   // Else, if the local file doesn't have local change:
126   //   - Dispatch to DownloadFile if the local file is a regular file.
127   //   - If the local file is a folder, handle this case as a conflict.  Lower
128   //     the priority of the tracker, and defer further handling to
129   //     local-to-remote change.
130   // Else:
131   //  # The file has local modification.
132   //  - Handle this case as a conflict.  Lower the priority of the tracker, and
133   //    defer further handling to local-to-remote change.
134   void DidPrepareForAddOrUpdateFile(scoped_ptr<SyncTaskToken> token,
135                                     SyncStatusCode status);
136
137   // Handles remotely added folder.  Needs Prepare() call.
138   // TODO(tzik): Write details and implement this.
139   void HandleFolderUpdate(scoped_ptr<SyncTaskToken> token);
140   void DidPrepareForFolderUpdate(scoped_ptr<SyncTaskToken> token,
141                                  SyncStatusCode status);
142
143   // Handles deleted remote file.  Needs Prepare() call.
144   // If the deleted tracker is the sync-root:
145   //  - TODO(tzik): Needs special handling.
146   // Else, if the deleted tracker is a app-root:
147   //  - TODO(tzik): Needs special handling.
148   // Else, if the local file is already deleted:
149   //  - Do nothing anymore to the local, call SyncCompleted().
150   // Else, if the local file is modified:
151   //  - Do nothing to the local file, call SyncCompleted().
152   // Else, if the local file is not modified:
153   //  - Delete local file.
154   //  # Note: if the local file is a folder, delete recursively.
155   void HandleDeletion(scoped_ptr<SyncTaskToken> token);
156   void DidPrepareForDeletion(scoped_ptr<SyncTaskToken> token,
157                              SyncStatusCode status);
158
159   void HandleFileMove(scoped_ptr<SyncTaskToken> token);
160
161   // Handles new file.  Needs Prepare() call.
162   void HandleContentUpdate(scoped_ptr<SyncTaskToken> token);
163
164   void ListFolderContent(scoped_ptr<SyncTaskToken> token);
165   void DidListFolderContent(
166       scoped_ptr<SyncTaskToken> token,
167       scoped_ptr<FileIDList> children,
168       google_apis::GDataErrorCode error,
169       scoped_ptr<google_apis::FileList> file_list);
170
171   void SyncCompleted(scoped_ptr<SyncTaskToken> token, SyncStatusCode status);
172   void FinalizeSync(scoped_ptr<SyncTaskToken> token, SyncStatusCode status);
173
174   void Prepare(const SyncStatusCallback& callback);
175   void DidPrepare(const SyncStatusCallback& callback,
176                   SyncStatusCode status,
177                   const SyncFileMetadata& metadata,
178                   const FileChangeList& changes);
179
180   void DeleteLocalFile(scoped_ptr<SyncTaskToken> token);
181   void DownloadFile(scoped_ptr<SyncTaskToken> token);
182   void DidDownloadFile(scoped_ptr<SyncTaskToken> token,
183                        storage::ScopedFile file,
184                        google_apis::GDataErrorCode error,
185                        const base::FilePath&);
186   void DidApplyDownload(scoped_ptr<SyncTaskToken> token,
187                         storage::ScopedFile,
188                         SyncStatusCode status);
189
190   void CreateFolder(scoped_ptr<SyncTaskToken> token);
191
192   // TODO(tzik): After we convert all callbacks to token-passing style,
193   // drop this function.
194   SyncStatusCallback SyncCompletedCallback(scoped_ptr<SyncTaskToken> token);
195
196   drive::DriveServiceInterface* drive_service();
197   MetadataDatabase* metadata_database();
198   RemoteChangeProcessor* remote_change_processor();
199
200   SyncEngineContext* sync_context_;  // Not owned.
201
202   scoped_ptr<FileTracker> dirty_tracker_;
203   scoped_ptr<FileMetadata> remote_metadata_;
204
205   storage::FileSystemURL url_;
206   SyncAction sync_action_;
207
208   bool prepared_;
209   bool sync_root_deletion_;
210
211   scoped_ptr<SyncFileMetadata> local_metadata_;
212   scoped_ptr<FileChangeList> local_changes_;
213
214   base::WeakPtrFactory<RemoteToLocalSyncer> weak_ptr_factory_;
215
216   DISALLOW_COPY_AND_ASSIGN(RemoteToLocalSyncer);
217 };
218
219 }  // namespace drive_backend
220 }  // namespace sync_file_system
221
222 #endif  // CHROME_BROWSER_SYNC_FILE_SYSTEM_DRIVE_BACKEND_REMOTE_TO_LOCAL_SYNCER_H_