… or “How do you solve a problem like Background Location Tracking on the iPhone?”
This post has ended up pretty long and I realize that people of the Internet don’t like to read too much (TL;DR), especially when magical new Apple hardware is being released so I’ve highlighted the preamble below to allow you to jump straight to the amazing insightful ideas.
As you probably know if you read my blog, or are aware of my website mapme.at (and it’s corresponding blog) I like to track my location. I think it’s fun and useful. I use it to show friends and family where I am and what I’ve been up to. I use it as a personal record of where I’ve been allowing me to go back months and even years later and find out things like “yes, I was in Company B’s office on that date, they should have paid me”. Lots of other people like to track their location too using it to help with socializing, with fitness and lots of other uses. Hey even the government thinks it’s good to track people… but maybe we shouldn’t go there.
I use lots of methods to track my location depending on how much accuracy I want to store. At the very least I try to “check in” to every “place” that I visit using the mapme.at mobile page which works well on my iPhone. I also like to store more accurate high resolution traces like the one below of a ferry ride through Sydney, Australia. These are great, especially when I’m taking photos or sending lots of tweets, allowing me to look back later and see exactly where I was when I did whatever I did. I tend to use an iPhone app called GPS Tracker from Instamapper.com to do this. It’s a very simple app and simply stores up locations for a minute before sending them to a server. They have an API which allows me to pull these into mapme.at and show my trace alongside the rest of my location history. The app’s great but having to launch it and keep it active to get a full trace isn’t ideal. Poking the screen every few minutes while driving to stop the phone locking isn’t the safest thing to do! It took me a good few months before I found out that if you were playing music in the background then the foreground app could stay active but even this isn’t ideal. Perhaps you want to listen to the radio instead. It also means that the only thing you can use the phone for is the tracking app, so if I’m walking down the street I can’t track and use twitter at the same time.
Apple have been quite insistent on not allowing apps to run in the background (well, when I say insistent, there’s simply no way to do it in the SDK). The reasons they tend to cite (sorry, a cursory google didn’t find any official responses) center around the fact that running multiple apps at once causes unnecessary load on the CPU which causes the battery to drain too fast. As an iPhone 3G (not 3GS) user I know that battery life can be an issue on the iPhone, my aging phone sometimes has issues getting through the night!
Not being able to run multiple apps has never been a huge deal for me, apart from this background tracking aspect. My previous phone, a Sony Ericsson K750i, couldn’t run multiple third party J2ME apps at once. It could run the current app in the background though and so has often ended up being a better option for tracking though does require me to carry two phones, this one and my iPhone (I can run 2 apps at once now, 1 per phone!)
So you might ask why I’m writing a blog post about this, none of this is particularly new information. Well, a few months ago I came up with an idea that I was convinced solved the problem and, I thought, would be the direction Apple would take. More recent rumours about Apple simply “turning on” background/multiple apps in iPhone OS 4.0 made me a little less confident that Apple would go with the idea but I’ve decided that even if Apple do allow background apps, “we” in the iPhone SDK Geo developers community need to be a clever about how we handle these apps. As such I’m going to outline what I think(/thought/hope) Apple will do, and then I’ll discuss what we can do if they don’t.
The direction that I think Apple will take is inspired by their solution to the “How are we going to write Instant Messaging apps??” question previously asked of Apple. Their solution to that was to create a single central channel by which developers could send information back to the iPhone even when their app is not running. Developers use the “Push Notifications API” to do this. On the phone, when their app is first run it will request the ability to send push notifications, the OS will show a message to the user confirming that they want to allow this and the app will then be given a “device token” which uniquely identifies the phone. The app then sends this token to a server and that server now has the ability to send push notifications to the phone, using the token, whenever it wants. The Push Notifications API only allows for simple small messages but is an efficient way to allow apps to update their users without running in the background.
So to do the same thing for location updates Apple should offer a single central API for requesting the location when the app is not running. I think Apple will call it something along the lines of “Mobile My Core Location Remote Notifications Me API” but for now I’ll just refer to it as “the API”. As far as users and iPhone (client) developers are concerned the API interaction would be very similar to push notifications. The app would request access to location updates in the background, the user would see a message such as:
“Ace Tracker” would like to use your location now and in the future
This will allow the app to know where you are even when it isn’t running.
If the user accepts, the app receives a token which it sends back to its server. On the server side I’m not sure how Apple would handle things, currently push notifications are done as a very simple SSL encoded binary connection. For background location updating the best solution would most likely be something based on XMPP so that the server could connect to Apple once and just sit and wait for updates. I’m guessing Apple wouldn’t want a polling option with multiple servers continually asking “where are my users?!”, and having Apple pushing to various different servers that may or may not be turned on and active is probably even less likely.
So that’s the crux of it, Apple should offer an API that gives apps the ability to get location updates in the background. But still you might be thinking there’s a problem with this. Way up in my preamble I did mention that one of the problems with background apps is battery usage. Using Core Location continuously on the iPhone is one of the best ways to drain your battery so surely Apple aren’t going to make it easy for developers to do this? Well Apple engineers tend to be pretty smart and I reckon they’ll be able to find interesting and novel ways to reduce the battery usage. Ways that – if Apple choose not to go with an API and just to allow background apps universally – we should use ourselfes.
Using Wi-Fi Positioning it’s possible to get a relatively good location fix just by doing a quick scan of the Wi-Fi airwaves. This might not work so well as you’re walking down a street as your position would keep jumping around by 50-150m or so, but if you’re sat in a bar or an office should give good results. How to know you’re sitting still? Well, one way is just to notice that the nearby access points haven’t changed for the past 5 minutes and decide based on that, another approach would be to use the accelerometer in the phone: if the iPhone hasn’t moved for hours then there’s no point trying to get a location fix at all. Again it might be possible to do similar things using cell based positioning, in cities the cells tend to be smaller which helps to get the accuracy higher. Doing some low power cell positioning to check for movement of more than a few hundred yards before deciding to turn on the GPS could be one way to save power. I’m sure there’s lots more options too.
Obviously some of these techniques aren’t going to work if you want a 1-second high accuracy trace of your location, but if this is what you’re looking for then there’s not much you can do about battery life. A lot of interesting applications could be made using just simple background “checking in” giving a good profile of the businesses you visit on a regular basis for instance. While developers using the iPhone SDK don’t have full access to the hardware and so wouldn’t necessarily be able to optimise for switching between the different locating technologies, Apple do, and this is why I think they should create this API even if they do allow background apps. Even without full access to the hardware I think we as iPhone SDK developers should be able to create something much better than a hundred apps that all simply fire up Core Location, ask for best accuracy, and then constantly push that back to our servers and I think that we should start looking at ways to do this.
Obviously decisions would need to be made, for instance for this to work optimally and not require multiple background processes for different apps there would need to be a single central service to send the location updates to. A central brokering service would be best. While I’d be ecstatic if mapme.at was used other choices would be Yahoo’s Fireeagle or potentially the new location services Facebook are rumoured to be introducing. Also while I talk about a “single centralised solution” I do realise that competition can be good so the idea of multiple implementations isn’t, in essence, bad I’m just trying to avoid everyone in the location space coming up with a solution which just results in multiple background updating processes running and defeating the purpose of this whole exercise!
So that’s my idea. Might be a crazy one, who knows, might even be what Apple have planned anyway. A very knowledgeable friend seemed impressed though and pushed me to write up this blog post (and reminded me about the usefulness of the accelerometer) so maybe there’s something here. Let me know any comments you have, and I’ll be at WhereCamp in a few hours so would love to discuss it with you then. In fact I’ll be in the bay area until late Monday afternoon if anyone at Apple wants to get in touch 😉 If I don’t hear anything I might just write some code and stick it on github!
I noticed looking back on my notes for this article that I listed to myself two things that make background tracking difficult: power and connectivity. Connectivity becomes a big issue as soon as you start roaming and would certainly be something worth looking at, having a way to store a trace for a long period of time and then report it back later would be great. I decided not to cover it in this article though as it was just getting far too big, maybe if there’s interest I’ll write something else up.
Also, yes, Android already allows background apps, as far as I know there’s nothing similar to what I’m proposing for that platform, maybe there should be.