Socket are interfaces that allow you to transfer data in bidirectional from app to another app. Socket has two sides. Each side is identified by a combination of two elements: the IP address and port. Socket programing is used in various situation in iOS application development like on line gaming, chat application etc.
So many guides and articles are available to make socket connection between apps but these are very limited in Objective-C and complicated to integrated them. This article discusses only how we can create a socket connection from one app to another app. After establishing connection both app can send and receive data to each other.
Setting Socket Connection
You can use the CFStream API to establish a socket connection. The NSStream class does not support connecting to a remote host on iOS. CFStream does support this behavior, however, and once you have created your streams with the CFStream API, you can cast your CFStreams to NSStreams.
- (void)connection:(NSString*)serviceName forIpAddress:(NSString *)ipAddress
forPort:(NSString *)portNo
{
if(inputStream && outputStream)
[self close];
NSString *urlString = [NSString stringWithFormat:@"http://%@", ipAddress];
NSURL *website = [NSURL URLWithString:urlString];
if (!website) {
NSLog(@"%@ is not a valid URL", website);
}
CFReadStreamRef readStream;
CFWriteStreamRef writeStream;
CFStreamCreatePairWithSocketToHost(NULL, (CFStringRef)[website host], [portNo intValue], &readStream, &writeStream);
CFReadStreamSetProperty(readStream, kCFStreamPropertyShouldCloseNativeSocket, kCFBooleanTrue);
CFWriteStreamSetProperty(writeStream, kCFStreamPropertyShouldCloseNativeSocket, kCFBooleanTrue);
inputStream = (NSInputStream *)readStream;
outputStream = (NSOutputStream *)writeStream;
[self open];
}
- (void)open
{
[inputStream setDelegate:self];
[outputStream setDelegate:self];
[inputStream scheduleInRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];
[outputStream scheduleInRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];
[inputStream open];
[outputStream open];
}
Once you have cast the CFStreams to NSStreams, set the delegate, schedule the stream on a run loop, and open the stream as usual. The delegate should begin to receive stream-event messages (stream:handleEvent:). This method is described below in 'Reading From Socket Connection' section.
Reading From Socket Connection
After a NSInputStream object is sent open, you can find out about its status, whether it has bytes available to read, and the nature of any error with the following messages:
streamStatus
hasBytesAvailable
streamError
- The returned status is an NSStreamStatus constant indicating that the stream is opening, reading, at the end of the stream, and so on. This code for reading data from socket connection listed below.
-(void)stream:(NSStream *)theStream handleEvent:(NSStreamEvent)streamEvent
{
NSString *event;
switch (streamEvent)
{
case NSStreamEventNone:
event = @"NSStreamEventNone";
break;
case NSStreamEventOpenCompleted:
event = @"NSStreamEventOpenCompleted";
break;
case NSStreamEventHasBytesAvailable:
event = @"NSStreamEventHasBytesAvailable";
if (theStream == inputStream)
{
uint8_t buffer[1024];
int len;
while ([inputStream hasBytesAvailable])
{
len = [inputStream read:buffer maxLength:1024];
if (len > 0)
{
NSMutableString *output = [[NSMutableString alloc] initWithBytes:buffer length:len encoding:NSUTF8StringEncoding];
NSLog(@"Received data--------------------%@", output);
}
}
}
break;
case NSStreamEventHasSpaceAvailable:
event = @"NSStreamEventHasSpaceAvailable";
break;
case NSStreamEventErrorOccurred:
event = @"NSStreamEventErrorOccurred";
[self close];
break;
case NSStreamEventEndEncountered:
event = @"NSStreamEventEndEncountered";
[self close];
break;
default:
event = @"Unknown";
break;
}
NSLog(@"event------%@",event);
}
When an NSInputStream object reaches the end of a stream, it sends the delegate a NSStreamEventEndEncountered event in a stream:handleEvent:message. The delegate should dispose of the object by doing the mirror-opposite of what it did to prepare the object. Also we should do When the NSInputStream object experiences errors processing the stream.
- (void)close
{
[inputStream close];
[outputStream close];
[inputStream removeFromRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];
[outputStream removeFromRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];
[inputStream setDelegate:nil];
[outputStream setDelegate:nil];
inputStream = nil;
outputStream = nil;
}
Writing To Socket Connection
After a NSOutputStream object is sent open, you can find out about its status, whether it has space for writing data, and the nature of any error with the following messages:
streamStatus
hasSpaceAvailable
streamError
The returned status is an NSStreamStatus constant indicating that the stream is opening, writing, at the end of the stream, and so on. This code for writing data to socket connection listed below.
- (void)dataSending:(NSString*)data
{
if(outputStream)
{
if(![outputStream hasSpaceAvailable])
return;
NSData *_data=[data dataUsingEncoding:NSUTF8StringEncoding];
int data_len = [_data length];
uint8_t *readBytes = (uint8_t *)[_data bytes];
int byteIndex=0;
unsigned int len=0;
while (TRUE)
{
len = ((data_len - byteIndex >= 40960) ?
40960 : (data_len-byteIndex));
if(len==0)
break;
uint8_t buf[len];
(void)memcpy(buf, readBytes, len);
len = [outputStream write:(const uint8_t *)buf maxLength:len];
byteIndex += len;
readBytes += len;
}
NSLog(@"Sent data----------------------%@",data);
}
}
hello..
ReplyDeletei use above code for socket connection in ios. its working it won't give any error but no response at run time.
i just got printed output
NSStreamEventHasSpaceAvailable
i got only NSStreamEventHasSpaceAvailable
ReplyDeletewhat will happen here ? how can know data reading and writing happing here.
pls let me know
This indicates your NSOutputStream is ready to send data. Please read 'Writing To Socket Connection' in my blog.
Deletehow can i give input value for socket?
ReplyDeletehow i give input for socket ?
ReplyDeleteHow event work and how to LISTEN for events?
ReplyDelete