OLD | NEW |
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 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 | 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 #include "content/browser/geofencing/geofencing_manager.h" | 5 #include "content/browser/geofencing/geofencing_manager.h" |
6 | 6 |
7 #include <algorithm> | 7 #include <algorithm> |
8 | 8 |
9 #include "base/callback.h" | 9 #include "base/callback.h" |
10 #include "content/browser/geofencing/geofencing_service.h" | 10 #include "content/browser/geofencing/geofencing_service.h" |
11 #include "content/browser/service_worker/service_worker_context_wrapper.h" | 11 #include "content/browser/service_worker/service_worker_context_wrapper.h" |
| 12 #include "content/public/browser/browser_context.h" |
12 #include "content/public/browser/browser_thread.h" | 13 #include "content/public/browser/browser_thread.h" |
| 14 #include "content/public/browser/storage_partition.h" |
13 #include "third_party/WebKit/public/platform/WebCircularGeofencingRegion.h" | 15 #include "third_party/WebKit/public/platform/WebCircularGeofencingRegion.h" |
| 16 #include "third_party/WebKit/public/platform/WebGeofencingEventType.h" |
| 17 #include "url/gurl.h" |
14 | 18 |
15 namespace content { | 19 namespace content { |
16 | 20 |
17 struct GeofencingManager::Registration { | 21 struct GeofencingManager::Registration { |
18 Registration(int64 service_worker_registration_id, | 22 Registration(int64 service_worker_registration_id, |
19 const GURL& service_worker_origin, | 23 const GURL& service_worker_origin, |
20 const std::string& region_id, | 24 const std::string& region_id, |
21 const blink::WebCircularGeofencingRegion& region, | 25 const blink::WebCircularGeofencingRegion& region, |
22 const StatusCallback& callback, | 26 const StatusCallback& callback, |
23 int64 geofencing_registration_id); | 27 int64 geofencing_registration_id); |
24 | |
25 int64 service_worker_registration_id; | 28 int64 service_worker_registration_id; |
26 GURL service_worker_origin; | 29 GURL service_worker_origin; |
27 std::string region_id; | 30 std::string region_id; |
28 blink::WebCircularGeofencingRegion region; | 31 blink::WebCircularGeofencingRegion region; |
29 | 32 |
30 // Registration ID as returned by the |GeofencingService|. | 33 // Registration ID as returned by the |GeofencingService|. |
31 int64 geofencing_registration_id; | 34 int64 geofencing_registration_id; |
32 | 35 |
33 // Callback to call when registration is completed. This field is reset when | 36 // Callback to call when registration is completed. This field is reset when |
34 // registration is complete. | 37 // registration is complete. |
35 StatusCallback registration_callback; | 38 StatusCallback registration_callback; |
36 | 39 |
37 // Returns true if registration has been completed, and thus should be | 40 // Returns true if registration has been completed, and thus should be |
38 // included in calls to GetRegisteredRegions. | 41 // included in calls to GetRegisteredRegions. |
39 bool is_active() const { return registration_callback.is_null(); } | 42 bool is_active() const { return registration_callback.is_null(); } |
40 }; | 43 }; |
41 | 44 |
42 GeofencingManager::Registration::Registration( | 45 GeofencingManager::Registration::Registration( |
43 int64 service_worker_registration_id, | 46 int64 service_worker_registration_id, |
44 const GURL& service_worker_origin, | 47 const GURL& service_worker_origin, |
45 const std::string& region_id, | 48 const std::string& region_id, |
46 const blink::WebCircularGeofencingRegion& region, | 49 const blink::WebCircularGeofencingRegion& region, |
47 const GeofencingManager::StatusCallback& callback, | 50 const GeofencingManager::StatusCallback& callback, |
48 int64 geofencing_registration_id) | 51 int64 geofencing_registration_id) |
49 : service_worker_registration_id(service_worker_registration_id), | 52 : service_worker_registration_id(service_worker_registration_id), |
| 53 service_worker_origin(service_worker_origin), |
50 region_id(region_id), | 54 region_id(region_id), |
51 region(region), | 55 region(region), |
52 geofencing_registration_id(geofencing_registration_id), | 56 geofencing_registration_id(geofencing_registration_id), |
53 registration_callback(callback) { | 57 registration_callback(callback) { |
54 } | 58 } |
55 | 59 |
56 GeofencingManager::GeofencingManager( | 60 GeofencingManager::GeofencingManager( |
57 const scoped_refptr<ServiceWorkerContextWrapper>& service_worker_context) | 61 const scoped_refptr<ServiceWorkerContextWrapper>& service_worker_context) |
58 : service_(nullptr), service_worker_context_(service_worker_context) { | 62 : service_(nullptr), service_worker_context_(service_worker_context) { |
59 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 63 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
(...skipping 160 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
220 DCHECK(registration); | 224 DCHECK(registration); |
221 DCHECK(!registration->is_active()); | 225 DCHECK(!registration->is_active()); |
222 registration->registration_callback.Run(status); | 226 registration->registration_callback.Run(status); |
223 registration->registration_callback.Reset(); | 227 registration->registration_callback.Reset(); |
224 | 228 |
225 // If the registration wasn't succesful, remove it from our storage. | 229 // If the registration wasn't succesful, remove it from our storage. |
226 if (status != GEOFENCING_STATUS_OK) | 230 if (status != GEOFENCING_STATUS_OK) |
227 ClearRegistration(registration); | 231 ClearRegistration(registration); |
228 } | 232 } |
229 | 233 |
| 234 void GeofencingManager::RegionEntered(int64 geofencing_registration_id) { |
| 235 DispatchGeofencingEvent(blink::WebGeofencingEventTypeEnter, |
| 236 geofencing_registration_id); |
| 237 } |
| 238 |
| 239 void GeofencingManager::RegionExited(int64 geofencing_registration_id) { |
| 240 DispatchGeofencingEvent(blink::WebGeofencingEventTypeLeave, |
| 241 geofencing_registration_id); |
| 242 } |
| 243 |
230 GeofencingManager::Registration* GeofencingManager::FindRegistration( | 244 GeofencingManager::Registration* GeofencingManager::FindRegistration( |
231 int64 service_worker_registration_id, | 245 int64 service_worker_registration_id, |
232 const std::string& region_id) { | 246 const std::string& region_id) { |
233 DCHECK_CURRENTLY_ON(BrowserThread::IO); | 247 DCHECK_CURRENTLY_ON(BrowserThread::IO); |
234 ServiceWorkerRegistrationsMap::iterator registrations_iterator = | 248 ServiceWorkerRegistrationsMap::iterator registrations_iterator = |
235 registrations_.find(service_worker_registration_id); | 249 registrations_.find(service_worker_registration_id); |
236 if (registrations_iterator == registrations_.end()) | 250 if (registrations_iterator == registrations_.end()) |
237 return nullptr; | 251 return nullptr; |
238 RegionIdRegistrationMap::iterator registration = | 252 RegionIdRegistrationMap::iterator registration = |
239 registrations_iterator->second.find(region_id); | 253 registrations_iterator->second.find(region_id); |
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
279 DCHECK_CURRENTLY_ON(BrowserThread::IO); | 293 DCHECK_CURRENTLY_ON(BrowserThread::IO); |
280 registrations_by_id_.erase(registration->geofencing_registration_id); | 294 registrations_by_id_.erase(registration->geofencing_registration_id); |
281 ServiceWorkerRegistrationsMap::iterator registrations_iterator = | 295 ServiceWorkerRegistrationsMap::iterator registrations_iterator = |
282 registrations_.find(registration->service_worker_registration_id); | 296 registrations_.find(registration->service_worker_registration_id); |
283 DCHECK(registrations_iterator != registrations_.end()); | 297 DCHECK(registrations_iterator != registrations_.end()); |
284 registrations_iterator->second.erase(registration->region_id); | 298 registrations_iterator->second.erase(registration->region_id); |
285 if (registrations_iterator->second.empty()) | 299 if (registrations_iterator->second.empty()) |
286 registrations_.erase(registrations_iterator); | 300 registrations_.erase(registrations_iterator); |
287 } | 301 } |
288 | 302 |
| 303 void GeofencingManager::DispatchGeofencingEvent( |
| 304 blink::WebGeofencingEventType event_type, |
| 305 int64 geofencing_registration_id) { |
| 306 DCHECK_CURRENTLY_ON(BrowserThread::IO); |
| 307 Registration* registration = FindRegistrationById(geofencing_registration_id); |
| 308 if (!registration || |
| 309 registration->service_worker_registration_id == |
| 310 kInvalidServiceWorkerRegistrationId) { |
| 311 // TODO(mek): Log/track these failures. |
| 312 return; |
| 313 } |
| 314 |
| 315 service_worker_context_->context()->storage()->FindRegistrationForId( |
| 316 registration->service_worker_registration_id, |
| 317 registration->service_worker_origin, |
| 318 base::Bind(&GeofencingManager::DeliverGeofencingEvent, |
| 319 this, |
| 320 event_type, |
| 321 geofencing_registration_id)); |
| 322 } |
| 323 |
| 324 void GeofencingManager::DeliverGeofencingEvent( |
| 325 blink::WebGeofencingEventType event_type, |
| 326 int64 geofencing_registration_id, |
| 327 ServiceWorkerStatusCode service_worker_status, |
| 328 const scoped_refptr<ServiceWorkerRegistration>& |
| 329 service_worker_registration) { |
| 330 DCHECK_CURRENTLY_ON(BrowserThread::IO); |
| 331 Registration* registration = FindRegistrationById(geofencing_registration_id); |
| 332 if (!registration) { |
| 333 // Geofence got unregistered in the meantime, no longer need to deliver |
| 334 // event. |
| 335 return; |
| 336 } |
| 337 |
| 338 if (service_worker_status != SERVICE_WORKER_OK) { |
| 339 // TODO(mek): SW no longer exists, somehow handle this. |
| 340 return; |
| 341 } |
| 342 |
| 343 ServiceWorkerVersion* active_version = |
| 344 service_worker_registration->active_version(); |
| 345 if (!active_version) { |
| 346 // TODO(mek): No active version, potentially because one is still being |
| 347 // installed. Handle this somehow. |
| 348 return; |
| 349 } |
| 350 |
| 351 // Hold on to the service worker registration in the callback to keep it alive |
| 352 // until the callback dies. Otherwise the registration could be released when |
| 353 // this method returns - before the event is delivered to the service worker. |
| 354 base::Callback<void(ServiceWorkerStatusCode)> dispatch_event_callback = |
| 355 base::Bind(&GeofencingManager::DeliverGeofencingEventEnd, |
| 356 this, |
| 357 service_worker_registration); |
| 358 active_version->DispatchGeofencingEvent(dispatch_event_callback, |
| 359 event_type, |
| 360 registration->region_id, |
| 361 registration->region); |
| 362 } |
| 363 |
| 364 void GeofencingManager::DeliverGeofencingEventEnd( |
| 365 const scoped_refptr<ServiceWorkerRegistration>& service_worker_registration, |
| 366 ServiceWorkerStatusCode service_worker_status) { |
| 367 DCHECK_CURRENTLY_ON(BrowserThread::IO); |
| 368 // TODO(mek): log/check result. |
| 369 } |
| 370 |
289 } // namespace content | 371 } // namespace content |
OLD | NEW |