XCode iDevice app - How to listen for message/request from server? - ios

I have a project where I need to be able to send messages from a server running a web service to a specific iDevice. I have no idea how to do this, so any help is very appreciated.
The scenario: I have a web service which receives some message from an iDevice (could also be a Mac or PC, even an Android device). Depending on the content of this message I need to be able to send a message from the web service to another iDevice (I know the IP-address of the specific iDevice). I know how to use URLRequests to send a message from an iDevice to a server and collect the response from the server. In principle I could every 10 seconds send a request to the server asking if the server has any new messages to the sender (the iDevice sending the request), but I am pretty sure this is not the correct way to do it. Is there a way to have an iDevice listen for server communication on a specific port, so that the iDevice only does something active when it receives a message from the server to do something, e.g. display a message in the app listening for the server communication?
I guess I need to use something similar to the technology used for iMessage, but how is this done?
I am using XCode 4.6.2, iOS 6.1.
EDIT: Just to clarify my needs a bit more: The APNS seems to be TOO unreliable (at least that is what I have read in other threads regarding APN) as the web service in some cases can have the need for sending 2 distinct message to an iDevice within 1 minute (in some cases seconds), and as far as I have read in other threads this will simply not be possible because of how Apple's server handles ASPNS.
The app i am developing only needs to receive messages from the server when the app is active - is there any way, not using APNs, to do this, e.g. making the app listen for communication on a specific port?

Your scenario seems pretty similar to APPLE PUSH NOTIFICATIONs (APNs).
Ideally your server side should write a code in such a way that if there is any change on server side & need to be informed to all associated devices.
Then your server should post notification Apple server which will then send a notification to all the associated devices.
Refer this link
You already have but can use this code to identify the iOS/Mac deivce
NSString *identifierString = [[NSUserDefaults standardUserDefaults] objectForKey:#"myID"];
if (!identifierString) {
CFUUIDRef identifier = CFUUIDCreate(NULL);
identifierString = (NSString*)CFUUIDCreateString(NULL, identifier);
[[NSUserDefaults standardUserDefaults] setObject:identifierString forKey:#"myID"];
}
NSLog(#"%#",identifierString);
this code works till the lifetime of the app only.

After some search I have decided not to use the APNS, because it seems like people are having all sort of experience with it. I cannot use APNS because my project needs 100 % reliability and instant communication with the server.
I have decided to use tcp communication since my project only will be used in a local network. This will obviously mean more power consumption on the iDevices, but reliability is more crucial to the project.

Related

iOS Remote Notifications Badge Count Strategy When Network Connection Is Poor

I am trying to understand the best practice for remote notifications on iOS when the user has a particularly poor network connection or no network connection.
The scenario is such:
The user gets some remote notifications and at some point in the future opens the app. At this point I wan't to let the server know ASAP that the badge count is now zero. I am using server side badge count management as the only way you can update the icon badge reliably is in the APNS payload. However the call to the server fails as there is no network connectivity. Then the user puts the app into the background so I can't make any further calls to the server if network came back. Subsequently a new remote notification comes in but the badge number is wrong because the server doesn't know it needed to be zeroed.
Am I missing something here? Any advice gratefully received as I haven't found any articles online dealing with this scenario.
Yes, you have implemented in right way. We can't do anything if there is problem in internet connection. Badge count is managed by server only. So, whenever you open application, application will update Zero to server. Now, if it is not properly updated to server then it is not possible to manage it from Mobile side.

iOS Methodology: should I listen to a socket?

I know almost nothing about server/sockets programming. Pardon my ignorance.
I'm making an iOS app that needs to integrate with my web server. The function is analogous to a chat room - multiple clients will be 'connected' and 'listening' to a server session, any one client can send a 'bit', and all clients will receive the 'bit'.
Should I use low-level socket listening and callbacks for this? Is there a better, more power-efficient way? A cool framework I should use?
There are many options for this:
Use a socket to your server and roll your own protocol
Use web sockets and long polling from your app. This means you will fire a HTTP request and your server will keep it open for, let's say, one minute waiting for messages. Take a look here to start: What are Long-Polling, Websockets, Server-Sent Events (SSE) and Comet?
Use a chat server like Openfire or Ejabberd, which use XMPP, and on your client use XMPPFramework (https://github.com/robbiehanson/XMPPFramework)
Depending on the complexity of your app (authentication? blocking contacts? one-to-many and one-to-one chat?) you can decide on any of the above options. With more details I may be able to help you more.
If you want to be able to receive data while the app is not in the foreground, you will need to use Apple's push notification feature, which is implemented in hardware and the only way to make network connections to a device that is in power saving mode.
There's plenty of documentation how it works, basically the device registers with your server (after asking the user for permission), you use the token it gives you to send a ping to Apple's server, which forwards the ping on to the device. The device can then contact your server and download the actual data you want to send to it.
If you're OK with the server only communicating with your app while the app is running, you have a few options. The easiest is "long polling" where the app sends a HTTP request to the server, using something like this:
NSURL *serverUrl = [NSURL URLWithString:#"http://example.com/"];
NSString *response = [NSString stringWithContentsOfURL:serverUrl usedEncoding:NULL error:NULL];
NSLog(#"%#", response);
Instead of the server responding instantly, it can wait around for a long time (for example 45 seconds) until it has something to send to the device, then it responds with the information.
If 45 seconds are reached without having anything to send, it just sends a nothing response and the phone immediately opens up a new URL request to the same URL. This keeps the server from having a bunch of old/abandoned connections open. Typically connections are dropped after 60 seconds, so you want to respond before that time limit is reached. Obviously you'll want to do the request on a background queue with NSOperationQueue.
There are other options, you could use sockets, you could start a web server on a custom HTTP port on the phone (eg: https://github.com/robbiehanson/CocoaHTTPServer). But long polling is often the easiest choice.
Most apps use a combination of push notifications and something else.

iOS Push Notifications: App as Provider?

I understand the basic concept of having a provider talk to Apple's Push Notification Server which then pushes the notification to the phone. Usually, the provider is an app server running on some machine somewhere completely separate from the app.
However, we don't currently have a separate server, and don't yet need one as everything is currently handled in-app. So, is there any way we can use the app itself as the provider to send a notification to Apple's server and thus to another phone?
Basic concept: we have a game and when a user completes 70% of the level, we'd like to notify his competitors that he's close to finishing the game (or that he has finished at 100%).
If it's possible, are there any security concerns with this approach?
P.S. The app already knows who the competitors are because it displays them in a UITableView.
Technically it's possible. If you include the push certificate with your app, and you have a way to send the device token of each device to all other devices that may need to push to that device, you can push a notification directly from one device to another.
However, in practice, that would require opening and closing many connections to the APNS servers frequently (you'll need a connection for each device, and every time a device loses network connection - which may happen often - you'll have to re-open that connection), which will probably cause Apple to block your app from connecting to their APNS server (since they would interpret it a DDoS attack).
Therefore you should use a server.
For future visitors to this question: we wound up ditching Amazon SNS since we spent nearly 8 hours and couldn't get it working the way we wanted. Instead, we setup Parse Push in rough 15 minutes with exactly what we wanted to do, so I would definitely recommend giving it a look.

Chat app synchronization on background in IOS

I have a chat application developed by JS. I want to send PING to server once in a while. Its not a problem if app runs on fore ground. The problem is when user minimizes it or open another app. My app looses its focus and gets into suspended state.
I have following two use-cases.
To keep the chat session open I need to send PING to server (Its an IRC server) every X minutes even the app runs in background.
We also need to check for new messages (by ajax on a local http server) and add a local notification to the notification queue so when user clicks on it app can resume
I have found apple does not allow running apps in the background. if they allow they require special permission. I found some apps does it by requesting finite length execution time.
What is the best way to get highest possible background execution time? As a chat app can I request permission for voip, location or any other way ?
Note: the app will be running in an environment where there is no Internet. Hence push notification will not work here.
Update: After doing a lot searching I found background fetch. It seem background fetch will suite it. But still the problem remains, its not called in a timely manner.
This sounds like an interesting problem. From reading the various comments, it sounds like you want this to work when you're on a local network - so you have wifi, but the wifi router/base station isn't connected to the actual internet?
Because background refresh isn't going to be predictable - you'll never know when it is going to update - you might want to get creative.
You could look into exploiting iOS VOIP support, only without the Voice! Apple has some tips on VOIP here. VOIP basically uses something called SIP (Session Initiation Protocol), which is signalling layer of the call, and a lot like HTTP. It's this SIP layer that you want to take advantage of.
This isn't going to be terribly easy, but it should be achievable. Setup your app to use VOIP, and then look into something like PJSip as your SIP library. Then, on your local network have a SIP Server (I'm sure there are plenty open source implementations) that you can register your iPhone against (so your server knows where your phone is, pretending to be a VOIP phone). This should work, because it doesn't need to go through Apple as far as I am aware... And will run happily on your local network.
Then, the server can send a message via SIP to the handset, as if it were instigating a VOIP session. You app is awoken, gets the messages - ideally from the SIP message if possible - and then just doesn't start the session. SIP was designed just for creating sessions, not just VOIP. When I worked in Telecoms R&D (a long time ago) we were using it to swap between Text/Voice/Video, all using local servers.
You'll have to jump a lot of hoops to make this work, but it would be pretty awesome. I have never tried this actual use case - especially with iOS, but I'm fairly sure it will work. It is a bit of a fudge, but should get you where you need to go.
Good luck!
You can use something like PubNub to build this chat app with iOS using native Objective-C code, or with the Phonegap (Cordova) libs.
The beauty with using a real-time messaging network like PubNub is that when the app goes to the background, you can easily have the chat messages come in on APNS.
When the app is in the foreground, it can just receive them as the native (PubNub) message. And if it needs to "catch-up" with the messages it missed while in the background (but received via APNS), its trivial to implement.
Also, PubNub is platform agnostic -- so you can easily also use it on Web, Android, BB, Windows Phone, etc.
http://www.pubnub.com/blog/build-real-time-chat-10-lines-code/
http://www.pubnub.com/blog/html5-websockets-beautiful-real-time-chat-on-mobile-using-pubnubs-channel-presence/
https://github.com/pubnub/objective-c/tree/master/iOS
https://github.com/pubnub/javascript/tree/master/phonegap
geremy

iPhone app development. How does an app like snapchat send data from user to user?

I'm just starting to get into app development and have just been learning the uses of Xcode and Objective-C language. Just wondering how an app like snapchat or any other app can send data from one user to another. General answers would suffice just to better my understanding.
How do they test this functionality?
How can they connect peer to peer and send data from one phone to another? Is it all accessed in one database that the app connects to everytime that it pulls down?
When you sign up for an app like this with a registered account is that information stored on the iphone?
Well there are two ways data can be sent to a device. One is the device polls the main server periodically. This can be seen in a pull to refresh scenario. The other is the server can send a push notification to the specific phone and app which causes the data to be received by the device and displayed however the programmer wants. So device to device is essentially one person sending something through a web service call to your server. Your server them packages that information into a Json payload and sends a push notification to the recipient. It seems like its device to device because its so quick, but it requires that you have a server in the middle and of course your server is really sending the push notification to Apple's push server, so there really are two servers involved.
How do they test this functionality?
I would try to do this with real devices, and/or using a network sniffer tool to inspect the send packets.
How can they connect peer to peer and send data from one phone to another? Is it all accessed in one database that the app connects to everytime that it pulls down?
Someones sends you a snap
your app will ask the database every ...min or when you reload if there's something new to load, and gets it from the database if there is something new
When you sign up for an app like this with a registered account is that information stored on the iphone?
Connect to snapchat
get a snap from someone and wait till you can view it
start airplane mode and see if it loads, if it does there are files (temporarily) stored on your iPhone.

Resources