Edit: start with iOS8, apple introduces the PushKit framework to release the work we need to do to set up the VoIP application and it also reduces power consumption. You really need to switch to it
There are tips for developing a VoIP application, a link from Apple
The Voice over Internet Protocol (VoIP) application allows the user to make phone calls using an Internet connection instead of the cellular device service. Such an application must maintain a constant network connection to its associated service so that it can receive incoming calls and other relevant data. Instead of constantly supporting VoIP applications, the system allows you to pause them and provides means for monitoring their sockets for them. When incoming traffic is detected, the system wakes up the VoIP application and returns its sockets to it.
There are several requirements for using a VoIP application:
- Turn on Voice over IP for your application. (Since VoIP applications include audio content, it is recommended that you also enable the background Audio and AirPlay modes.) You enable background modes on the Features tab of your Xcode project.
- Configure one of the application sockets to use VoIP.
- Before going to the background, call the setKeepAliveTimeout: handler method: the method to set the handler, which will be executed periodically. Your application can use this handler to maintain its service connection.
- Customize your audio session to handle transitions to and from active use.
- To provide the best user experience on your iPhone, use the Core Telephony framework to customize your cell phone calling behavior; see the link to the basic telephony platform.
- To provide good performance for your VoIP application, use the Configuration Infrastructure system to detect network changes and enable your application. sleep as much as possible.
Enabling VoIP background mode allows the system to know that it should let the application run in the background, if necessary, to manage its network sockets. This key also allows your application to play background sound (although enabling Audio and AirPlay is still encouraged). An application that supports this mode also restarts in the background immediately after booting the system to ensure that VoIP services are always available.
The code below shows how to configure an application socket to use VoIP.
Step 1: connecting to the server
uint16_t port ; NSString *strIp ; char ip[20] = {0} ; memset(ip, 0, sizeof(ip)) ; memcpy(ip, [strIp UTF8String], [strIp length]) ; clientSocket = socket(AF_INET, SOCK_STREAM, 0) ; struct sockaddr_in server_addr ; bzero(&server_addr, sizeof(server_addr)) ; server_addr.sin_port = htons(port) ; server_addr.sin_addr.s_addr = inet_addr(ip) ; server_addr.sin_family = AF_INET ; int i = connect(clientSocket, (const struct sockaddr *)&server_addr, sizeof(server_addr)) ; if (i >= 0) { }
Server-side code can be in C ++, but you can pass clientSocket to an Objective-C instance, this is an int value.
Step 2. Create and configure read and write stream
After connecting to the server, you need to create a read and write stream based on clientSocket using CFStreamCreatePairWithSocket() and set the streams property using NSStreamNetworkServiceTypeVoIP .
Define read and write streams and save them. Close and release them when the connection is lost.
@property (nonatomic, strong) NSInputStream *inputStream ; @property (nonatomic, strong) NSOutputStream *outputStream ;
Then config streams:
CFReadStreamRef readStreamRef = nil ; CFWriteStreamRef writeStreamRef = nil ; CFStreamCreatePairWithSocket(NULL, clientSocket, &readStreamRef, &writeStreamRef) ;
Before connecting to the read and write stream, make sure that the socket is already connected.
Step 3: save the connection
[[UIApplication sharedApplication] setKeepAliveTimeout:600 handler:^{ // the code to check if the socket is connected to server // if not, reconnect to server // and re-set the read stream and write stream in step2 }] ;
When your application enters the background, the socket is controlled by the system, and when the server sends a packet to your application, the system wakes up and passes the packet to it. You only have a few seconds to process the data, so don't do a lot of work here. Since this is a VoIP application, the socket must be used to notify the user that an incoming call is received, and you can click the local notification to let the user know about it.
Since VoIP applications must remain enabled to receive incoming calls, the system automatically restarts the application if it exits with a non-zero exit code. (This type of exit can occur when there is memory pressure, and your application terminates as a result.) However, terminating the application also frees all of its sockets, including the one used to maintain the connection to the VoIP service. Therefore, when the application starts, it always needs to create its sockets from scratch.
I created a sample project here , the corresponding server code.