示例#1
0
        private IQ GetPrivate(XmppStream stream, IQ iq, XmppHandlerContext context)
        {
            var privateStore = (Private)iq.Query;

            if (!privateStore.HasChildElements)
            {
                return(XmppStanzaError.ToNotAcceptable(iq));
            }

            var retrived = new List <Element>();

            foreach (var childNode in privateStore.ChildNodes)
            {
                if (childNode is Element)
                {
                    var elementToRetrive = (Element)childNode;
                    var elementRestored  = context.StorageManager.PrivateStorage.GetPrivate(iq.From, elementToRetrive);
                    retrived.Add(elementRestored ?? elementToRetrive);
                }
            }

            privateStore.RemoveAllChildNodes();
            foreach (var element in retrived)
            {
                privateStore.AddChild(element);
            }

            iq.SwitchDirection();
            iq.Type = IqType.result;
            return(iq);
        }
示例#2
0
        private void ProcessAuthIQSet(XmppStream stream, AuthIq iq, XmppHandlerContext context)
        {
            if (string.IsNullOrEmpty(iq.Query.Username) || string.IsNullOrEmpty(iq.Query.Resource))
            {
                context.Sender.SendTo(stream, XmppStanzaError.ToNotAcceptable(iq));
                return;
            }

            bool authorized = false;

            if (!string.IsNullOrEmpty(iq.Query.Digest))
            {
                authorized = AuthDigest(iq.Query.Username, iq.Query.Digest, stream, context.UserManager);
            }
            if (!string.IsNullOrEmpty(iq.Query.Password))
            {
                authorized = AuthPlain(iq.Query.Username, iq.Query.Password, stream, context.UserManager);
            }
            if (authorized)
            {
                stream.Authenticate(iq.Query.Username);

                var answer = new IQ(IqType.result);
                answer.Id   = iq.Id;
                answer.To   = iq.From;
                answer.From = iq.To;
                context.Sender.SendTo(stream, answer);
            }
            else
            {
                context.Sender.SendTo(stream, XmppStanzaError.ToNotAuthorized(iq));
            }
        }
示例#3
0
        private void ProcessAuthIQSet(XmppStream stream, AuthIq iq, XmppHandlerContext context)
        {
            if (string.IsNullOrEmpty(iq.Query.Username) || string.IsNullOrEmpty(iq.Query.Resource))
            {
                context.Sender.SendTo(stream, XmppStanzaError.ToNotAcceptable(iq));
                return;
            }

            context.Sender.SendTo(stream, XmppStanzaError.ToNotAuthorized(iq));
        }
        public override IQ HandleIQ(XmppStream stream, IQ iq, XmppHandlerContext context)
        {
            if (iq.Type != IqType.get || !iq.HasTo)
            {
                return(XmppStanzaError.ToNotAcceptable(iq));
            }

            var currSession = context.SessionManager.GetSession(iq.From);

            if (currSession == null || !currSession.Available)
            {
                return(XmppStanzaError.ToForbidden(iq));
            }

            double seconds = 0;//available

            if (iq.To.IsServer)
            {
                seconds = (DateTime.UtcNow - startedTime).TotalSeconds;
            }
            else
            {
                var session = context.SessionManager.GetSession(iq.To);
                if (session == null || !session.Available)
                {
                    var lastActivity = context.StorageManager.OfflineStorage.GetLastActivity(iq.To);
                    if (lastActivity != null)
                    {
                        seconds        = (DateTime.UtcNow - lastActivity.LogoutDateTime).TotalSeconds;
                        iq.Query.Value = lastActivity.Status;
                    }
                    else
                    {
                        return(XmppStanzaError.ToRecipientUnavailable(iq));
                    }
                }
            }

            ((Last)(iq.Query)).Seconds = (int)seconds;
            iq.Type = IqType.result;
            iq.SwitchDirection();
            return(iq);
        }
示例#5
0
        private IQ SetPrivate(XmppStream stream, IQ iq, XmppHandlerContext context)
        {
            var @private = (Private)iq.Query;

            if ([email protected])
            {
                return(XmppStanzaError.ToNotAcceptable(iq));
            }

            foreach (var childNode in @private.ChildNodes)
            {
                if (childNode is Element)
                {
                    context.StorageManager.PrivateStorage.SetPrivate(iq.From, (Element)childNode);
                }
            }
            iq.Query = null;
            iq.SwitchDirection();
            iq.Type = IqType.result;
            return(iq);
        }
示例#6
0
        public override void ElementHandle(XmppStream stream, Element element, XmppHandlerContext context)
        {
            var iq = (AuthIq)element;

            if (stream.Authenticated)
            {
                context.Sender.SendTo(stream, XmppStanzaError.ToConflict(iq));
                return;
            }

            if (iq.Type == IqType.get)
            {
                ProcessAuthIQGet(stream, iq, context);
            }
            else if (iq.Type == IqType.set)
            {
                ProcessAuthIQSet(stream, iq, context);
            }
            else
            {
                context.Sender.SendTo(stream, XmppStanzaError.ToNotAcceptable(iq));
            }
        }
示例#7
0
        public void ProcessStreamElement(Node node, XmppStream stream)
        {
            if (node == null)
            {
                throw new ArgumentNullException("node");
            }
            if (stream == null)
            {
                throw new ArgumentNullException("stream");
            }

            try
            {
                var address = new Jid(stream.Domain);

                foreach (var handler in HandlerStorage.GetStreamHandlers(address, node.GetType()))
                {
                    handler.ElementHandle(stream, (Element)node.Clone(), context);
                }

                if (node is Stanza)
                {
                    var stanza = (Stanza)node;

                    if (!validator.ValidateStanza(stanza, stream, context))
                    {
                        return;
                    }

                    if (stanza.HasTo)
                    {
                        address = stanza.To;
                    }

                    var handlres = HandlerStorage.GetStanzaHandlers(address, GetStanzaType(stanza));
                    if (handlres.Count == 0)
                    {
                        if (stanza is IQ)
                        {
                            var iq = (IQ)stanza;
                            if ((iq.Type == IqType.error || iq.Type == IqType.result) && iq.HasTo && iq.To.HasUser)
                            {
                                //result and error retranslate to user
                                var session = context.SessionManager.GetSession(iq.To);
                                if (session != null)
                                {
                                    sender.SendTo(session, iq);
                                    return;
                                }
                            }
                            //result and error ignored by server
                        }
                        sender.SendTo(stream, XmppStanzaError.ToServiceUnavailable(stanza));
                        log.DebugFormat("Stanza handler not found for address '{0}'", address);
                        return;
                    }

                    bool      iqHandled = true;
                    Stopwatch stopwatch = null;

                    foreach (var handler in handlres)
                    {
                        if (log.IsDebugEnabled)
                        {
                            stopwatch = Stopwatch.StartNew();
                        }

                        if (stanza is IQ)
                        {
                            var answer = handler.HandleIQ(stream, (IQ)stanza.Clone(), context);
                            if (answer != null)
                            {
                                sender.SendTo(stream, answer);
                                iqHandled = answer.Id == stanza.Id;
                            }
                        }
                        else if (stanza is Message)
                        {
                            handler.HandleMessage(stream, (Message)stanza.Clone(), context);
                        }
                        else if (stanza is Presence)
                        {
                            handler.HandlePresence(stream, (Presence)stanza.Clone(), context);
                        }
                        else
                        {
                            sender.SendTo(stream, XmppStanzaError.ToNotAcceptable(stanza));
                            return;
                        }

                        if (log.IsDebugEnabled)
                        {
                            stopwatch.Stop();
                            log.DebugFormat("Process stanza handler '{1}' on address '{0}', time: {2}ms", address, handler.GetType().FullName, stopwatch.Elapsed.TotalMilliseconds);
                        }
                    }
                    if (!iqHandled)
                    {
                        sender.SendTo(stream, XmppStanzaError.ToServiceUnavailable(stanza));
                        return;
                    }
                }
            }
            catch (Exception ex)
            {
                ProcessException(ex, node, stream);
            }
        }
        private IQ SetRegister(XmppStream stream, IQ iq, XmppHandlerContext context)
        {
            var register = (Register)iq.Query;

            iq.Type = IqType.result;

            if (register.RemoveAccount)
            {
                if (!stream.Authenticated || !iq.From.HasUser)
                {
                    context.Sender.SendToAndClose(stream, XmppStreamError.NotAuthorized);
                }

                context.UserManager.RemoveUser(iq.From);
                foreach (var s in context.SessionManager.GetBareJidSessions(iq.From))
                {
                    if (s.Stream.Id == stream.Id)
                    {
                        continue;
                    }
                    context.Sender.SendToAndClose(s.Stream, XmppStreamError.Conflict);
                }
                //TODO: remove roster subscriptions
                register.RemoveAllChildNodes();
                iq.SwitchDirection();
                return(iq);
            }

            if (string.IsNullOrEmpty(register.Username) ||
                string.IsNullOrEmpty(register.Password) ||
                Stringprep.NamePrep(register.Username) != register.Username)
            {
                var error = XmppStanzaError.ToNotAcceptable(iq);
                if (string.IsNullOrEmpty(register.Username))
                {
                    error.Error.Message = "Empty required field Username.";
                }
                else if (string.IsNullOrEmpty(register.Password))
                {
                    error.Error.Message = "Empty required field Password.";
                }
                else if (Stringprep.NamePrep(register.Username) != register.Username)
                {
                    error.Error.Message = "Invalid character.";
                }
                return(error);
            }

            var userJid = new Jid(register.Username, stream.Domain, null);

            if (context.UserManager.IsUserExists(userJid))
            {
                return(XmppStanzaError.ToConflict(iq));
            }

            var user = new User(userJid, register.Password);

            context.UserManager.SaveUser(user);

            register.RemoveAllChildNodes();
            if (stream.Authenticated)
            {
                iq.SwitchDirection();
            }
            else
            {
                iq.To = null;
            }
            iq.From = null;
            return(iq);
        }