diff options
author | Guillaume Melquiond <guillaume.melquiond@gmail.com> | 2007-08-17 17:20:30 +0000 |
---|---|---|
committer | Guillaume Melquiond <guillaume.melquiond@gmail.com> | 2007-08-17 17:20:30 +0000 |
commit | ea118bf61623bcfae4b405d1bb2381b8d80d2837 (patch) | |
tree | 6ce388eb6ed9c15098980e5937f691ce4b5b816e /src/chat-server | |
parent | df2091fd748f83d34543a61d05e44f617412d9c0 (diff) | |
download | manaserv-ea118bf61623bcfae4b405d1bb2381b8d80d2837.tar.gz manaserv-ea118bf61623bcfae4b405d1bb2381b8d80d2837.tar.bz2 manaserv-ea118bf61623bcfae4b405d1bb2381b8d80d2837.tar.xz manaserv-ea118bf61623bcfae4b405d1bb2381b8d80d2837.zip |
Used TokenCollector to manage cookies in ChatHandler.
Diffstat (limited to 'src/chat-server')
-rw-r--r-- | src/chat-server/chathandler.cpp | 125 | ||||
-rw-r--r-- | src/chat-server/chathandler.hpp | 56 |
2 files changed, 79 insertions, 102 deletions
diff --git a/src/chat-server/chathandler.cpp b/src/chat-server/chathandler.cpp index d202dd99..8710168d 100644 --- a/src/chat-server/chathandler.cpp +++ b/src/chat-server/chathandler.cpp @@ -39,44 +39,19 @@ #include "utils/stringfilter.h" #include "utils/tokendispenser.hpp" - -struct ChatPendingLogin -{ - std::string character; - AccountLevel level; - int timeout; -}; - -typedef std::map< std::string, ChatPendingLogin > ChatPendingLogins; -static ChatPendingLogins pendingLogins; - -typedef std::map< std::string, ChatClient * > ChatPendingClients; -static ChatPendingClients pendingClients; - void registerChatClient(const std::string &token, const std::string &name, int level) { - ChatPendingClients::iterator i = pendingClients.find(token); - if (i != pendingClients.end()) - { - ChatClient *computer = i->second; - computer->characterName = name; - computer->accountLevel = (AccountLevel) level; - pendingClients.erase(i); - MessageOut result; - result.writeShort(CPMSG_CONNECT_RESPONSE); - result.writeByte(ERRMSG_OK); - computer->send(result); - } - else - { - ChatPendingLogin p; - p.character = name; - p.level = (AccountLevel) level; - p.timeout = 300; // world ticks - pendingLogins.insert(std::make_pair(token, p)); - } + ChatHandler::Pending *p = new ChatHandler::Pending; + p->character = name; + p->level = (AccountLevel) level; + chatHandler->mTokenCollector.addPendingConnect(token, p); +} + +ChatHandler::ChatHandler(): + mTokenCollector(this) +{ } bool ChatHandler::startListen(enet_uint16 port) @@ -85,15 +60,27 @@ bool ChatHandler::startListen(enet_uint16 port) return ConnectionHandler::startListen(port); } -void ChatHandler::removeOutdatedPending() +void ChatHandler::deletePendingClient(ChatClient *c) { - ChatPendingLogins::iterator i = pendingLogins.begin(), next; - while (i != pendingLogins.end()) - { - next = i; ++next; - if (--i->second.timeout <= 0) pendingLogins.erase(i); - i = next; - } + MessageOut msg(GPMSG_CONNECTION_TIMEDOUT); + + // The computer will be deleted when the disconnect event is processed + c->disconnect(msg); +} + +void ChatHandler::deletePendingConnect(Pending *p) +{ + delete p; +} + +void ChatHandler::tokenMatched(ChatClient *c, Pending *p) +{ + c->characterName = p->character; + c->accountLevel = p->level; + delete p; + MessageOut msg(CPMSG_CONNECT_RESPONSE); + msg.writeByte(ERRMSG_OK); + c->send(msg); } NetComputer *ChatHandler::computerConnected(ENetPeer *peer) @@ -101,28 +88,22 @@ NetComputer *ChatHandler::computerConnected(ENetPeer *peer) return new ChatClient(peer); } -void ChatHandler::computerDisconnected(NetComputer *computer) +void ChatHandler::computerDisconnected(NetComputer *comp) { - // Remove user from all channels - chatChannelManager-> - removeUserFromAllChannels(static_cast<ChatClient*>(computer)); - ChatPendingClients::iterator i_end = pendingClients.end(); - for (ChatPendingClients::iterator i = pendingClients.begin(); - i != i_end; ++i) + ChatClient *computer = static_cast< ChatClient * >(comp); + + if (computer->characterName.empty()) { - if (i->second == computer) - { - pendingClients.erase(i); - break; - } + // Not yet fully logged in, remove it from pending clients. + mTokenCollector.deletePendingClient(computer); + } + else + { + // Remove user from all channels. + chatChannelManager->removeUserFromAllChannels(computer); } - delete computer; -} -void ChatHandler::process(enet_uint32 timeout) -{ - ConnectionHandler::process(timeout); - removeOutdatedPending(); + delete computer; } void ChatHandler::processMessage(NetComputer *comp, MessageIn &message) @@ -133,26 +114,9 @@ void ChatHandler::processMessage(NetComputer *comp, MessageIn &message) if (computer.characterName.empty()) { if (message.getId() != PCMSG_CONNECT) return; - std::string magic_token = message.readString(MAGIC_TOKEN_LENGTH); - ChatPendingLogins::iterator i = pendingLogins.find(magic_token); - if (i == pendingLogins.end()) - { - ChatPendingClients::iterator i_end = pendingClients.end(); - for (ChatPendingClients::iterator i = pendingClients.begin(); - i != i_end; ++i) - { - if (i->second == &computer) return; - } - pendingClients.insert(std::make_pair(magic_token, &computer)); - return; - } - computer.characterName = i->second.character; - computer.accountLevel = i->second.level; - pendingLogins.erase(i); - result.writeShort(CPMSG_CONNECT_RESPONSE); - result.writeByte(ERRMSG_OK); - computer.send(result); + std::string magic_token = message.readString(MAGIC_TOKEN_LENGTH); + mTokenCollector.addPendingClient(magic_token, &computer); // sendGuildRejoin(computer); return; } @@ -481,8 +445,7 @@ ChatHandler::handleUnregisterChannelMessage(ChatClient &client, MessageIn &msg) client.send(reply); } - void -ChatHandler::handleEnterChannelMessage(ChatClient &client, MessageIn &msg) +void ChatHandler::handleEnterChannelMessage(ChatClient &client, MessageIn &msg) { MessageOut reply(CPMSG_ENTER_CHANNEL_RESPONSE); diff --git a/src/chat-server/chathandler.hpp b/src/chat-server/chathandler.hpp index 72f0ef31..43e70013 100644 --- a/src/chat-server/chathandler.hpp +++ b/src/chat-server/chathandler.hpp @@ -29,6 +29,7 @@ #include "net/connectionhandler.hpp" class ChatClient; +enum AccountLevel; /** * Manages chat related things like private messaging, chat channel handling @@ -40,14 +41,19 @@ class ChatClient; */ class ChatHandler : public ConnectionHandler { - public: + /** - * Overridden from ConnectionHandler to also clean connected clients - * that haven't sent in a magic token. - * - * @see ConnectionHandler::process + * Data needed for initializing a ChatClient. */ - void process(enet_uint32 timeout = 0); + struct Pending + { + std::string character; + AccountLevel level; + }; + + public: + + ChatHandler(); /** * Start the handler. @@ -78,6 +84,21 @@ class ChatHandler : public ConnectionHandler const std::string &inviterName, const std::string &guildName); + /** + * Called by TokenCollector when a client wrongly connected. + */ + void deletePendingClient(ChatClient *); + + /** + * Called by TokenCollector when a client failed to connect. + */ + void deletePendingConnect(Pending *); + + /** + * Called by TokenCollector when a client succesfully connected. + */ + void tokenMatched(ChatClient *, Pending *); + protected: /** * Process chat related messages. @@ -147,28 +168,14 @@ class ChatHandler : public ConnectionHandler const std::string &text); /** - * Sends a message to every client in a registered channel. O(c*u), - * where <b>c</b> is the amount of connected clients and <b>u</b> the - * number of users in the given channel. + * Sends a message to every client in a registered channel. * * @param channel the channel to send the message in, must not be NULL * @param msg the message to be sent - * - * @todo <b>b_lindeijer:</b> Currently this method is looping through - * the channel users for each connected client in order to - * determine whether it should receive the message. It would be - * much better to directly associate the connected clients with - * the channel. */ void sendInChannel(ChatChannel *channel, MessageOut &msg); /** - * Removes outdated pending logins. These are connected clients that - * still haven't sent in their magic token. - */ - void removeOutdatedPending(); - - /** * Send user joined message. * * @param channel the channel to send the message in, must not be NULL @@ -183,6 +190,13 @@ class ChatHandler : public ConnectionHandler * @param name the name of the user who left */ void sendUserLeft(ChatChannel *channel, const std::string &name); + + /** + * Container for pending clients and pending connections. + */ + TokenCollector<ChatHandler, ChatClient *, Pending *> mTokenCollector; + friend void registerChatClient(const std::string &, const std::string &, int); + }; /** |