iOS AsyncSocket使用教程

作者: iOS学末 | 来源:发表于2016-09-06 14:46 被阅读614次
    • 使用AsyncSocket的时候可以做一层封装,根据需求提供几个接口出来。比如:连接、断开连接、发送消息等等。还有接受消息,接受到的消息可以通过通知、代理、block等传出去。
    • 对AsyncSocket使用.一般来说,一个用户只需要建立一个socket长连接,所以可以用单例类方便使用。
    使用AsyncSocket

    1.创建socket的单例类

    //在LGSocketServe.h 
    #import <Foundation/Foundation.h>
    #import "AsyncSocket.h"
    #import "GCDAsyncSocket.h"
    @interface LGSocketServe : NSObject
    //创建属性 用于连接
    @property (nonatomic, strong, readonly) GCDAsyncSocket          *socket;
    @property (nonatomic, copy,   readonly) NSString                *socketHost;
    @property (nonatomic, assign, readonly) uint16_t                socketPort;
    
    //创建单列类
    +(instancetype)shareSocket;
    @end
    
    
    
    //在LGSocketServe.m
    #import "LGSocketServe.h"
    #import <UIKit/UIKit.h>
    
    @interface LGSocketServe ()
    
    @property (nonatomic, strong, readwrite) GCDAsyncSocket         *socket;
    @property (nonatomic, copy,   readwrite) NSString               *socketHost;
    @property (nonatomic, assign, readwrite) uint16_t               socketPort;
    
    @end
    
    @implementation LGSocketServe 
    
    +(instancetype)shareSocket
    {
        static dispatch_once_t onceToken;
        static LGSocketServe *socket;
        dispatch_once(&onceToken, ^{
            socket = [[LGSocketServe alloc]init];
        });
        return socket;
    }
    - (instancetype)init
    {
        self = [super init];
        if (self) {
            self.socket = [[GCDAsyncSocket alloc]initWithDelegate:self delegateQueue:dispatch_get_global_queue(0, 0)];
        }
        return self;
    }
    
    //创建连接
    - (void)connected:(NSString *)host onPort:(uint16_t)port error:(NSError *)error{
        self.socketHost = host;
        self.socketPort = port;
        //必须确认在断开连接的情况下,进行连接
        if (self.socket.isDisconnected) {
            [self.socket connectToHost:self.socketHost onPort:self.socketPort error:nil];
        }else{
            [self.socket disconnect];
            [self.socket connectToHost:self.socketHost onPort:self.socketPort error:nil];
        }
        [self.socket connectToHost:host onPort:port error:nil];
    }
    //心跳连接
    -(void)longConnectToSocket{
        // 根据服务器要求发送固定格式的数据,假设为指令@"longConnect",但是一般不会是这么简单的指令
        NSString *longConnect = @"longConnect\r\n";
        NSData   *dataStream  = [longConnect dataUsingEncoding:NSUTF8StringEncoding];
        [self.socket writeData:dataStream withTimeout:-1 tag:0];
    }
    //连接成功
    - (void)socket:(GCDAsyncSocket *)sock didConnectToHost:(NSString *)host port:(uint16_t)port
    {
        //每隔特定时间向服务器发送心跳包
        //在longConnectToSocket方法中进行长连接需要向服务器发送特定信息
        self.longConnectTimer
        = [NSTimer timerWithTimeInterval:kSocketConnectTimerTimeInterval
                                  target:self
                                selector:@selector(longConnectToSocket)
                                userInfo:nil
                                 repeats:YES];
        [[NSRunLoop currentRunLoop] addTimer:self.longConnectTimer
                                     forMode:NSRunLoopCommonModes];
    }
    //断开连接
    - (void)disConnected{
    
        [self.socket disconnect];
    }
    //断开之后重新连接
    - (void)socketDidDisconnect:(GCDAsyncSocket *)sock withError:(NSError *)err
    {
        //这里可以列举枚举值
        //因用户自动断开 不自动连接
        if (self.offlineError == SZYSocketOfflineByServer) {
            [self.longConnectTimer invalidate];
            self.longConnectTimer = nil;
            [self.socket setDelegate:nil];
            [self.socket disconnect];
        //因服务器原因断开 自动连接
        }else if (self.offlineError == SZYSocketOfflineByServer){
        
            [self.longConnectTimer invalidate];
            self.longConnectTimer = nil;
            [self.socket setDelegate:nil];
            [self.socket disconnect];
            [self.socket setDelegate:self];
            [self.socket connectToHost:self.socketHost
                                onPort:self.socketPort
                                 error:nil];
        //因Wifi原因断开 不自动连接
        }else{
            [self.longConnectTimer invalidate];
            self.longConnectTimer = nil;
            [self.socket setDelegate:nil];
            [self.socket disconnect];
        }
        
    }
    //写入数据
    - (void)writeData:(NSData *)data withTimeout:(NSTimeInterval)timeout tag:(long)tag{
    
        [self.socket writeData:data withTimeout:-1 tag:100];
    }
    - (void)socket:(GCDAsyncSocket *)sock didReadData:(NSData *)data withTag:(long)tag {
        NSString *dataString = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
        NSLog(@"读取到的消息:%@", dataString);
    }
    //读取数据
    - (void)readDataToData:(NSData *)data withTimeout:(NSTimeInterval)timeout tag:(long)tag{
        [self.socket readDataToData:data withTimeout:-1 tag:100];
        
    }
    - (void)socket:(GCDAsyncSocket *)sock didWriteDataWithTag:(long)tag {
        NSLog(@"didWriteDataWithTag");
    }
    
    

    有错误欢迎留言指正

    相关文章

      网友评论

      • 卓敦:楼主,这样只传IP和端口,怎么知道是谁给谁发信息呢
      • df697075d374:楼主你好,一个客户端要连接两个端口怎么搞?

      本文标题:iOS AsyncSocket使用教程

      本文链接:https://www.haomeiwen.com/subject/agtkettx.html