Не получать больше сообщений после получения первого сообщения с сервера Java в клиенте iOS с использованием NSInputStream

У меня есть сервер Java (и он может правильно прочитать запрос от моего клиента iOS - он даже генерирует ответ и, кажется, отправляет его правильно, хотя я каждый раз получал ответ на первое сообщение с сервера, но не получаю другие сообщения после получение первого сообщения):

последовательность общения

Step 1-> client send login message to server

Step 2-> server validate the user and sends login info to the clients

Step 3-> Message Packet1

         Message Packet2

         Message Packet3

         Message Packet4

 step-4-> I have checked server log and it says server has send 4 string 
          messages

 Step-5 -> On client side I am receiving only first message i.e. Message 
           Packet1, and there no other packets on NSInputStream showing. or NSStreamEventHasBytesAvailable option in delegate method->
- (void)stream:(NSStream *)theStream
handleEvent:(NSStreamEvent)streamEvent

В большинстве случаев не вызывает более одного, но иногда вызывает и получает данные MessagePacket2 или MessagePacket4.

Пожалуйста, помогите мне, я не могу понять, почему я получаю только первый пакет с сервера вместо 4 пакетов, так как сервер отправляет 4 пакета.

Я использовал код из приведенного ниже руководства -> http://www.raywenderlich.com/3932/networking-tutorial-for-ios-how-to-create-a-socket-based-iphone-app-and-server#comments

Мой код здесь->

@interface NetworkManager()<NSStreamDelegate>

@property (strong, nonatomic)NSInputStream        *objInputStream;
@property (strong, nonatomic)NSOutputStream       *objOutputStream;

@end

- (void)initializeNetworkCommunicationToServer
{
self.networkOpened = NO;

CFReadStreamRef readStream;
CFWriteStreamRef writeStream;

CFStreamCreatePairWithSocketToHost(NULL,
                                   (CFStringRef)SERVER_HOSTNAME,
                                   SERVER_PORT_ADDR,
                                   &readStream,
                                   &writeStream);

self.objInputStream = (__bridge_transfer NSInputStream *)readStream;
self.objOutputStream = (__bridge_transfer NSOutputStream*)writeStream;


[self.objInputStream setDelegate:self];
[self.objOutputStream setDelegate:self];

[self.objInputStream scheduleInRunLoop:[NSRunLoop currentRunLoop]
                               forMode:NSDefaultRunLoopMode];
[self.objOutputStream scheduleInRunLoop:[NSRunLoop currentRunLoop]
                                forMode:NSDefaultRunLoopMode];
[self.objInputStream open];
[self.objOutputStream open];

}

//------------------------------------------------------
pragma NSStreamDelegate delegate method
//------------------------------------------------------

- (void)stream:(NSStream *)theStream
handleEvent:(NSStreamEvent)streamEvent
{

switch (streamEvent)
{
    case NSStreamEventNone:
    {
        NSLog(@"NSStreamEventNone");
        break;
    }
    case NSStreamEventOpenCompleted:
    {
        NSLog(@"NSStreamEventOpenCompleted");

    }
        break;
    case NSStreamEventHasBytesAvailable:
    {
        NSLog(@"NSStreamEventHasBytesAvailable:");

        if (theStream == self.objInputStream)
        {
            while ([self.objInputStream hasBytesAvailable])
            {
                uint8_t buffer[1024];
                unsigned int len = 0;

                len = [self.objInputStream read:buffer
                                      maxLength:sizeof(buffer)];
                if (len > 0)
                {

                    NSString *output =
                    [[NSString alloc] initWithBytes:buffer
                                             length:len
                                           encoding:NSASCIIStringEncoding];

                    if (nil != output)
                    {
                        NSLog(@"server said: %@", output);
                    }

                }//end of if(len > 0)

            }//end of while
        } //end of  if (theStream == self.objInputStream)

    }
        break;
    case NSStreamEventErrorOccurred:
    {
        NSLog(@"NSStreamEventErrorOccurred: Can not connect to the host!");
    }
        break;
    case NSStreamEventEndEncountered:
    {

        NSLog(@"NSStreamEventEndEncountered & network connection ended");

        [theStream close];
        [theStream removeFromRunLoop:[NSRunLoop currentRunLoop]
                             forMode:NSDefaultRunLoopMode];

        theStream = nil;
    }
        break;

        // The NSStreamEventHasSpaceAvailable event indicates that you can write (at least one byte!) to the stream without blocking. That does not mean that previously written data is completely delivered to the other endpoint of the connection.
    case NSStreamEventHasSpaceAvailable:
    {
        NSLog(@"NSStreamEventHasSpaceAvailable");

        if(NO == self.networkOpened)
        {
            self.networkOpened = YES;

            [self sendMessage:@"login:username,password"];

        }
    }
        break;
    default:
    {
        NSLog(@"Unknown event");
    }
}
}


//------------------------------------------------------
#pragma mark - send packet
//------------------------------------------------------

- (void)sendMessage:(NSString*)lstrMessage
{
NSMutableData *data = [[NSMutableData alloc] initWithData:
                       [lstrMessage dataUsingEncoding:NSASCIIStringEncoding]];

unsigned char suffixBytes[] = {1, 1, 0};
[data appendBytes:suffixBytes length:3];

[self.objOutputStream write:[data bytes] maxLength:[data length]];

NSLog(@"message sent->%@",[NSString stringWithUTF8String:[data bytes]]);

}

person user4388479    schedule 23.12.2014    source источник


Ответы (1)


Я понятия не имею, что не так с вашим кодом, но мой опыт настройки потоков говорит мне, что будет смысл попробовать другой способ подписки на потоки Core Foundation с использованием CF API вместо бесплатного подключения к NSInputStream. Я имею в виду функции CFReadStreamSetClient и CFReadStreamScheduleWithRunLoop. Вы можете увидеть пример того, как это сделать, в моем вспомогательном классе для тестирования POSInputStreamLibrary.

person Pavel Osipov    schedule 25.12.2014