IOS/SWIFT use gps ,internet and calculation on the background - ios

As a new iOS developer I am need to ask if it possible to run a background service on the phone when the application close and in this service to use user location, send the location to server and the return data compare to another data (for some calculation) and also send to the user Local Push Notification and all of this from the background ?

It's definitely possible to do all those things. Here's some info to start you off with location:
https://developer.apple.com/library/ios/documentation/UserExperience/Conceptual/LocationAwarenessPG/CoreLocation/CoreLocation.html
and notifications:
https://developer.apple.com/library/ios/documentation/NetworkingInternet/Conceptual/RemoteNotificationsPG/Chapters/WhatAreRemoteNotif.html
Both documents discuss how these things work in general, but also talk briefly about how they work in the background. Hopefully this gives you a jumping off point to find what you need.

Related

What is my best bet on periodically running a task to update Live Activity when my app is in the background?

I have an idea for an app that utilises Live Activities, inspired by the Flightly app (it starts a Live Activity for a plane ride): Basically I wanna use open data from an HTTP endpoint that is reachable via the onboard WiFi on a bus. E.g. you board the bus, connect to the onboard WiFi, open the app, it fetches details about the stops and then you start a Live Activity guiding you to a selected stop. So far so good. But sometimes the bus faces delays, etc. In that case, I need to update the Live Activity. That is easy when my app is running. It is not so easy, when my app is not running (or running in the background).
What is my best approach to regularly fetching data from the endpoint and updating my Live Activity? The problem is, that the endpoint is only reachable on the buses WiFi. So it looks like I cannot use APNS to push updates to the Live Activity (since my service running outside the bus cannot access the endpoint that provides the details and thus cannot push any meaningful updates). Background Tasks (e.g. background app refresh) run infrequently.
What options are left? I thought about receiving location updates in the background and acting on them to update my app state (and possible the Live Activity, if needed), although I haven't investigated that path in detail, yet.
Has anybody faced a similar issue and found a solution or can provide some guidance on how to approach this problem?
I think the easiest option is core location. So keep your application running by monitoring the position and then you can update the Live Activity by fetching the information from your access point. It should be fine for app review since you could use the the location to show a position on a map and only while the person is on the bus.
If your application isn't running you have to send the ActivityAttributes via APNS. Since the data cannot be accessed from a remote server that would communicate with APNS there is no direct way to use ActivityKit push notifications. An indirect approach (which I would not recommend) would be to send silent push notifications triggers every 5min or so and fetch the newest information when the application is woken up. But this won't work when the app is force-quit and using silent pushes to trigger polling will give you a bad score by the system and eventually the frequency will be throttled from APNS.

Schedule UILocalNotification based on changes to Core Data

I'm making a simple app with a Today Widget extension that logs events.
The user can tap a button in the app or the related Today Widget to log an event. These events are saved with Core Data any time the button is pressed either place.
Whenever a new event is logged in the app, I run a function called updateLocalNotificationsFromCoreData(). It handles the setup of UILocalNotifications based on the most recent event in Core Data after clearing the appropriate existing notifications.
However, when a new event is logged from the Today Widget, I can't use this function because I need to register the Local Notification with UIApplication.sharedApplication().scheduleLocalNotification(), and UIApplication is not available in the Today Widget extension.
I realize I'll probably need do something unconventional or hacky to get this working, so I'm trying to evaluate possible approaches and come up with a relatively robust solution.
Basically, I want to find a way I can call my
updateLocalNotificationsFromCoreData() function right away any time a new event is logged.
If I can't do it every time an event is logged, an alternative would be to trigger the updateLocalNotificationsFromCoreData() function periodically (somewhat frequently) another way. Here are some solutions I was thinking about using, but I don't like any of them:
Do it in AppDelegate when the app is launched (or another state change)
One approach I'm thinking about is running my updateLocalNotificationsFromCoreData()function in AppDelegate somewhere, like didFinishLaunchingWithOptions.
The downside is that it would require the user to open the app periodically. If the user didn't open it much the notification behavior would be inconsistent. I'd prefer a solution where a user could interact with only the Today Widget and reliably get Local Notifications without ever opening the app.
Sync the events to a server and use Push Notifications
I've thought about syncing the data in Core Data to a server, then setting up Push Notifications to the user's phone based on that.
I don't like this, because I want the user to still be able to get notifications without an Internet connection. It also introduces a lot of extra overhead of syncing the data with a server.
Ping a server, and send a content-available Push Notification
When someone logs an event with the widget, I could ping a server. That server could send back a silent content-available push notification to trigger the app to run updateLocalNotificationsFromCoreData() in the background.
I found a similar question (Scheduling local notification from within a Today extension) where one answer proposes a similar solution. Unlike the previous solution, an Internet connection is not needed to receive the notifications, but an Internet connection would be required to make sure the notifications are up to date when a new event is logged.
Background fetch
I thought about using Background Fetch to fetch something arbitrary from a server, then run the updateLocalNotificationsFromCoreData(). This would be a way to trigger the update in the background, although it seems silly to fetch data if that data isn't being used, and seems like something for which an app could be rejected. There also seems to be a risk of the system not calling the background update regularly if the user doesn't open the app much and mostly uses the Today Widget.
Use background location updates
This seems like the dumbest approach, but I thought I would mention it anyway since I thought about it. I could use one of the low accuracy background location update modes to trigger updateLocalNotificationsFromCoreData().
It would require the user to allow location in the background, which would be hard to explain. And, it would require the user to at least move around a few blocks to trigger the function, which could provide an inconsistent user experience. Also, it would increase power consumption of the app for a silly reason.
I'd really appreciate fresh ideas about how I might be able to reliably schedule local notifications when Core Data changes on a device that doesn't have an Internet connection!
Or, if that doesn't seem possible, I'd appreciated feedback on which approach seems to make the most sense.
EDIT: I came up with a new solution. It's not ideal, but I think it's better than these other approaches I was considering. When someone taps the button to log the event, I launch the full app. It's annoying because I have all the data I need at that point to give the user feedback and log the event within the Today Widget without launching the app, but by launching the app I have the opportunity to check and schedule local notifications.
Also, in iOS 9 the annoyance on the user is slightly minimized because the system-wide "back" button will appear and let the user go back to the previous app easily once my app has launched from the Today Widget.
In the future I may try a solution where one of the server-based approaches above is used when an Internet connection is available, and I would then fall back to this system of opening the app only when the network connection is not available and I need to schedule the local notifications within the app.

iOS: communicating GPS position change to remote web service when app is running in background

I would like to implement a geofence based domotic activation system.
There are different ways to define a geofence (e.g.). What I am concerned about is how this will all come together (service activation).
I am thinking of the use case where the geofence is set up by the user via phone (say via the App I am developing). Once this is done then the data will be stored in a remote webservice. iOS app development guidelines says that you cannot have an app running in the background and here my doubts start..
The point of defining the geofence is to activate some domestic/domotic service once the user enters the geofence that he defined as house. However if the App is running on background how can I get the app to communicate the position to the web service?
I have found this tutorial on remote background data fetching.
Apple developer documentation mentions that you can get background location change updates and hence I assume I can have some code to perform certain actions within the app when I receive a location change call back (from the location manager service). If this is correct I am then wondering whether combining this step plus using remote posting of data may be a valid solution (this has to happen when the app is in background mode).
If not would you be able to suggest an alternative approach?
I believe that if you request notifications within a geo fence you app will be woken up to get the notification, you can use this notification to then request a background session, which can then be used to update your web service.

ios xcode : checking live updates using a .net API

I'm trying to look for a way as to how I can notify a user of new updates based off of a .Net API that I created. Much like that notification you get on facebook, I just need to alert the user that something has been updated. So I'm thinking I need a function that runs in the background while my user uses the app combined with a NSTimer.
Based on my research (and on this question https://stackoverflow.com/a/14835300/639713) apparently you can only achieve such a thing for VOIP and location services. And that using push notification is the only way. Is it really the only option that I can use for such a need? Or are there any other ways?
Thank you for your time.
You have two options:
While your app is open, poll the server every so often to see if there are any updates to report.
This will work only as long as the user has your app open, and as you note, your app will only be allowed to stay open for a long time if it happens to be a VOIP or navigation app.
Use push notifications to push updates to the user’s device.
The disadvantage here is that you will need to write some server-side code to talk to Apple’s push notification servers (as described in this tutorial). This may or may not be a big deal in your particular situation, but it’s the only way to get data to the user when your app isn’t open.

iOS: Start uploading user location after request from server

I need to achieve this: I have an app, which wants to keep track of location of family members. Since I don't want to keep the GPS running all the time, I was thinking I could just send a request from server, when some family member wants to know my location.
But I ran into some problems:
I can't use PUSH Notifications, because those need to be confirmed (tapped on) and only after that the app knows something happened. (This would not be great, since kids probably wouldn't tap the push notifications)
The other option would be to keep the app running in the background, checking server for any news and if it found some request on server only then start the GPS tracking and upload coordinates to server. This sounds a bit better, but also battery draining.
Did anyone already try this? Is there any better way to this problem?
Thanks for any reactions! :)
Yes, I think the only option for you left is run Location Services in background.
For this in Plist set for Required background modes to App registers for location updates. This will enable you to send location updates as you want.
But note that this will only work when application is running or in background, and it will not run when you application is closed. If user closes your application, then you can fire push notification if you done get any updates from device.
Also, note that you need to mention in description of your application, that Application uses location services which will drain your battery, otherwise your application will not be approved.
Hope this info helps you..
We had similar problem in our application. We followed the approach that keep listening to push notification port, whenever we receive any notification, then check if it's for our application and then react accordingly.
We can have listening to port on long time to save battery draining.
Sorry cannot share any of the code with you, but I hope this might be some help.

Resources