OLD | NEW |
| (Empty) |
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 #ifndef WEBKIT_BROWSER_APPCACHE_APPCACHE_SERVICE_IMPL_H_ | |
6 #define WEBKIT_BROWSER_APPCACHE_APPCACHE_SERVICE_IMPL_H_ | |
7 | |
8 #include <map> | |
9 #include <set> | |
10 | |
11 #include "base/gtest_prod_util.h" | |
12 #include "base/memory/ref_counted.h" | |
13 #include "base/memory/scoped_ptr.h" | |
14 #include "base/observer_list.h" | |
15 #include "base/time/time.h" | |
16 #include "base/timer/timer.h" | |
17 #include "net/base/completion_callback.h" | |
18 #include "net/base/net_errors.h" | |
19 #include "webkit/browser/appcache/appcache_service.h" | |
20 #include "webkit/browser/quota/quota_manager_proxy.h" | |
21 #include "webkit/browser/webkit_storage_browser_export.h" | |
22 #include "webkit/common/appcache/appcache_interfaces.h" | |
23 | |
24 namespace net { | |
25 class URLRequestContext; | |
26 } // namespace net | |
27 | |
28 namespace base { | |
29 class FilePath; | |
30 class MessageLoopProxy; | |
31 } | |
32 | |
33 namespace content { | |
34 FORWARD_DECLARE_TEST(AppCacheServiceImplTest, ScheduleReinitialize); | |
35 class AppCacheServiceImplTest; | |
36 class AppCacheStorageImplTest; | |
37 } | |
38 | |
39 namespace quota { | |
40 class SpecialStoragePolicy; | |
41 } | |
42 | |
43 namespace appcache { | |
44 | |
45 class AppCacheBackendImpl; | |
46 class AppCacheExecutableHandlerFactory; | |
47 class AppCacheQuotaClient; | |
48 class AppCachePolicy; | |
49 class AppCacheStorage; | |
50 | |
51 // Refcounted container to manage the lifetime of the old storage instance | |
52 // during Reinitialization. | |
53 class WEBKIT_STORAGE_BROWSER_EXPORT AppCacheStorageReference | |
54 : public base::RefCounted<AppCacheStorageReference> { | |
55 public: | |
56 AppCacheStorage* storage() const { return storage_.get(); } | |
57 private: | |
58 friend class AppCacheServiceImpl; | |
59 friend class base::RefCounted<AppCacheStorageReference>; | |
60 AppCacheStorageReference(scoped_ptr<AppCacheStorage> storage); | |
61 ~AppCacheStorageReference(); | |
62 | |
63 scoped_ptr<AppCacheStorage> storage_; | |
64 }; | |
65 | |
66 // Class that manages the application cache service. Sends notifications | |
67 // to many frontends. One instance per user-profile. Each instance has | |
68 // exclusive access to its cache_directory on disk. | |
69 class WEBKIT_STORAGE_BROWSER_EXPORT AppCacheServiceImpl | |
70 : public AppCacheService { | |
71 public: | |
72 | |
73 class WEBKIT_STORAGE_BROWSER_EXPORT Observer { | |
74 public: | |
75 // An observer method to inform consumers of reinitialzation. Managing | |
76 // the lifetime of the old storage instance is a delicate process. | |
77 // Consumers can keep the old disabled instance alive by hanging on to the | |
78 // ref provided. | |
79 virtual void OnServiceReinitialized( | |
80 AppCacheStorageReference* old_storage_ref) = 0; | |
81 virtual ~Observer() {} | |
82 }; | |
83 | |
84 // If not using quota management, the proxy may be NULL. | |
85 explicit AppCacheServiceImpl(quota::QuotaManagerProxy* quota_manager_proxy); | |
86 virtual ~AppCacheServiceImpl(); | |
87 | |
88 void Initialize(const base::FilePath& cache_directory, | |
89 base::MessageLoopProxy* db_thread, | |
90 base::MessageLoopProxy* cache_thread); | |
91 | |
92 void AddObserver(Observer* observer) { | |
93 observers_.AddObserver(observer); | |
94 } | |
95 | |
96 void RemoveObserver(Observer* observer) { | |
97 observers_.RemoveObserver(observer); | |
98 } | |
99 | |
100 // For use in catastrophic failure modes to reboot the appcache system | |
101 // without relaunching the browser. | |
102 void ScheduleReinitialize(); | |
103 | |
104 // AppCacheService implementation: | |
105 virtual void CanHandleMainResourceOffline( | |
106 const GURL& url, | |
107 const GURL& first_party, | |
108 const net::CompletionCallback& callback) OVERRIDE; | |
109 virtual void GetAllAppCacheInfo( | |
110 AppCacheInfoCollection* collection, | |
111 const net::CompletionCallback& callback) OVERRIDE; | |
112 virtual void DeleteAppCacheGroup( | |
113 const GURL& manifest_url, | |
114 const net::CompletionCallback& callback) OVERRIDE; | |
115 | |
116 // Deletes all appcaches for the origin, 'callback' is invoked upon | |
117 // completion. This method always completes asynchronously. | |
118 // (virtual for unit testing) | |
119 virtual void DeleteAppCachesForOrigin( | |
120 const GURL& origin, const net::CompletionCallback& callback); | |
121 | |
122 // Checks the integrity of 'response_id' by reading the headers and data. | |
123 // If it cannot be read, the cache group for 'manifest_url' is deleted. | |
124 void CheckAppCacheResponse(const GURL& manifest_url, int64 cache_id, | |
125 int64 response_id); | |
126 | |
127 // Context for use during cache updates, should only be accessed | |
128 // on the IO thread. We do NOT add a reference to the request context, | |
129 // it is the callers responsibility to ensure that the pointer | |
130 // remains valid while set. | |
131 net::URLRequestContext* request_context() const { return request_context_; } | |
132 void set_request_context(net::URLRequestContext* context) { | |
133 request_context_ = context; | |
134 } | |
135 | |
136 // The appcache policy, may be null, in which case access is always allowed. | |
137 // The service does NOT assume ownership of the policy, it is the callers | |
138 // responsibility to ensure that the pointer remains valid while set. | |
139 AppCachePolicy* appcache_policy() const { return appcache_policy_; } | |
140 void set_appcache_policy(AppCachePolicy* policy) { | |
141 appcache_policy_ = policy; | |
142 } | |
143 | |
144 // The factory may be null, in which case invocations of exe handlers | |
145 // will result in an error response. | |
146 // The service does NOT assume ownership of the factory, it is the callers | |
147 // responsibility to ensure that the pointer remains valid while set. | |
148 AppCacheExecutableHandlerFactory* handler_factory() const { | |
149 return handler_factory_; | |
150 } | |
151 void set_handler_factory( | |
152 AppCacheExecutableHandlerFactory* factory) { | |
153 handler_factory_ = factory; | |
154 } | |
155 | |
156 quota::SpecialStoragePolicy* special_storage_policy() const { | |
157 return special_storage_policy_.get(); | |
158 } | |
159 void set_special_storage_policy(quota::SpecialStoragePolicy* policy); | |
160 | |
161 quota::QuotaManagerProxy* quota_manager_proxy() const { | |
162 return quota_manager_proxy_.get(); | |
163 } | |
164 | |
165 AppCacheQuotaClient* quota_client() const { | |
166 return quota_client_; | |
167 } | |
168 | |
169 // Each child process in chrome uses a distinct backend instance. | |
170 // See chrome/browser/AppCacheDispatcherHost. | |
171 void RegisterBackend(AppCacheBackendImpl* backend_impl); | |
172 void UnregisterBackend(AppCacheBackendImpl* backend_impl); | |
173 AppCacheBackendImpl* GetBackend(int id) const { | |
174 BackendMap::const_iterator it = backends_.find(id); | |
175 return (it != backends_.end()) ? it->second : NULL; | |
176 } | |
177 | |
178 AppCacheStorage* storage() const { return storage_.get(); } | |
179 | |
180 // Disables the exit-time deletion of session-only data. | |
181 void set_force_keep_session_state() { force_keep_session_state_ = true; } | |
182 bool force_keep_session_state() const { return force_keep_session_state_; } | |
183 | |
184 protected: | |
185 friend class content::AppCacheServiceImplTest; | |
186 friend class content::AppCacheStorageImplTest; | |
187 FRIEND_TEST_ALL_PREFIXES(content::AppCacheServiceImplTest, | |
188 ScheduleReinitialize); | |
189 | |
190 class AsyncHelper; | |
191 class CanHandleOfflineHelper; | |
192 class DeleteHelper; | |
193 class DeleteOriginHelper; | |
194 class GetInfoHelper; | |
195 class CheckResponseHelper; | |
196 | |
197 typedef std::set<AsyncHelper*> PendingAsyncHelpers; | |
198 typedef std::map<int, AppCacheBackendImpl*> BackendMap; | |
199 | |
200 void Reinitialize(); | |
201 | |
202 base::FilePath cache_directory_; | |
203 scoped_refptr<base::MessageLoopProxy> db_thread_; | |
204 scoped_refptr<base::MessageLoopProxy> cache_thread_; | |
205 AppCachePolicy* appcache_policy_; | |
206 AppCacheQuotaClient* quota_client_; | |
207 AppCacheExecutableHandlerFactory* handler_factory_; | |
208 scoped_ptr<AppCacheStorage> storage_; | |
209 scoped_refptr<quota::SpecialStoragePolicy> special_storage_policy_; | |
210 scoped_refptr<quota::QuotaManagerProxy> quota_manager_proxy_; | |
211 PendingAsyncHelpers pending_helpers_; | |
212 BackendMap backends_; // One 'backend' per child process. | |
213 // Context for use during cache updates. | |
214 net::URLRequestContext* request_context_; | |
215 // If true, nothing (not even session-only data) should be deleted on exit. | |
216 bool force_keep_session_state_; | |
217 base::Time last_reinit_time_; | |
218 base::TimeDelta next_reinit_delay_; | |
219 base::OneShotTimer<AppCacheServiceImpl> reinit_timer_; | |
220 ObserverList<Observer> observers_; | |
221 | |
222 DISALLOW_COPY_AND_ASSIGN(AppCacheServiceImpl); | |
223 }; | |
224 | |
225 } // namespace appcache | |
226 | |
227 #endif // WEBKIT_BROWSER_APPCACHE_APPCACHE_SERVICE_IMPL_H_ | |
OLD | NEW |