OpenFire:在 IQHandler 中,如何获取发送它的经过身份验证的用户?

Posted

技术标签:

【中文标题】OpenFire:在 IQHandler 中,如何获取发送它的经过身份验证的用户?【英文标题】:OpenFire: In an IQHandler, how to get the authenticated user that sent it? 【发布时间】:2014-03-31 04:53:36 【问题描述】:

我想实现一个IQHandler,但我想确保只有经过身份验证的用户才能向它发送 IQ 数据包。我想确保我从Packet.getFrom() 获得的 JID 是发送它的经过身份验证的用户。 我需要这个,这样没有人可以创建一个 IQ 数据包并将“来自”属性设置为他们自己以外的用户 ID。有人可以帮我解决这个问题吗?

【问题讨论】:

【参考方案1】:

试试这个:

ClientSession session = sessionManager.getSession(sender);
if(session.getStatus() == Session.STATUS_AUTHENTICATED) 
    //YOUR STUFF HERE

更新:

仔细观察源头。看来 IQRouter 已经为您完成了这项工作。如果您未通过身份验证,则服务器响应会出现错误说明。

public void route(IQ packet) 
        if (packet == null) 
            throw new NullPointerException();
        
        JID sender = packet.getFrom();
        ClientSession session = sessionManager.getSession(sender);
        try 
            // Invoke the interceptors before we process the read packet
            InterceptorManager.getInstance().invokeInterceptors(packet, session, true, false);
            JID to = packet.getTo();
            if (session != null && to != null && session.getStatus() == Session.STATUS_CONNECTED &&
                    !serverName.equals(to.toString())) 
                // User is requesting this server to authenticate for another server. Return
                // a bad-request error
                IQ reply = IQ.createResultIQ(packet);
                reply.setChildElement(packet.getChildElement().createCopy());
                reply.setError(PacketError.Condition.bad_request);
                session.process(reply);
                Log.warn("User tried to authenticate with this server using an unknown receipient: " +
                        packet.toXML());
            
            else if (session == null || session.getStatus() == Session.STATUS_AUTHENTICATED || (
                    isLocalServer(to) && (
                            "jabber:iq:auth".equals(packet.getChildElement().getNamespaceURI()) ||
                                    "jabber:iq:register"
                                            .equals(packet.getChildElement().getNamespaceURI()) ||
                                    "urn:ietf:params:xml:ns:xmpp-bind"
                                            .equals(packet.getChildElement().getNamespaceURI())))) 
                handle(packet);
            
            else 
                IQ reply = IQ.createResultIQ(packet);
                reply.setChildElement(packet.getChildElement().createCopy());
                reply.setError(PacketError.Condition.not_authorized);
                session.process(reply);
            
            // Invoke the interceptors after we have processed the read packet
            InterceptorManager.getInstance().invokeInterceptors(packet, session, true, true);
        

【讨论】:

我在源代码中看到了这个,所以我也假设你在说什么。但我的担忧仍然存在。似乎客户端可以为任何用户在数据包中设置from 字段,如果该用户在任何地方经过身份验证,服务器将接受它,不一定在用于发送数据包的会话中。所以,感觉就像sessionManager.getSession(sender) 会给你一个与我们用来发送这个数据包的会话完全无关的会话。

以上是关于OpenFire:在 IQHandler 中,如何获取发送它的经过身份验证的用户?的主要内容,如果未能解决你的问题,请参考以下文章

如何在 Openfire 中使用 smack

如何在 xmpp openfire 服务器中启用 websockets

如何让 Openfire 用户出现在聊天室中

如何使用 PHP 在 openfire 中创建聊天室并将用户添加到房间中

如何在android应用程序中从openfire获取离线消息[关闭]

如何在 Android 应用中使用 Smack 从 Openfire 服务器恢复两个用户之间的聊天记录