Apply _RELATIVE relocations ahead of others.
[chromium-blink-merge.git] / content / browser / service_worker / service_worker_storage.h
blob0eda8bf540e7616f6c736c77c2019c05a472ed3b
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.
5 #ifndef CONTENT_BROWSER_SERVICE_WORKER_SERVICE_WORKER_STORAGE_H_
6 #define CONTENT_BROWSER_SERVICE_WORKER_SERVICE_WORKER_STORAGE_H_
8 #include <deque>
9 #include <map>
10 #include <set>
11 #include <vector>
13 #include "base/bind.h"
14 #include "base/files/file_path.h"
15 #include "base/gtest_prod_util.h"
16 #include "base/memory/scoped_vector.h"
17 #include "base/memory/weak_ptr.h"
18 #include "content/browser/service_worker/service_worker_database.h"
19 #include "content/browser/service_worker/service_worker_database_task_manager.h"
20 #include "content/browser/service_worker/service_worker_version.h"
21 #include "content/common/content_export.h"
22 #include "content/common/service_worker/service_worker_status_code.h"
23 #include "url/gurl.h"
25 namespace base {
26 class SequencedTaskRunner;
27 class SingleThreadTaskRunner;
30 namespace storage {
31 class QuotaManagerProxy;
32 class SpecialStoragePolicy;
35 namespace content {
37 class ServiceWorkerContextCore;
38 class ServiceWorkerDiskCache;
39 class ServiceWorkerRegistration;
40 class ServiceWorkerRegistrationInfo;
41 class ServiceWorkerResponseReader;
42 class ServiceWorkerResponseWriter;
44 // This class provides an interface to store and retrieve ServiceWorker
45 // registration data.
46 class CONTENT_EXPORT ServiceWorkerStorage
47 : NON_EXPORTED_BASE(public ServiceWorkerVersion::Listener) {
48 public:
49 typedef std::vector<ServiceWorkerDatabase::ResourceRecord> ResourceList;
50 typedef base::Callback<void(ServiceWorkerStatusCode status)> StatusCallback;
51 typedef base::Callback<void(ServiceWorkerStatusCode status,
52 const scoped_refptr<ServiceWorkerRegistration>&
53 registration)> FindRegistrationCallback;
54 typedef base::Callback<
55 void(const std::vector<ServiceWorkerRegistrationInfo>& registrations)>
56 GetAllRegistrationInfosCallback;
57 typedef base::Callback<
58 void(ServiceWorkerStatusCode status, bool are_equal)>
59 CompareCallback;
61 ~ServiceWorkerStorage() override;
63 static scoped_ptr<ServiceWorkerStorage> Create(
64 const base::FilePath& path,
65 base::WeakPtr<ServiceWorkerContextCore> context,
66 scoped_ptr<ServiceWorkerDatabaseTaskManager> database_task_manager,
67 const scoped_refptr<base::SingleThreadTaskRunner>& disk_cache_thread,
68 storage::QuotaManagerProxy* quota_manager_proxy,
69 storage::SpecialStoragePolicy* special_storage_policy);
71 // Used for DeleteAndStartOver. Creates new storage based on |old_storage|.
72 static scoped_ptr<ServiceWorkerStorage> Create(
73 base::WeakPtr<ServiceWorkerContextCore> context,
74 ServiceWorkerStorage* old_storage);
76 // Finds registration for |document_url| or |pattern| or |registration_id|.
77 // The Find methods will find stored and initially installing registrations.
78 // Returns SERVICE_WORKER_OK with non-null registration if registration
79 // is found, or returns SERVICE_WORKER_ERROR_NOT_FOUND if no matching
80 // registration is found. The FindRegistrationForPattern method is
81 // guaranteed to return asynchronously. However, the methods to find
82 // for |document_url| or |registration_id| may complete immediately
83 // (the callback may be called prior to the method returning) or
84 // asynchronously.
85 void FindRegistrationForDocument(const GURL& document_url,
86 const FindRegistrationCallback& callback);
87 void FindRegistrationForPattern(const GURL& scope,
88 const FindRegistrationCallback& callback);
89 void FindRegistrationForId(int64 registration_id,
90 const GURL& origin,
91 const FindRegistrationCallback& callback);
93 ServiceWorkerRegistration* GetUninstallingRegistration(const GURL& scope);
95 // Returns info about all stored and initially installing registrations.
96 void GetAllRegistrations(const GetAllRegistrationInfosCallback& callback);
98 // Commits |registration| with the installed but not activated |version|
99 // to storage, overwritting any pre-existing registration data for the scope.
100 // A pre-existing version's script resources remain available if that version
101 // is live. PurgeResources should be called when it's OK to delete them.
102 void StoreRegistration(ServiceWorkerRegistration* registration,
103 ServiceWorkerVersion* version,
104 const StatusCallback& callback);
106 // Updates the state of the registration's stored version to active.
107 void UpdateToActiveState(
108 ServiceWorkerRegistration* registration,
109 const StatusCallback& callback);
111 // Updates the stored time to match the value of
112 // registration->last_update_check().
113 void UpdateLastUpdateCheckTime(ServiceWorkerRegistration* registration);
115 // Deletes the registration data for |registration_id|. If the registration's
116 // version is live, its script resources will remain available.
117 // PurgeResources should be called when it's OK to delete them.
118 void DeleteRegistration(int64 registration_id,
119 const GURL& origin,
120 const StatusCallback& callback);
122 scoped_ptr<ServiceWorkerResponseReader> CreateResponseReader(
123 int64 response_id);
124 scoped_ptr<ServiceWorkerResponseWriter> CreateResponseWriter(
125 int64 response_id);
127 // Adds |id| to the set of resources ids that are in the disk
128 // cache but not yet stored with a registration.
129 void StoreUncommittedResponseId(int64 id);
131 // Removes |id| from uncommitted list, adds it to the
132 // purgeable list and purges it.
133 void DoomUncommittedResponse(int64 id);
135 // Compares only the response bodies.
136 void CompareScriptResources(int64 lhs_id, int64 rhs_id,
137 const CompareCallback& callback);
139 // Deletes the storage and starts over.
140 void DeleteAndStartOver(const StatusCallback& callback);
142 // Returns new IDs which are guaranteed to be unique in the storage.
143 int64 NewRegistrationId();
144 int64 NewVersionId();
145 int64 NewResourceId();
147 // Intended for use only by ServiceWorkerRegisterJob and
148 // ServiceWorkerRegistration.
149 void NotifyInstallingRegistration(
150 ServiceWorkerRegistration* registration);
151 void NotifyDoneInstallingRegistration(
152 ServiceWorkerRegistration* registration,
153 ServiceWorkerVersion* version,
154 ServiceWorkerStatusCode status);
155 void NotifyUninstallingRegistration(ServiceWorkerRegistration* registration);
156 void NotifyDoneUninstallingRegistration(
157 ServiceWorkerRegistration* registration);
159 void Disable();
160 bool IsDisabled() const;
162 // |resources| must already be on the purgeable list.
163 void PurgeResources(const ResourceList& resources);
165 private:
166 friend class ServiceWorkerResourceStorageTest;
167 friend class ServiceWorkerControlleeRequestHandlerTest;
168 friend class ServiceWorkerContextRequestHandlerTest;
169 friend class ServiceWorkerRequestHandlerTest;
170 friend class ServiceWorkerWriteToCacheJobTest;
171 FRIEND_TEST_ALL_PREFIXES(ServiceWorkerResourceStorageTest,
172 DeleteRegistration_NoLiveVersion);
173 FRIEND_TEST_ALL_PREFIXES(ServiceWorkerResourceStorageTest,
174 DeleteRegistration_WaitingVersion);
175 FRIEND_TEST_ALL_PREFIXES(ServiceWorkerResourceStorageTest,
176 DeleteRegistration_ActiveVersion);
177 FRIEND_TEST_ALL_PREFIXES(ServiceWorkerResourceStorageTest,
178 UpdateRegistration);
179 FRIEND_TEST_ALL_PREFIXES(ServiceWorkerResourceStorageDiskTest,
180 CleanupOnRestart);
181 FRIEND_TEST_ALL_PREFIXES(ServiceWorkerResourceStorageDiskTest,
182 ClearOnExit);
184 struct InitialData {
185 int64 next_registration_id;
186 int64 next_version_id;
187 int64 next_resource_id;
188 std::set<GURL> origins;
190 InitialData();
191 ~InitialData();
194 // Because there are too many params for base::Bind to wrap a closure around.
195 struct DidDeleteRegistrationParams {
196 int64 registration_id;
197 GURL origin;
198 StatusCallback callback;
200 DidDeleteRegistrationParams();
201 ~DidDeleteRegistrationParams();
204 typedef std::vector<ServiceWorkerDatabase::RegistrationData> RegistrationList;
205 typedef std::map<int64, scoped_refptr<ServiceWorkerRegistration> >
206 RegistrationRefsById;
207 typedef base::Callback<void(
208 InitialData* data,
209 ServiceWorkerDatabase::Status status)> InitializeCallback;
210 typedef base::Callback<void(
211 const GURL& origin,
212 const ServiceWorkerDatabase::RegistrationData& deleted_version_data,
213 const std::vector<int64>& newly_purgeable_resources,
214 ServiceWorkerDatabase::Status status)> WriteRegistrationCallback;
215 typedef base::Callback<void(
216 bool origin_is_deletable,
217 const ServiceWorkerDatabase::RegistrationData& deleted_version_data,
218 const std::vector<int64>& newly_purgeable_resources,
219 ServiceWorkerDatabase::Status status)> DeleteRegistrationCallback;
220 typedef base::Callback<void(
221 const ServiceWorkerDatabase::RegistrationData& data,
222 const ResourceList& resources,
223 ServiceWorkerDatabase::Status status)> FindInDBCallback;
224 typedef base::Callback<void(const std::vector<int64>& resource_ids,
225 ServiceWorkerDatabase::Status status)>
226 GetResourcesCallback;
228 ServiceWorkerStorage(
229 const base::FilePath& path,
230 base::WeakPtr<ServiceWorkerContextCore> context,
231 scoped_ptr<ServiceWorkerDatabaseTaskManager> database_task_manager,
232 const scoped_refptr<base::SingleThreadTaskRunner>& disk_cache_thread,
233 storage::QuotaManagerProxy* quota_manager_proxy,
234 storage::SpecialStoragePolicy* special_storage_policy);
236 base::FilePath GetDatabasePath();
237 base::FilePath GetDiskCachePath();
239 bool LazyInitialize(
240 const base::Closure& callback);
241 void DidReadInitialData(
242 InitialData* data,
243 ServiceWorkerDatabase::Status status);
244 void DidFindRegistrationForDocument(
245 const GURL& document_url,
246 const FindRegistrationCallback& callback,
247 int64 callback_id,
248 const ServiceWorkerDatabase::RegistrationData& data,
249 const ResourceList& resources,
250 ServiceWorkerDatabase::Status status);
251 void DidFindRegistrationForPattern(
252 const GURL& scope,
253 const FindRegistrationCallback& callback,
254 const ServiceWorkerDatabase::RegistrationData& data,
255 const ResourceList& resources,
256 ServiceWorkerDatabase::Status status);
257 void DidFindRegistrationForId(
258 const FindRegistrationCallback& callback,
259 const ServiceWorkerDatabase::RegistrationData& data,
260 const ResourceList& resources,
261 ServiceWorkerDatabase::Status status);
262 void DidGetAllRegistrations(
263 const GetAllRegistrationInfosCallback& callback,
264 RegistrationList* registrations,
265 ServiceWorkerDatabase::Status status);
266 void DidStoreRegistration(
267 const StatusCallback& callback,
268 const ServiceWorkerDatabase::RegistrationData& new_version,
269 const GURL& origin,
270 const ServiceWorkerDatabase::RegistrationData& deleted_version,
271 const std::vector<int64>& newly_purgeable_resources,
272 ServiceWorkerDatabase::Status status);
273 void DidUpdateToActiveState(
274 const StatusCallback& callback,
275 ServiceWorkerDatabase::Status status);
276 void DidDeleteRegistration(
277 const DidDeleteRegistrationParams& params,
278 bool origin_is_deletable,
279 const ServiceWorkerDatabase::RegistrationData& deleted_version,
280 const std::vector<int64>& newly_purgeable_resources,
281 ServiceWorkerDatabase::Status status);
282 void ReturnFoundRegistration(
283 const FindRegistrationCallback& callback,
284 const ServiceWorkerDatabase::RegistrationData& data,
285 const ResourceList& resources);
287 scoped_refptr<ServiceWorkerRegistration> GetOrCreateRegistration(
288 const ServiceWorkerDatabase::RegistrationData& data,
289 const ResourceList& resources);
290 ServiceWorkerRegistration* FindInstallingRegistrationForDocument(
291 const GURL& document_url);
292 ServiceWorkerRegistration* FindInstallingRegistrationForPattern(
293 const GURL& scope);
294 ServiceWorkerRegistration* FindInstallingRegistrationForId(
295 int64 registration_id);
297 // Lazy disk_cache getter.
298 ServiceWorkerDiskCache* disk_cache();
299 void OnDiskCacheInitialized(int rv);
301 void StartPurgingResources(const std::vector<int64>& ids);
302 void StartPurgingResources(const ResourceList& resources);
303 void ContinuePurgingResources();
304 void PurgeResource(int64 id);
305 void OnResourcePurged(int64 id, int rv);
307 // Deletes purgeable and uncommitted resources left over from the previous
308 // browser session. This must be called once per session before any database
309 // operation that may mutate the purgeable or uncommitted resource lists.
310 void DeleteStaleResources();
311 void DidCollectStaleResources(const std::vector<int64>& stale_resource_ids,
312 ServiceWorkerDatabase::Status status);
314 void ClearSessionOnlyOrigins();
316 // Static cross-thread helpers.
317 static void CollectStaleResourcesFromDB(
318 ServiceWorkerDatabase* database,
319 scoped_refptr<base::SequencedTaskRunner> original_task_runner,
320 const GetResourcesCallback& callback);
321 static void ReadInitialDataFromDB(
322 ServiceWorkerDatabase* database,
323 scoped_refptr<base::SequencedTaskRunner> original_task_runner,
324 const InitializeCallback& callback);
325 static void DeleteRegistrationFromDB(
326 ServiceWorkerDatabase* database,
327 scoped_refptr<base::SequencedTaskRunner> original_task_runner,
328 int64 registration_id,
329 const GURL& origin,
330 const DeleteRegistrationCallback& callback);
331 static void WriteRegistrationInDB(
332 ServiceWorkerDatabase* database,
333 scoped_refptr<base::SequencedTaskRunner> original_task_runner,
334 const ServiceWorkerDatabase::RegistrationData& registration,
335 const ResourceList& resources,
336 const WriteRegistrationCallback& callback);
337 static void FindForDocumentInDB(
338 ServiceWorkerDatabase* database,
339 scoped_refptr<base::SequencedTaskRunner> original_task_runner,
340 const GURL& document_url,
341 const FindInDBCallback& callback);
342 static void FindForPatternInDB(
343 ServiceWorkerDatabase* database,
344 scoped_refptr<base::SequencedTaskRunner> original_task_runner,
345 const GURL& scope,
346 const FindInDBCallback& callback);
347 static void FindForIdInDB(
348 ServiceWorkerDatabase* database,
349 scoped_refptr<base::SequencedTaskRunner> original_task_runner,
350 int64 registration_id,
351 const GURL& origin,
352 const FindInDBCallback& callback);
353 static void DeleteAllDataForOriginsFromDB(
354 ServiceWorkerDatabase* database,
355 const std::set<GURL>& origins);
357 void ScheduleDeleteAndStartOver();
358 void DidDeleteDatabase(
359 const StatusCallback& callback,
360 ServiceWorkerDatabase::Status status);
361 void DidDeleteDiskCache(
362 const StatusCallback& callback,
363 bool result);
365 // For finding registrations being installed or uninstalled.
366 RegistrationRefsById installing_registrations_;
367 RegistrationRefsById uninstalling_registrations_;
369 // Origins having registations.
370 std::set<GURL> registered_origins_;
372 // Pending database tasks waiting for initialization.
373 std::vector<base::Closure> pending_tasks_;
375 int64 next_registration_id_;
376 int64 next_version_id_;
377 int64 next_resource_id_;
379 enum State {
380 UNINITIALIZED,
381 INITIALIZING,
382 INITIALIZED,
383 DISABLED,
385 State state_;
387 base::FilePath path_;
388 base::WeakPtr<ServiceWorkerContextCore> context_;
390 // Only accessed using |database_task_manager_|.
391 scoped_ptr<ServiceWorkerDatabase> database_;
393 scoped_ptr<ServiceWorkerDatabaseTaskManager> database_task_manager_;
394 scoped_refptr<base::SingleThreadTaskRunner> disk_cache_thread_;
395 scoped_refptr<storage::QuotaManagerProxy> quota_manager_proxy_;
396 scoped_refptr<storage::SpecialStoragePolicy> special_storage_policy_;
397 scoped_ptr<ServiceWorkerDiskCache> disk_cache_;
398 std::deque<int64> purgeable_resource_ids_;
399 bool is_purge_pending_;
400 bool has_checked_for_stale_resources_;
401 std::set<int64> pending_deletions_;
403 base::WeakPtrFactory<ServiceWorkerStorage> weak_factory_;
405 DISALLOW_COPY_AND_ASSIGN(ServiceWorkerStorage);
408 } // namespace content
410 #endif // CONTENT_BROWSER_SERVICE_WORKER_SERVICE_WORKER_STORAGE_H_