OLD | NEW |
1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2013 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 "chrome/browser/extensions/api/location/location_manager.h" | 5 #include "chrome/browser/extensions/api/location/location_manager.h" |
6 | 6 |
7 #include <math.h> | 7 #include <math.h> |
8 #include <vector> | 8 #include <vector> |
9 | 9 |
10 #include "base/bind.h" | 10 #include "base/bind.h" |
(...skipping 195 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
206 LocationRequest::LocationRequest( | 206 LocationRequest::LocationRequest( |
207 const base::WeakPtr<LocationManager>& location_manager, | 207 const base::WeakPtr<LocationManager>& location_manager, |
208 const std::string& extension_id, | 208 const std::string& extension_id, |
209 const std::string& request_name, | 209 const std::string& request_name, |
210 const double* distance_update_threshold_meters, | 210 const double* distance_update_threshold_meters, |
211 const double* time_between_updates_ms) | 211 const double* time_between_updates_ms) |
212 : request_name_(request_name), | 212 : request_name_(request_name), |
213 extension_id_(extension_id), | 213 extension_id_(extension_id), |
214 location_manager_(location_manager) { | 214 location_manager_(location_manager) { |
215 // TODO(vadimt): use request_info. | 215 // TODO(vadimt): use request_info. |
216 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 216 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
217 | 217 |
218 if (time_between_updates_ms) { | 218 if (time_between_updates_ms) { |
219 update_policies_.push_back( | 219 update_policies_.push_back( |
220 new updatepolicy::TimeBasedUpdatePolicy( | 220 new updatepolicy::TimeBasedUpdatePolicy( |
221 *time_between_updates_ms)); | 221 *time_between_updates_ms)); |
222 } | 222 } |
223 | 223 |
224 if (distance_update_threshold_meters) { | 224 if (distance_update_threshold_meters) { |
225 update_policies_.push_back( | 225 update_policies_.push_back( |
226 new updatepolicy::DistanceBasedUpdatePolicy( | 226 new updatepolicy::DistanceBasedUpdatePolicy( |
227 *distance_update_threshold_meters)); | 227 *distance_update_threshold_meters)); |
228 } | 228 } |
229 } | 229 } |
230 | 230 |
231 void LocationRequest::Initialize() { | 231 void LocationRequest::Initialize() { |
232 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 232 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
233 callback_ = base::Bind(&LocationRequest::OnLocationUpdate, | 233 callback_ = base::Bind(&LocationRequest::OnLocationUpdate, |
234 base::Unretained(this)); | 234 base::Unretained(this)); |
235 | 235 |
236 BrowserThread::PostTask( | 236 BrowserThread::PostTask( |
237 BrowserThread::IO, | 237 BrowserThread::IO, |
238 FROM_HERE, | 238 FROM_HERE, |
239 base::Bind(&LocationRequest::AddObserverOnIOThread, | 239 base::Bind(&LocationRequest::AddObserverOnIOThread, |
240 this)); | 240 this)); |
241 } | 241 } |
242 | 242 |
243 void LocationRequest::GrantPermission() { | 243 void LocationRequest::GrantPermission() { |
244 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); | 244 DCHECK_CURRENTLY_ON(BrowserThread::IO); |
245 content::GeolocationProvider::GetInstance()->UserDidOptIntoLocationServices(); | 245 content::GeolocationProvider::GetInstance()->UserDidOptIntoLocationServices(); |
246 } | 246 } |
247 | 247 |
248 LocationRequest::~LocationRequest() { | 248 LocationRequest::~LocationRequest() { |
249 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); | 249 DCHECK_CURRENTLY_ON(BrowserThread::IO); |
250 content::GeolocationProvider::GetInstance()->RemoveLocationUpdateCallback( | 250 content::GeolocationProvider::GetInstance()->RemoveLocationUpdateCallback( |
251 callback_); | 251 callback_); |
252 } | 252 } |
253 | 253 |
254 void LocationRequest::AddObserverOnIOThread() { | 254 void LocationRequest::AddObserverOnIOThread() { |
255 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); | 255 DCHECK_CURRENTLY_ON(BrowserThread::IO); |
256 | 256 |
257 // TODO(vadimt): This can get a location cached by GeolocationProvider, | 257 // TODO(vadimt): This can get a location cached by GeolocationProvider, |
258 // contrary to the API definition which says that creating a location watch | 258 // contrary to the API definition which says that creating a location watch |
259 // will get new location. | 259 // will get new location. |
260 content::GeolocationProvider::GetInstance()->AddLocationUpdateCallback( | 260 content::GeolocationProvider::GetInstance()->AddLocationUpdateCallback( |
261 callback_, true); | 261 callback_, true); |
262 } | 262 } |
263 | 263 |
264 void LocationRequest::OnLocationUpdate(const content::Geoposition& position) { | 264 void LocationRequest::OnLocationUpdate(const content::Geoposition& position) { |
265 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); | 265 DCHECK_CURRENTLY_ON(BrowserThread::IO); |
266 if (ShouldSendUpdate(position)) { | 266 if (ShouldSendUpdate(position)) { |
267 OnPositionReported(position); | 267 OnPositionReported(position); |
268 BrowserThread::PostTask( | 268 BrowserThread::PostTask( |
269 BrowserThread::UI, | 269 BrowserThread::UI, |
270 FROM_HERE, | 270 FROM_HERE, |
271 base::Bind(&LocationManager::SendLocationUpdate, | 271 base::Bind(&LocationManager::SendLocationUpdate, |
272 location_manager_, | 272 location_manager_, |
273 extension_id_, | 273 extension_id_, |
274 request_name_, | 274 request_name_, |
275 position)); | 275 position)); |
276 } | 276 } |
277 } | 277 } |
278 | 278 |
279 bool LocationRequest::ShouldSendUpdate(const content::Geoposition& position) { | 279 bool LocationRequest::ShouldSendUpdate(const content::Geoposition& position) { |
280 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); | 280 DCHECK_CURRENTLY_ON(BrowserThread::IO); |
281 for (UpdatePolicyVector::iterator it = update_policies_.begin(); | 281 for (UpdatePolicyVector::iterator it = update_policies_.begin(); |
282 it != update_policies_.end(); | 282 it != update_policies_.end(); |
283 ++it) { | 283 ++it) { |
284 if (!((*it)->ShouldSendUpdate(position))) { | 284 if (!((*it)->ShouldSendUpdate(position))) { |
285 return false; | 285 return false; |
286 } | 286 } |
287 } | 287 } |
288 return true; | 288 return true; |
289 } | 289 } |
290 | 290 |
291 void LocationRequest::OnPositionReported(const content::Geoposition& position) { | 291 void LocationRequest::OnPositionReported(const content::Geoposition& position) { |
292 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); | 292 DCHECK_CURRENTLY_ON(BrowserThread::IO); |
293 for (UpdatePolicyVector::iterator it = update_policies_.begin(); | 293 for (UpdatePolicyVector::iterator it = update_policies_.begin(); |
294 it != update_policies_.end(); | 294 it != update_policies_.end(); |
295 ++it) { | 295 ++it) { |
296 (*it)->OnPositionReported(position); | 296 (*it)->OnPositionReported(position); |
297 } | 297 } |
298 } | 298 } |
299 | 299 |
300 LocationManager::LocationManager(content::BrowserContext* context) | 300 LocationManager::LocationManager(content::BrowserContext* context) |
301 : profile_(Profile::FromBrowserContext(context)) { | 301 : profile_(Profile::FromBrowserContext(context)) { |
302 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_LOADED, | 302 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_LOADED, |
303 content::Source<Profile>(profile_)); | 303 content::Source<Profile>(profile_)); |
304 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_UNLOADED_DEPRECATED, | 304 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_UNLOADED_DEPRECATED, |
305 content::Source<Profile>(profile_)); | 305 content::Source<Profile>(profile_)); |
306 } | 306 } |
307 | 307 |
308 void LocationManager::AddLocationRequest( | 308 void LocationManager::AddLocationRequest( |
309 const std::string& extension_id, | 309 const std::string& extension_id, |
310 const std::string& request_name, | 310 const std::string& request_name, |
311 const double* distance_update_threshold_meters, | 311 const double* distance_update_threshold_meters, |
312 const double* time_between_updates_ms) { | 312 const double* time_between_updates_ms) { |
313 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 313 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
314 // TODO(vadimt): Consider resuming requests after restarting the browser. | 314 // TODO(vadimt): Consider resuming requests after restarting the browser. |
315 | 315 |
316 // Override any old request with the same name. | 316 // Override any old request with the same name. |
317 RemoveLocationRequest(extension_id, request_name); | 317 RemoveLocationRequest(extension_id, request_name); |
318 | 318 |
319 LocationRequestPointer location_request = | 319 LocationRequestPointer location_request = |
320 new LocationRequest(AsWeakPtr(), | 320 new LocationRequest(AsWeakPtr(), |
321 extension_id, | 321 extension_id, |
322 request_name, | 322 request_name, |
323 distance_update_threshold_meters, | 323 distance_update_threshold_meters, |
324 time_between_updates_ms); | 324 time_between_updates_ms); |
325 location_request->Initialize(); | 325 location_request->Initialize(); |
326 location_requests_.insert( | 326 location_requests_.insert( |
327 LocationRequestMap::value_type(extension_id, location_request)); | 327 LocationRequestMap::value_type(extension_id, location_request)); |
328 } | 328 } |
329 | 329 |
330 void LocationManager::RemoveLocationRequest(const std::string& extension_id, | 330 void LocationManager::RemoveLocationRequest(const std::string& extension_id, |
331 const std::string& name) { | 331 const std::string& name) { |
332 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 332 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
333 | 333 |
334 std::pair<LocationRequestMap::iterator, LocationRequestMap::iterator> | 334 std::pair<LocationRequestMap::iterator, LocationRequestMap::iterator> |
335 extension_range = location_requests_.equal_range(extension_id); | 335 extension_range = location_requests_.equal_range(extension_id); |
336 | 336 |
337 for (LocationRequestMap::iterator it = extension_range.first; | 337 for (LocationRequestMap::iterator it = extension_range.first; |
338 it != extension_range.second; | 338 it != extension_range.second; |
339 ++it) { | 339 ++it) { |
340 if (it->second->request_name() == name) { | 340 if (it->second->request_name() == name) { |
341 location_requests_.erase(it); | 341 location_requests_.erase(it); |
342 return; | 342 return; |
(...skipping 19 matching lines...) Expand all Loading... |
362 if (position.heading >= 0. && position.heading <= 360.) | 362 if (position.heading >= 0. && position.heading <= 360.) |
363 coordinates->heading.reset(new double(position.heading)); | 363 coordinates->heading.reset(new double(position.heading)); |
364 if (position.speed >= 0.) | 364 if (position.speed >= 0.) |
365 coordinates->speed.reset(new double(position.speed)); | 365 coordinates->speed.reset(new double(position.speed)); |
366 } | 366 } |
367 | 367 |
368 void LocationManager::SendLocationUpdate( | 368 void LocationManager::SendLocationUpdate( |
369 const std::string& extension_id, | 369 const std::string& extension_id, |
370 const std::string& request_name, | 370 const std::string& request_name, |
371 const content::Geoposition& position) { | 371 const content::Geoposition& position) { |
372 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 372 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
373 | 373 |
374 scoped_ptr<base::ListValue> args(new base::ListValue()); | 374 scoped_ptr<base::ListValue> args(new base::ListValue()); |
375 std::string event_name; | 375 std::string event_name; |
376 | 376 |
377 if (position.Validate() && | 377 if (position.Validate() && |
378 position.error_code == content::Geoposition::ERROR_CODE_NONE) { | 378 position.error_code == content::Geoposition::ERROR_CODE_NONE) { |
379 // Set data for onLocationUpdate event. | 379 // Set data for onLocationUpdate event. |
380 location::Location location; | 380 location::Location location; |
381 location.name = request_name; | 381 location.name = request_name; |
382 GeopositionToApiCoordinates(position, &location.coords); | 382 GeopositionToApiCoordinates(position, &location.coords); |
(...skipping 10 matching lines...) Expand all Loading... |
393 | 393 |
394 scoped_ptr<Event> event(new Event(event_name, args.Pass())); | 394 scoped_ptr<Event> event(new Event(event_name, args.Pass())); |
395 | 395 |
396 ExtensionSystem::Get(profile_)->event_router()-> | 396 ExtensionSystem::Get(profile_)->event_router()-> |
397 DispatchEventToExtension(extension_id, event.Pass()); | 397 DispatchEventToExtension(extension_id, event.Pass()); |
398 } | 398 } |
399 | 399 |
400 void LocationManager::Observe(int type, | 400 void LocationManager::Observe(int type, |
401 const content::NotificationSource& source, | 401 const content::NotificationSource& source, |
402 const content::NotificationDetails& details) { | 402 const content::NotificationDetails& details) { |
403 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); | 403 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
404 | 404 |
405 switch (type) { | 405 switch (type) { |
406 case chrome::NOTIFICATION_EXTENSION_LOADED: { | 406 case chrome::NOTIFICATION_EXTENSION_LOADED: { |
407 // Grants permission to use geolocation once an extension with "location" | 407 // Grants permission to use geolocation once an extension with "location" |
408 // permission is loaded. | 408 // permission is loaded. |
409 const Extension* extension = | 409 const Extension* extension = |
410 content::Details<const Extension>(details).ptr(); | 410 content::Details<const Extension>(details).ptr(); |
411 | 411 |
412 if (extension->HasAPIPermission(APIPermission::kLocation)) { | 412 if (extension->HasAPIPermission(APIPermission::kLocation)) { |
413 BrowserThread::PostTask( | 413 BrowserThread::PostTask( |
(...skipping 24 matching lines...) Expand all Loading... |
438 LocationManager::GetFactoryInstance() { | 438 LocationManager::GetFactoryInstance() { |
439 return g_factory.Pointer(); | 439 return g_factory.Pointer(); |
440 } | 440 } |
441 | 441 |
442 // static | 442 // static |
443 LocationManager* LocationManager::Get(content::BrowserContext* context) { | 443 LocationManager* LocationManager::Get(content::BrowserContext* context) { |
444 return BrowserContextKeyedAPIFactory<LocationManager>::Get(context); | 444 return BrowserContextKeyedAPIFactory<LocationManager>::Get(context); |
445 } | 445 } |
446 | 446 |
447 } // namespace extensions | 447 } // namespace extensions |
OLD | NEW |