iOS —— CocoaAsyncSocket

CocoaAsyncSocket爲macOS、iOS和tvOS提供了易於使用且功能強大的異步套接字庫。他是基於C 語言Socket的一層封裝,更加的面向對象。使得原生連接狀態以及接受消息等函數都以代理的方式體現。使用性極高,極大提高開發效率。

CocoaAsyncSocket中主要包含兩個類:

  • GCDAsyncSocket.//基於TCP/IP協議的socket網絡庫
  • GCDAsyncUdpSocket.//基於UDP/IP協議的socket網絡庫

GCDAsyncSocket 的使用

@property (nonatomic, strong) GCDAsyncSocket *socket;

    // 1: 創建socekt --id -->
    if (self.socket == nil) {
        self.socket = [[GCDAsyncSocket alloc] initWithDelegate:self delegateQueue:dispatch_get_global_queue(0, 0)];
    }
    
    // 2: 連接socket
    if (!self.socket.isConnected) {
        NSError *error;
        [self.socket connectToHost:@"127.0.0.1" onPort:8090 error:&error];
    }

  // 發送消息
     NSData *data = [self.contentTF.text dataUsingEncoding:NSUTF8StringEncoding];
    [self.socket writeData:data withTimeout:-1 tag:10086];

   GCDAsyncSocketDelegate


//已經連接到服務器
- (void)socket:(GCDAsyncSocket *)sock didConnectToHost:(nonnull NSString *)host port:(uint16_t)port{
    
    NSLog(@"連接成功 : %@---%d",host,port);
    [self.socket readDataWithTimeout:-1 tag:10086];
}

// 連接斷開
- (void)socketDidDisconnect:(GCDAsyncSocket *)sock withError:(NSError *)err{
    NSLog(@"斷開 socket連接 原因:%@",err);
}

//已經接收服務器返回來的數據
- (void)socket:(GCDAsyncSocket *)sock didReadData:(NSData *)data withTag:(long)tag{
    NSLog(@"接收到tag = %ld : %ld 長度的數據",tag,data.length);
    [self.socket readDataWithTimeout:-1 tag:10086];
   // 每次發送數據必須重新開啓監聽,(經典問題)
}

//消息發送成功 代理函數 向服務器 發送消息
- (void)socket:(GCDAsyncSocket *)sock didWriteDataWithTag:(long)tag{
    NSLog(@"%ld 發送數據成功",tag);
}

重連和斷開的操作

//重新連接
    // 1: 創建socekt --id -->
    if (self.socket == nil) {
        self.socket = [[GCDAsyncSocket alloc] initWithDelegate:self delegateQueue:dispatch_get_global_queue(0, 0)];
    }
    
    // 2: 連接socket
    if (!self.socket.isConnected) {
        NSError *error;
        [self.socket connectToHost:@"127.0.0.1" onPort:8090 error:&error];
    }

//關閉socket
    [self.socket disconnect];
    self.socket = nil;

GCDAsyncUdpSocket

udp 在連接的時候直接綁定端口,不需要地址的連接,極大節約了時間。 在發送消息的時候,直接對着某個地址的的某個端口直接發送,類似廣播形式。


@property (nonatomic, strong) GCDAsyncUdpSocket *udpSocket;

 // 1. 創建UDP
    if (!self.udpSocket) {
        self.udpSocket = [[GCDAsyncUdpSocket alloc]initWithDelegate:sender delegateQueue:dispatch_get_global_queue(0, 0)];
    }
    //2. 綁定socket
    NSError *error;
    [self.udpSocket bindToPort:8090 error:&error];
    if (error) {
        // 監聽錯誤
    }else{
        //監聽成功則開始接收消息
        [self.udpSocket beginReceiving:&error];
    }
   // 發送消息
    [self.udpSocket sendData:[NSData new] toHost:@"192.168.31.19" port:8090 withTimeout:-1 tag:10010];


#pragma mark - GCDAsyncUdpSocketDelegate

// 連接成功
- (void)udpSocket:(GCDAsyncUdpSocket *)sock didConnectToAddress:(NSData *)address{
    NSLog(@"連接成功 --- %@",address);
}

// 連接失敗
- (void)udpSocket:(GCDAsyncUdpSocket *)sock didNotConnect:(NSError *)error{
    NSLog(@"連接失敗 反饋: %@",error);
}

// 發送數據成功
- (void)udpSocket:(GCDAsyncUdpSocket *)sock didSendDataWithTag:(long)tag{
    NSLog(@"%ld tag 發送數據成功",tag);
}

// 發送數據失敗
- (void)udpSocket:(GCDAsyncUdpSocket *)sock didNotSendDataWithTag:(long)tag dueToError:(NSError *)error{
    NSLog(@"%ld tag 發送數據失敗 : %@",tag,error);
}

// 接受數據的回調
- (void)udpSocket:(GCDAsyncUdpSocket *)sock didReceiveData:(NSData *)data fromAddress:(NSData *)address withFilterContext:(id)filterContext{
    
}

// 關閉失敗
- (void)udpSocketDidClose:(GCDAsyncUdpSocket *)sock withError:(NSError *)error{
    NSLog(@"關閉失敗: %@",error);
}

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章