Upstream version 5.34.104.0
[platform/framework/web/crosswalk.git] / src / chrome / browser / sync_file_system / local / local_file_sync_service.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_LOCAL_LOCAL_FILE_SYNC_SERVICE_H_
6 #define CHROME_BROWSER_SYNC_FILE_SYSTEM_LOCAL_LOCAL_FILE_SYNC_SERVICE_H_
7
8 #include <map>
9 #include <set>
10 #include <string>
11
12 #include "base/basictypes.h"
13 #include "base/callback.h"
14 #include "base/memory/ref_counted.h"
15 #include "base/memory/weak_ptr.h"
16 #include "base/observer_list.h"
17 #include "chrome/browser/sync_file_system/local/local_origin_change_observer.h"
18 #include "chrome/browser/sync_file_system/remote_change_processor.h"
19 #include "chrome/browser/sync_file_system/sync_callbacks.h"
20 #include "chrome/browser/sync_file_system/sync_status_code.h"
21
22 class GURL;
23 class Profile;
24
25 namespace fileapi {
26 class FileSystemContext;
27 }
28
29 namespace leveldb {
30 class Env;
31 }
32
33 namespace webkit_blob {
34 class ScopedFile;
35 }
36
37 namespace sync_file_system {
38
39 class FileChange;
40 class LocalChangeProcessor;
41 class LocalFileSyncContext;
42 struct LocalFileSyncInfo;
43
44 // Maintains local file change tracker and sync status.
45 // Owned by SyncFileSystemService (which is a per-profile object).
46 class LocalFileSyncService
47     : public RemoteChangeProcessor,
48       public LocalOriginChangeObserver,
49       public base::SupportsWeakPtr<LocalFileSyncService> {
50  public:
51   typedef base::Callback<LocalChangeProcessor*(const GURL& origin)>
52       GetLocalChangeProcessorCallback;
53
54   class Observer {
55    public:
56     Observer() {}
57     virtual ~Observer() {}
58
59     // This is called when there're one or more local changes available.
60     // |pending_changes_hint| indicates the pending queue length to help sync
61     // scheduling but the value may not be accurately reflect the real-time
62     // value.
63     virtual void OnLocalChangeAvailable(int64 pending_changes_hint) = 0;
64
65    private:
66     DISALLOW_COPY_AND_ASSIGN(Observer);
67   };
68
69   typedef base::Callback<void(SyncStatusCode status,
70                               bool has_pending_changes)>
71       HasPendingLocalChangeCallback;
72
73   static scoped_ptr<LocalFileSyncService> Create(Profile* profile);
74   static scoped_ptr<LocalFileSyncService> CreateForTesting(
75       Profile* profile,
76       leveldb::Env* env_override);
77   virtual ~LocalFileSyncService();
78
79   void Shutdown();
80
81   void MaybeInitializeFileSystemContext(
82       const GURL& app_origin,
83       fileapi::FileSystemContext* file_system_context,
84       const SyncStatusCallback& callback);
85
86   void AddChangeObserver(Observer* observer);
87
88   // Registers |url| to wait until sync is enabled for |url|.
89   // |on_syncable_callback| is to be called when |url| becomes syncable
90   // (i.e. when we have no pending writes and the file is successfully locked
91   // for sync).
92   // Calling this method again while this already has another URL waiting
93   // for sync will overwrite the previously registered URL.
94   void RegisterURLForWaitingSync(const fileapi::FileSystemURL& url,
95                                  const base::Closure& on_syncable_callback);
96
97   // Synchronize one (or a set of) local change(s) to the remote server
98   // using local_change_processor given by SetLocalChangeProcessor().
99   // |processor| must have same or longer lifetime than this service.
100   // It is invalid to call this method before calling SetLocalChangeProcessor().
101   void ProcessLocalChange(const SyncFileCallback& callback);
102
103   // Sets a local change processor. The value is ignored if
104   // SetLocalChangeProcessorCallback() is called separately.
105   // Either this or SetLocalChangeProcessorCallback() must be called before
106   // any ProcessLocalChange().
107   void SetLocalChangeProcessor(LocalChangeProcessor* local_change_processor);
108
109   // Sets a closure which gets a local change processor for the given origin.
110   // Note that once this is called it overrides the direct processor setting
111   // done by SetLocalChangeProcessor().
112   // Either this or SetLocalChangeProcessor() must be called before any
113   // ProcessLocalChange().
114   //
115   // TODO(kinuko): Remove this method once we stop using multiple backends
116   // (crbug.com/324215), or deprecate the other if we keep doing so.
117   void SetLocalChangeProcessorCallback(
118       const GetLocalChangeProcessorCallback& get_local_change_processor);
119
120   // Returns true via |callback| if the given file |url| has local pending
121   // changes.
122   void HasPendingLocalChanges(
123       const fileapi::FileSystemURL& url,
124       const HasPendingLocalChangeCallback& callback);
125
126   void PromoteDemotedChanges();
127
128   // Returns the metadata of a remote file pointed by |url|.
129   virtual void GetLocalFileMetadata(
130       const fileapi::FileSystemURL& url,
131       const SyncFileMetadataCallback& callback);
132
133   // RemoteChangeProcessor overrides.
134   virtual void PrepareForProcessRemoteChange(
135       const fileapi::FileSystemURL& url,
136       const PrepareChangeCallback& callback) OVERRIDE;
137   virtual void ApplyRemoteChange(
138       const FileChange& change,
139       const base::FilePath& local_path,
140       const fileapi::FileSystemURL& url,
141       const SyncStatusCallback& callback) OVERRIDE;
142   virtual void FinalizeRemoteSync(
143       const fileapi::FileSystemURL& url,
144       bool clear_local_changes,
145       const base::Closure& completion_callback) OVERRIDE;
146   virtual void RecordFakeLocalChange(
147       const fileapi::FileSystemURL& url,
148       const FileChange& change,
149       const SyncStatusCallback& callback) OVERRIDE;
150
151   // LocalOriginChangeObserver override.
152   virtual void OnChangesAvailableInOrigins(
153       const std::set<GURL>& origins) OVERRIDE;
154
155   // Called when a particular origin (app) is disabled/enabled while
156   // the service is running. This may be called for origins/apps that
157   // are not initialized for the service.
158   void SetOriginEnabled(const GURL& origin, bool enabled);
159
160  private:
161   typedef std::map<GURL, fileapi::FileSystemContext*> OriginToContext;
162   friend class OriginChangeMapTest;
163
164   class OriginChangeMap {
165    public:
166     typedef std::map<GURL, int64> Map;
167
168     OriginChangeMap();
169     ~OriginChangeMap();
170
171     // Sets |origin| to the next origin to process. (For now we simply apply
172     // round-robin to pick the next origin to avoid starvation.)
173     // Returns false if no origins to process.
174     bool NextOriginToProcess(GURL* origin);
175
176     int64 GetTotalChangeCount() const;
177
178     // Update change_count_map_ for |origin|.
179     void SetOriginChangeCount(const GURL& origin, int64 changes);
180
181     void SetOriginEnabled(const GURL& origin, bool enabled);
182
183    private:
184     // Per-origin changes (cached info, could be stale).
185     Map change_count_map_;
186     Map::iterator next_;
187
188     // Holds a set of disabled (but initialized) origins.
189     std::set<GURL> disabled_origins_;
190   };
191
192   LocalFileSyncService(Profile* profile, leveldb::Env* env_override);
193
194   void DidInitializeFileSystemContext(
195       const GURL& app_origin,
196       fileapi::FileSystemContext* file_system_context,
197       const SyncStatusCallback& callback,
198       SyncStatusCode status);
199   void DidInitializeForRemoteSync(
200       const fileapi::FileSystemURL& url,
201       fileapi::FileSystemContext* file_system_context,
202       const PrepareChangeCallback& callback,
203       SyncStatusCode status);
204
205   // Runs local_sync_callback_ and resets it.
206   void RunLocalSyncCallback(
207       SyncStatusCode status,
208       const fileapi::FileSystemURL& url);
209
210   // Callback for ApplyRemoteChange.
211   void DidApplyRemoteChange(
212       const SyncStatusCallback& callback,
213       SyncStatusCode status);
214
215   // Callbacks for ProcessLocalChange.
216   void DidGetFileForLocalSync(
217       SyncStatusCode status,
218       const LocalFileSyncInfo& sync_file_info,
219       webkit_blob::ScopedFile snapshot);
220   void ProcessNextChangeForURL(
221       webkit_blob::ScopedFile snapshot,
222       const LocalFileSyncInfo& sync_file_info,
223       const FileChange& last_change,
224       const FileChangeList& changes,
225       SyncStatusCode status);
226
227   // A thin wrapper of get_local_change_processor_.
228   LocalChangeProcessor* GetLocalChangeProcessor(
229       const fileapi::FileSystemURL& url);
230
231   Profile* profile_;
232
233   scoped_refptr<LocalFileSyncContext> sync_context_;
234
235   // Origin to context map. (Assuming that as far as we're in the same
236   // profile single origin wouldn't belong to multiple FileSystemContexts.)
237   OriginToContext origin_to_contexts_;
238
239   // Origins which have pending changes but have not been initialized yet.
240   // (Used only for handling dirty files left in the local tracker database
241   // after a restart.)
242   std::set<GURL> pending_origins_with_changes_;
243
244   OriginChangeMap origin_change_map_;
245
246   // This callback is non-null while a local sync is running (i.e.
247   // ProcessLocalChange has been called and has not been returned yet).
248   SyncFileCallback local_sync_callback_;
249
250   LocalChangeProcessor* local_change_processor_;
251   GetLocalChangeProcessorCallback get_local_change_processor_;
252
253   ObserverList<Observer> change_observers_;
254
255   DISALLOW_COPY_AND_ASSIGN(LocalFileSyncService);
256 };
257
258 }  // namespace sync_file_system
259
260 #endif  // CHROME_BROWSER_SYNC_FILE_SYSTEM_LOCAL_LOCAL_FILE_SYNC_SERVICE_H_