• iOS开发--XMPPFramework--用户登录(三)


    创了一个XMPP即时通讯交流群140147825,欢迎大家来交流~我们是一起写代码的弟兄~

    我们在第一篇文章中,已经介绍了Openfire服务器的搭建等环境的配置,

    第二篇文章中,导入了XMPPFramework框架,

    这一篇,我们将正式进入代码环节,说一说用户的登陆。

    1、我们选择新建一个XMPPManager来统一管理即时聊天模块,当然,这个对象得要是个单例。并在其中配置控制台打印设置,这样能让我们看得更清楚些。

    + (instancetype)sharedInstance {
        static dispatch_once_t onceToken;
        dispatch_once(&onceToken, ^{
            instance = [[XMPPManager alloc] init];
            
            //配置日志打印工具
            [DDLog addLogger:[DDTTYLogger sharedInstance] withLogLevel:XMPP_LOG_FLAG_SEND_RECV];
            
            //打开控制台文字色彩
            [[DDTTYLogger sharedInstance] setColorsEnabled:YES];
            //XMPP_LOG_FLAG_SEND | XMPP_LOG_FLAG_RECV_POST 给这2个级别一人一个颜色
            [[DDTTYLogger sharedInstance] setForegroundColor:[UIColor orangeColor] backgroundColor:[UIColor whiteColor] forFlag:XMPP_LOG_FLAG_SEND];
            [[DDTTYLogger sharedInstance] setForegroundColor:[UIColor magentaColor] backgroundColor:[UIColor whiteColor] forFlag:XMPP_LOG_FLAG_RECV_POST];
        });
        return instance;
    }

    我们首先在这个单例中初始化一个XMPPStream对象,起到连接的作用。我们用getter方法进行加载:

    - (XMPPStream *)xmppStream {
        if (_xmppStream == nil) {
            _xmppStream = [[XMPPStream alloc] init];
            [_xmppStream addDelegate:self delegateQueue:dispatch_get_main_queue()];
            [_xmppStream setHostName:@"172.10.0.95"];
            [_xmppStream setHostPort:5222];
            [self setupModule];
        }
        return _xmppStream;
    }

    我们先对XMPPStream进行初始化,再用addDelegate: delegateQueue:方法添加XMPPManager对象为代理。

    这里的第二个参数需要注意,需要传入一个队列,这个队列,决定了回调执行的队列,是在主队列还是其他队列。

    另外,XMPPStream对象可以添加多个代理,实现的原理我们会在以后讨论。简单来说,内部的实现,就是将其加入一个数组中。

    HostName和HostPort是本机配置的Openfire服务器的地址和端口,并且在最后设置我们需要用到的模块。

    2、设置模块

    // 设置模块
    - (void)setupModule {
        // 心跳检测
        self.xmppAutoPing = [[XMPPAutoPing alloc] initWithDispatchQueue:dispatch_get_main_queue()];
        // 客户端检测频率
        [self.xmppAutoPing setPingTimeout:360.0f];
        // 是否响应对方的ping
        [self.xmppAutoPing setRespondsToQueries:YES];
        [self.xmppAutoPing addDelegate:self delegateQueue:dispatch_get_main_queue()];
        
        // 自动重连模块
        self.xmppReconnect = [[XMPPReconnect alloc] initWithDispatchQueue:dispatch_get_main_queue()];
        [self.xmppReconnect setAutoReconnect:YES];
        
        // 激活
        [self.xmppAutoPing activate:self.xmppStream];
        [self.xmppReconnect activate:self.xmppStream];
    }

    我们可以根据注释看到,分别设置了心跳检测模块,自动重连模块,并且设置了代理,并分别在XMPPStream对象上进行激活,不然不会工作。

    3、连接及身份验证

    我们写了一个连接登录的方法

    - (void)loginWithJid:(XMPPJID *)aJid addPassword:(NSString *)password {
        self.myJID = aJid;
        [self.xmppStream setMyJID:aJid];
        [self.xmppStream connectWithTimeout:XMPPStreamTimeoutNone error:nil];
        self.myPassword = password;
    }

    这里需要说明,JID代表了每个用户,一般由三部分构成:用户名,域名和资源名,例如 test@example.com/Anthony。

    我们保存下来当前准备连接登录用户的JID和密码,并调用connectWithTimeout:error:进行连接。

    还记得我们之前给XMPPStream对象设置的代理吗?现在就派上用场啦,我们刚刚设置的,在主队列进行回调,下面是回调方法。

    /**
     *  socket连接建立成功 三次握手成功
     */
    - (void)xmppStream:(XMPPStream *)sender socketDidConnect:(GCDAsyncSocket *)socket {
        // [self.xmppStream authenticateWithPassword:self.myPassword error:nil];
    }
    
    /**
     * XML 流被完全打开的时候调用
     * At this point it's safe to begin communication with the server.
     * 在这个时间点 跟服务器对话是安全的
     **/
    - (void)xmppStreamDidConnect:(XMPPStream *)sender {
        //1.登录
        //2.上线
        [self.xmppStream authenticateWithPassword:self.myPassword error:nil];
    }
    
    //登录成功的委托
    - (void)xmppStreamDidAuthenticate:(XMPPStream *)sender {
        //<presence from= to= type= >
        //<show--系统状态图标/><status/>
        //</presence>
        //<presence/>
        //1.上线
        XMPPPresence *presence = [XMPPPresence presence];
        [presence addChild:[DDXMLElement elementWithName:@"show" stringValue:@"xa"]];
        [presence addChild:[DDXMLElement elementWithName:@"status" stringValue:@"快来找我聊天吧"]];
        [self.xmppStream sendElement:presence];
    }

    连接成功的情况下,会调用第一个和第二个方法。我们在第二个方法里面写登录认证,认证成功后,调用第三个方法,这样,我们就登录成功了!

    第三个方法中,我们可以设置我们的上线状态,调用sendElement:方法传一个XMPPPresence对象,告诉服务器我的登录状态。

    当然,也有连接失败的情况,会进入下面的回调:

    - (void)xmppStreamDidDisconnect:(XMPPStream *)sender withError:(NSError *)error {
        
    }
    
    - (void)xmppStream:(XMPPStream *)sender didNotAuthenticate:(DDXMLElement *)error {
        
    }

    当出现失败的情况,可以找一下是不是网络的原因,或者对照下上面说的模块,如果没有解决,欢迎贴出来大家讨论一下~

    以上就是用户登录的内容,下一篇,我们来说一说好友模块,下篇见~

     创了一个XMPP即时通讯交流群140147825,欢迎大家来交流~我们是一起写代码的弟兄~

  • 相关阅读:
    ORA-28000 帐户已被锁定问题处理
    德邦总管 修改oracle数据库用户密码的方法
    测试面试题目
    python 把一文件包含中文的字符写到另外文件乱码 UnicodeDecodeError: 'gbk' codec can't decode byte 0xac in position
    python version 2.7 required,which was not found in the registry
    ImportError: No module named dateutil.parser
    解决python2.x用urllib2证书验证错误, _create_unverified_context
    python多版本兼容性问题:当同时安装Python2和Python3后,如何兼容并切换
    MAC OS git客户端安装及操作
    Pycharm连接gitlab
  • 原文地址:https://www.cnblogs.com/FrankieZ/p/5281797.html
Copyright © 2020-2023  润新知