OLD | NEW |
---|---|
1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #import "ios/web/public/crw_browsing_data_store.h" | 5 #import "ios/web/public/crw_browsing_data_store.h" |
6 | 6 |
7 #import <Foundation/Foundation.h> | 7 #import <Foundation/Foundation.h> |
8 | 8 |
9 #import "base/ios/weak_nsobject.h" | 9 #import "base/ios/weak_nsobject.h" |
10 #include "base/logging.h" | 10 #include "base/logging.h" |
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
43 // |browsingDataType|. | 43 // |browsingDataType|. |
44 - (id<CRWBrowsingDataManager>)browsingDataManagerForBrowsingDataType: | 44 - (id<CRWBrowsingDataManager>)browsingDataManagerForBrowsingDataType: |
45 (NSString*)browsingDataType; | 45 (NSString*)browsingDataType; |
46 // Returns an array of browsing data managers for all the |browsingDataType|. | 46 // Returns an array of browsing data managers for all the |browsingDataType|. |
47 - (NSArray*)browsingDataManagersForBrowsingDataTypes:(NSSet*)browsingDataTypes; | 47 - (NSArray*)browsingDataManagersForBrowsingDataTypes:(NSSet*)browsingDataTypes; |
48 | 48 |
49 // Redefined to be read-write. Must be called from the main thread. | 49 // Redefined to be read-write. Must be called from the main thread. |
50 @property(nonatomic, assign) CRWBrowsingDataStoreMode mode; | 50 @property(nonatomic, assign) CRWBrowsingDataStoreMode mode; |
51 // Sets the mode iff there are no more stash or restore operations that are | 51 // Sets the mode iff there are no more stash or restore operations that are |
52 // still pending. |mode| can only be either |ACTIVE| or |INACTIVE|. | 52 // still pending. |mode| can only be either |ACTIVE| or |INACTIVE|. |
53 - (void)setModeIfNotStashingOrRestoring:(CRWBrowsingDataStoreMode)mode; | 53 // Returns YES if the mode change was successful. |
54 - (BOOL)setModeIfNoPendingStashOrRestoreOperations: | |
55 (CRWBrowsingDataStoreMode)mode; | |
56 | |
57 // The number of stash or restore operations that are still pending. | |
58 @property(nonatomic, assign) NSUInteger numberOfPendingStashOrRestoreOperations; | |
54 | 59 |
55 // Performs operations of type |operationType| on each of the | 60 // Performs operations of type |operationType| on each of the |
56 // |browsingDataManagers|. | 61 // |browsingDataManagers|. |
57 // The kind of operations are: | 62 // The kind of operations are: |
58 // 1) STASH: Stash operation involves stashing browsing data that web views | 63 // 1) STASH: Stash operation involves stashing browsing data that web views |
59 // (UIWebViews and WKWebViews) create to the associated BrowserState's state | 64 // (UIWebViews and WKWebViews) create to the associated BrowserState's state |
60 // path. | 65 // path. |
61 // 2) RESTORE: Restore operation involves restoring browsing data from the | 66 // 2) RESTORE: Restore operation involves restoring browsing data from the |
62 // associated BrowserState's state path so that web views (UIWebViews and | 67 // associated BrowserState's state path so that web views (UIWebViews and |
63 // WKWebViews) can read from them. | 68 // WKWebViews) can read from them. |
(...skipping 21 matching lines...) Expand all Loading... | |
85 @implementation CRWBrowsingDataStore { | 90 @implementation CRWBrowsingDataStore { |
86 web::BrowserState* _browserState; // Weak, owns this object. | 91 web::BrowserState* _browserState; // Weak, owns this object. |
87 // The mode of the CRWBrowsingDataStore. | 92 // The mode of the CRWBrowsingDataStore. |
88 CRWBrowsingDataStoreMode _mode; | 93 CRWBrowsingDataStoreMode _mode; |
89 // The dictionary that maps a browsing data type to its | 94 // The dictionary that maps a browsing data type to its |
90 // CRWBrowsingDataManager. | 95 // CRWBrowsingDataManager. |
91 base::scoped_nsobject<NSDictionary> _browsingDataTypeMap; | 96 base::scoped_nsobject<NSDictionary> _browsingDataTypeMap; |
92 // The last operation that was enqueued to be run. Can be stash, restore or a | 97 // The last operation that was enqueued to be run. Can be stash, restore or a |
93 // delete operation. | 98 // delete operation. |
94 base::scoped_nsobject<NSOperation> _lastDispatchedOperation; | 99 base::scoped_nsobject<NSOperation> _lastDispatchedOperation; |
95 // The last stash or restore operations that was dispatched to be run. | 100 // The number of stash or restore operations that are still pending. If this |
96 base::scoped_nsobject<NSOperation> _lastDispatchedStashOrRestoreOperation; | 101 // value > 0 the mode of the CRWBrowsingDataStore is SYNCHRONIZING. The mode |
102 // can be made ACTIVE or INACTIVE only be set when this value is 0. | |
103 NSUInteger _numberOfPendingStashOrRestoreOperations; | |
97 } | 104 } |
98 | 105 |
99 + (NSOperationQueue*)operationQueueForStashAndRestoreOperations { | 106 + (NSOperationQueue*)operationQueueForStashAndRestoreOperations { |
100 static dispatch_once_t onceToken = 0; | 107 static dispatch_once_t onceToken = 0; |
101 static NSOperationQueue* operationQueueForStashAndRestoreOperations = nil; | 108 static NSOperationQueue* operationQueueForStashAndRestoreOperations = nil; |
102 dispatch_once(&onceToken, ^{ | 109 dispatch_once(&onceToken, ^{ |
103 operationQueueForStashAndRestoreOperations = | 110 operationQueueForStashAndRestoreOperations = |
104 [[NSOperationQueue alloc] init]; | 111 [[NSOperationQueue alloc] init]; |
105 [operationQueueForStashAndRestoreOperations | 112 [operationQueueForStashAndRestoreOperations |
106 setMaxConcurrentOperationCount:1U]; | 113 setMaxConcurrentOperationCount:1U]; |
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
167 - (id<CRWBrowsingDataManager>)browsingDataManagerForBrowsingDataType: | 174 - (id<CRWBrowsingDataManager>)browsingDataManagerForBrowsingDataType: |
168 (NSString*)browsingDataType { | 175 (NSString*)browsingDataType { |
169 return [_browsingDataTypeMap objectForKey:browsingDataType]; | 176 return [_browsingDataTypeMap objectForKey:browsingDataType]; |
170 } | 177 } |
171 | 178 |
172 - (NSArray*)browsingDataManagersForBrowsingDataTypes:(NSSet*)browsingDataTypes { | 179 - (NSArray*)browsingDataManagersForBrowsingDataTypes:(NSSet*)browsingDataTypes { |
173 return [_browsingDataTypeMap objectsForKeys:[browsingDataTypes allObjects] | 180 return [_browsingDataTypeMap objectsForKeys:[browsingDataTypes allObjects] |
174 notFoundMarker:[NSNull null]]; | 181 notFoundMarker:[NSNull null]]; |
175 } | 182 } |
176 | 183 |
184 + (BOOL)automaticallyNotifiesObserversForKey:(NSString*)key { | |
185 // It is necessary to override this for |mode| because the default KVO | |
186 // behavior in NSObject is to fire a notification irrespective of if an actual | |
187 // change was made to the ivar or not. The |mode| property needs fine grained | |
188 // control over the actual notifications being fired since observers need to | |
189 // be notified iff the |mode| actually changed. | |
190 if ([key isEqual:@"mode"]) { | |
191 return NO; | |
192 } | |
193 return [super automaticallyNotifiesObserversForKey:(NSString*)key]; | |
194 } | |
195 | |
177 - (CRWBrowsingDataStoreMode)mode { | 196 - (CRWBrowsingDataStoreMode)mode { |
178 DCHECK([NSThread isMainThread]); | 197 DCHECK([NSThread isMainThread]); |
179 return _mode; | 198 return _mode; |
180 } | 199 } |
181 | 200 |
182 - (void)setMode:(CRWBrowsingDataStoreMode)mode { | 201 - (void)setMode:(CRWBrowsingDataStoreMode)mode { |
183 DCHECK([NSThread isMainThread]); | 202 DCHECK([NSThread isMainThread]); |
203 if (_mode == mode) { | |
204 return; | |
205 } | |
206 if (mode == ACTIVE || mode == INACTIVE) { | |
207 DCHECK(!_numberOfPendingStashOrRestoreOperations); | |
Eugene But (OOO till 7-30)
2015/05/29 21:14:26
Optional NIT:
s/_numberOfPendingStashOrRestoreOpe
shreyasv1
2015/05/29 22:22:56
Done.
| |
208 } | |
209 [self willChangeValueForKey:@"mode"]; | |
184 _mode = mode; | 210 _mode = mode; |
211 [self didChangeValueForKey:@"mode"]; | |
185 } | 212 } |
186 | 213 |
187 - (void)setModeIfNotStashingOrRestoring:(CRWBrowsingDataStoreMode)mode { | 214 - (BOOL)setModeIfNoPendingStashOrRestoreOperations: |
215 (CRWBrowsingDataStoreMode)mode { | |
188 DCHECK([NSThread isMainThread]); | 216 DCHECK([NSThread isMainThread]); |
189 DCHECK_NE(SYNCHRONIZING, mode); | 217 DCHECK_NE(SYNCHRONIZING, mode); |
190 if ([_lastDispatchedStashOrRestoreOperation isFinished]) { | 218 |
191 _mode = mode; | 219 if (!self.numberOfPendingStashOrRestoreOperations) { |
220 [self setMode:mode]; | |
221 return YES; | |
192 } | 222 } |
223 return NO; | |
193 } | 224 } |
194 | 225 |
195 - (void)makeActiveWithCompletionHandler:(ProceduralBlock)completionHandler { | 226 - (NSUInteger)numberOfPendingStashOrRestoreOperations { |
227 DCHECK([NSThread isMainThread]); | |
228 return _numberOfPendingStashOrRestoreOperations; | |
229 } | |
230 | |
231 - (void)setNumberOfPendingStashOrRestoreOperations: | |
232 (NSUInteger)numberOfPendingStashOrRestoreOperations { | |
233 DCHECK([NSThread isMainThread]); | |
234 _numberOfPendingStashOrRestoreOperations = | |
235 numberOfPendingStashOrRestoreOperations; | |
236 } | |
237 | |
238 - (void)makeActiveWithCompletionHandler: | |
239 (void (^)(BOOL success))completionHandler { | |
196 DCHECK([NSThread isMainThread]); | 240 DCHECK([NSThread isMainThread]); |
197 | 241 |
198 base::WeakNSObject<CRWBrowsingDataStore> weakSelf(self); | 242 base::WeakNSObject<CRWBrowsingDataStore> weakSelf(self); |
199 [self performOperationWithType:RESTORE | 243 [self performOperationWithType:RESTORE |
200 browsingDataManagers:[self allBrowsingDataManagers] | 244 browsingDataManagers:[self allBrowsingDataManagers] |
201 completionHandler:^{ | 245 completionHandler:^{ |
202 [weakSelf setModeIfNotStashingOrRestoring:ACTIVE]; | 246 BOOL modeUpdateWasSuccessful = [weakSelf |
247 setModeIfNoPendingStashOrRestoreOperations:ACTIVE]; | |
203 if (completionHandler) { | 248 if (completionHandler) { |
Eugene But (OOO till 7-30)
2015/05/29 21:14:26
Can you rename setModeIfNoPendingStashOrRestoreOpe
shreyasv1
2015/05/29 22:22:56
I actually tried to consolidate the logic with a m
Eugene But (OOO till 7-30)
2015/05/29 22:38:28
You proposal (finalizeChangeToMode:callCompletionH
shreyasv1
2015/06/01 18:31:54
Done.
| |
204 completionHandler(); | 249 completionHandler(modeUpdateWasSuccessful); |
205 } | 250 } |
206 }]; | 251 }]; |
207 } | 252 } |
208 | 253 |
209 - (void)makeInactiveWithCompletionHandler:(ProceduralBlock)completionHandler { | 254 - (void)makeInactiveWithCompletionHandler: |
255 (void (^)(BOOL success))completionHandler { | |
210 DCHECK([NSThread isMainThread]); | 256 DCHECK([NSThread isMainThread]); |
211 | 257 |
212 base::WeakNSObject<CRWBrowsingDataStore> weakSelf(self); | 258 base::WeakNSObject<CRWBrowsingDataStore> weakSelf(self); |
213 [self performOperationWithType:STASH | 259 [self performOperationWithType:STASH |
214 browsingDataManagers:[self allBrowsingDataManagers] | 260 browsingDataManagers:[self allBrowsingDataManagers] |
215 completionHandler:^{ | 261 completionHandler:^{ |
216 [weakSelf setModeIfNotStashingOrRestoring:INACTIVE]; | 262 BOOL modeUpdateWasSuccessful = [weakSelf |
263 setModeIfNoPendingStashOrRestoreOperations:INACTIVE]; | |
217 if (completionHandler) { | 264 if (completionHandler) { |
218 completionHandler(); | 265 completionHandler(modeUpdateWasSuccessful); |
219 } | 266 } |
220 }]; | 267 }]; |
221 } | 268 } |
222 | 269 |
223 - (void)removeDataOfTypes:(NSSet*)browsingDataTypes | 270 - (void)removeDataOfTypes:(NSSet*)browsingDataTypes |
224 completionHandler:(ProceduralBlock)completionHandler { | 271 completionHandler:(ProceduralBlock)completionHandler { |
225 DCHECK([NSThread isMainThread]); | 272 DCHECK([NSThread isMainThread]); |
226 | 273 |
227 NSArray* browsingDataManagers = | 274 NSArray* browsingDataManagers = |
228 [self browsingDataManagersForBrowsingDataTypes:browsingDataTypes]; | 275 [self browsingDataManagersForBrowsingDataTypes:browsingDataTypes]; |
(...skipping 28 matching lines...) Expand all Loading... | |
257 selector = @selector(restoreData); | 304 selector = @selector(restoreData); |
258 break; | 305 break; |
259 case REMOVE: | 306 case REMOVE: |
260 selector = @selector(removeData); | 307 selector = @selector(removeData); |
261 break; | 308 break; |
262 default: | 309 default: |
263 NOTREACHED(); | 310 NOTREACHED(); |
264 break; | 311 break; |
265 }; | 312 }; |
266 | 313 |
314 if (operationType == RESTORE || operationType == STASH) { | |
315 [self setMode:SYNCHRONIZING]; | |
316 ++self.numberOfPendingStashOrRestoreOperations; | |
317 completionHandler = ^{ | |
318 --self.numberOfPendingStashOrRestoreOperations; | |
319 completionHandler(); | |
320 }; | |
321 } | |
322 | |
267 id callCompletionHandlerOnMainThread = ^{ | 323 id callCompletionHandlerOnMainThread = ^{ |
268 // This can be called on a background thread, hence the need to bounce to | 324 // This is called on a background thread, hence the need to bounce to the |
269 // the main thread. | 325 // main thread. |
270 dispatch_async(dispatch_get_main_queue(), ^{ | 326 dispatch_async(dispatch_get_main_queue(), ^{ |
271 completionHandler(); | 327 completionHandler(); |
272 }); | 328 }); |
273 }; | 329 }; |
274 base::scoped_nsobject<NSOperation> operation([self | 330 base::scoped_nsobject<NSOperation> operation([self |
275 newOperationWithBrowsingDataManagers:browsingDataManagers | 331 newOperationWithBrowsingDataManagers:browsingDataManagers |
276 selector:selector | 332 selector:selector |
277 completionHandler:callCompletionHandlerOnMainThread]); | 333 completionHandler:callCompletionHandlerOnMainThread]); |
278 | 334 |
279 if (operationType == RESTORE || operationType == STASH) { | |
280 _mode = SYNCHRONIZING; | |
281 _lastDispatchedStashOrRestoreOperation.reset([operation retain]); | |
282 } | |
283 | 335 |
284 NSOperationQueue* queue = nil; | 336 NSOperationQueue* queue = nil; |
285 switch (operationType) { | 337 switch (operationType) { |
286 case STASH: | 338 case STASH: |
287 case RESTORE: | 339 case RESTORE: |
288 queue = [CRWBrowsingDataStore operationQueueForStashAndRestoreOperations]; | 340 queue = [CRWBrowsingDataStore operationQueueForStashAndRestoreOperations]; |
289 break; | 341 break; |
290 case REMOVE: | 342 case REMOVE: |
291 queue = [CRWBrowsingDataStore operationQueueForRemoveOperations]; | 343 queue = [CRWBrowsingDataStore operationQueueForRemoveOperations]; |
292 break; | 344 break; |
(...skipping 27 matching lines...) Expand all Loading... | |
320 DCHECK(queue); | 372 DCHECK(queue); |
321 | 373 |
322 if (_lastDispatchedOperation) { | 374 if (_lastDispatchedOperation) { |
323 [operation addDependency:_lastDispatchedOperation]; | 375 [operation addDependency:_lastDispatchedOperation]; |
324 } | 376 } |
325 _lastDispatchedOperation.reset([operation retain]); | 377 _lastDispatchedOperation.reset([operation retain]); |
326 [queue addOperation:operation]; | 378 [queue addOperation:operation]; |
327 } | 379 } |
328 | 380 |
329 @end | 381 @end |
OLD | NEW |