1

I have an app where the user can gps-track his activities.

Everything works as expected with background GPS updates, but there are very rare cases (1 out of 1000), where I am just not receiving update calls from CLLocationManager when my app is in background. Not immediately, but after some time.

My app starts receiving updates and then all of a sudden (can be a couple of minutes or hours of tracking) it just won't get any more locations updates. It continues reporting location as soon as the app get's active again. But of course those missing locations are bad!

I didn't figure out when and why it happens, that's why I wanted to ask if somebody else already experienced the same issue? I can say that it's not a phone call or something like that that is interrupting. I also don't get callbacks in the didFail delegate method. I just don't get anything any more.... And the big problem is that I have NO IDEA on how to debug that, as I can't reproduce it on purpose.

Any help is very much appreciated.

EDIT:

Here's how I setup my location Manager

self.locationManager = [[CLLocationManager alloc] init];
self.locationManager.delegate = self;

self.locationManager.distanceFilter = kMinimumDistanceFilter;
self.locationManager.desiredAccuracy = kCLLocationAccuracyNearestTenMeters;
self.locationManager.pausesLocationUpdatesAutomatically = NO;
self.locationManager.activityType = CLActivityTypeFitness;

[self.locationManager requestWhenInUseAuthorization];
[self.locationManager requestAlwaysAuthorization];

if ([self.locationManager respondsToSelector:@selector(setAllowsBackgroundLocationUpdates:)])
{
    self.locationManager.allowsBackgroundLocationUpdates = YES;
}

and then later when the Start-Recording-Button is hit

[self.locationManager startUpdatingLocation];

EDIT 2:

If you start this service and your app is suspended, the system stops the delivery of events until your app starts running again (either in the foreground or background). If your app is terminated, the delivery of new location events stops altogether. Therefore, if your app needs to receive location events while in the background, it must include the UIBackgroundModes key (with the location value) in its Info.plist file.

I don't even startUpdatingLocation in the background... But it seems as if that's what happening to my app. How would I be even able to start tracking if the app is suspended? That's impossible, isn't it? Cause suspended would mean it's not executing code?!?

Georg
  • 3,664
  • 3
  • 34
  • 75
  • Can you show the code where you set up your location manager? Do you call `startUpdatingLocation` in the foreground or background? Have you enabled significantlocation monitoring? http://stackoverflow.com/questions/20187700/startupdatelocations-in-background-didupdatingtolocation-only-called-10-20-time – Paulw11 Apr 04 '16 at 11:44
  • I update my question with some code. Thx for helping! `startUpdatingLocation` is called on the main thread and also while the app is in foreground. I also don't use significantlocation monitoring... – Georg Apr 04 '16 at 13:22
  • Do you set up your location manager again correctly if your app is relaunched (ie the location key is present in the dictionary passed to `didFi ishLaunchingWithOptions`?) – Paulw11 Apr 04 '16 at 13:28
  • It lives inside a singleton. So It's only initialized once... – Georg Apr 04 '16 at 13:32
  • Ok, but will the singleton get recreated when the app relaunches. There are two cases to consider for background location; when the app is loaded but in the background (ie suspended) and when the app has been unloaded and is re-launched into the background. In the second case you need to recreate your CLLocationManager instance before the delegate methods will be called – Paulw11 Apr 04 '16 at 13:43
  • Also, since you request "always" authorisation there is no need to request "when in use" authorisation – Paulw11 Apr 04 '16 at 13:46
  • Hm... not sure what you mean? My singleton will live as long as my app lives. It doesn't deallocate itself on a memory warning if you mean that. Or am I not understanding you correctly? So when do you think I would have to re-instantiate the `CLLocationManager`? – Georg Apr 04 '16 at 14:04
  • My app should never get suspended while the `CLLocationManger` is active, shouldn't it? – Georg Apr 04 '16 at 14:05
  • The user could stop moving for a time, they could go inside where there is no GPS signal. – Paulw11 Apr 04 '16 at 20:02
  • 1
    But that would not stop my tracking?!? Cause I have `pausesLocationUpdatesAutomatically` set to NO. I am now trying to reduce energy impact as much as possible. Maybe that helps... – Georg Apr 05 '16 at 06:40

1 Answers1

1

Do you have allowsBackgroundLocationUpdates set to YES in your Info.plist?

From documentation:

By default, this is NO for applications linked against iOS 9.0 or later, regardless of minimum deployment target.

With UIBackgroundModes set to include "location" in Info.plist, you must also set this property to YES at runtime whenever calling -startUpdatingLocation with the intent to continue in the background.

Setting this property to YES when UIBackgroundModes does not include "location" is a fatal error.

Resetting this property to NO is equivalent to omitting "location" from the UIBackgroundModes value. Access to location is still permitted whenever the application is running (ie not suspended), and has sufficient authorization (ie it has WhenInUse authorization and is in use, or it has Always authorization). However, the app will still be subject to the usual task suspension rules.

See -requestWhenInUseAuthorization and -requestAlwaysAuthorization for more details on possible authorization values.

Massimo Polimeni
  • 4,826
  • 4
  • 27
  • 54
  • We'll like I said, it's working in 999 of 1000 times of tracking. My question is what might be causing my CLLocationManager to stop reporting back location updates from time to time?!? – Georg Apr 04 '16 at 10:40
  • 1
    `allowsBackgroundLocationUpdates` is [a property on `CLLocationManager`](https://developer.apple.com/reference/corelocation/cllocationmanager/1620568-allowsbackgroundlocationupdates), not an `Info.plist` key. – bcattle Apr 12 '17 at 01:12