Changeset 6 in chevmsgr
- Timestamp:
- 08/29/15 02:20:50 (9 years ago)
- Location:
- trunk
- Files:
-
- 6 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/cf/network.cpp
r4 r6 182 182 cf::network::tcp::~tcp() 183 183 { 184 close();185 184 } 186 185 -
trunk/msg.cpp
r5 r6 5 5 makeTemplate(_obj, _type); \ 6 6 7 namespace Message 7 #define DELIMITER "$" 8 9 namespace Protocol 8 10 { 9 11 // parser 10 void Parser::parse(const std::string & message)12 void Message::parse(const std::string & message) 11 13 { 12 14 mObject = json::Deserialize(message); 13 15 } 14 16 15 std::string Parser::type() const17 std::string Message::type() const 16 18 { 17 19 return get<std::string>("type"); … … 31 33 void Request::makeTemplate(json::Object & obj, const std::string & type) const 32 34 { 33 obj["id"] = mID; 34 obj["type"] = type; 35 } 36 37 std::string Request::command(const std::string & cmd) const 38 { 39 DECLARE_TEMPLATE_OBJECT(obj, "command"); 40 41 obj["command"] = cmd; 42 43 return json::Serialize(obj); 35 obj[ProtocolType::ID ] = mID; 36 obj[ProtocolType::TYPE] = type; 44 37 } 45 38 46 39 std::string Request::sms(const std::string & phone) const 47 40 { 48 DECLARE_TEMPLATE_OBJECT(obj, "sms");41 DECLARE_TEMPLATE_OBJECT(obj, ProtocolType::SMS); 49 42 50 obj[ "phone"] = phone;43 obj[ProtocolType::PHONE] = phone; 51 44 52 45 return json::Serialize(obj); … … 55 48 std::string Request::join(const std::string & id, const std::string & pw, const std::string & sms) 56 49 { 57 DECLARE_TEMPLATE_OBJECT(obj, "join");50 DECLARE_TEMPLATE_OBJECT(obj, ProtocolType::JOIN); 58 51 59 obj[ "id"] = id;60 obj[ "pw"] = pw;61 obj[ "sms"] = sms;52 obj[ProtocolType::ID ] = id; 53 obj[ProtocolType::PW ] = pw; 54 obj[ProtocolType::SMS] = sms; 62 55 63 56 return json::Serialize(obj); … … 66 59 std::string Request::login(const std::string & pw) const 67 60 { 68 DECLARE_TEMPLATE_OBJECT(obj, "login");61 DECLARE_TEMPLATE_OBJECT(obj, ProtocolType::LOGIN); 69 62 70 obj[ "pw"] = mID + "$"+ pw;63 obj[ProtocolType::PW] = mID + DELIMITER + pw; 71 64 72 65 return json::Serialize(obj); 73 66 } 74 67 75 std::string Request:: chat(const std::string & to, const std::string & sessid, const std::string & message) const68 std::string Request::addFriend(const std::string & id) const 76 69 { 77 DECLARE_TEMPLATE_OBJECT(obj, "chat");70 DECLARE_TEMPLATE_OBJECT(obj, ProtocolType::ADD_FRIEND); 78 71 79 obj["from" ] = mID; 80 obj["to" ] = to; 81 obj["sess-id"] = sessid; 82 obj["message"] = message; 72 obj[ProtocolType::ID] = id; 83 73 84 74 return json::Serialize(obj); 85 75 } 86 76 87 std::string Request:: friendList() const77 std::string Request::openSession(const std::string & to) const 88 78 { 89 DECLARE_TEMPLATE_OBJECT(obj, "friend-list"); 79 DECLARE_TEMPLATE_OBJECT(obj, ProtocolType::OPEN_SESSION); 80 81 obj[ProtocolType::TO] = to; 82 83 return json::Serialize(obj); 84 } 85 86 std::string Request::chat(const std::string & sessid, const std::string & message, const int sensitive) const 87 { 88 DECLARE_TEMPLATE_OBJECT(obj, ProtocolType::CHAT); 89 90 obj[ProtocolType::FROM ] = mID; 91 obj[ProtocolType::SESSION_ID] = sessid; 92 obj[ProtocolType::MESSAGE ] = message; 93 obj[ProtocolType::SENSITIVE ] = sensitive; 94 95 return json::Serialize(obj); 96 } 97 98 std::string Request::getFriendList() const 99 { 100 DECLARE_TEMPLATE_OBJECT(obj, ProtocolType::GET_FRIEND_LIST); 90 101 91 102 return json::Serialize(obj); … … 95 106 void Response::makeTemplate(json::Object & obj, const std::string & type) const 96 107 { 97 obj[ "type"] = type;108 obj[ProtocolType::TYPE] = type; 98 109 } 99 110 100 std::string Response::result(const bool status) const111 std::string Response::result(const std::string & requestType, const bool status) const 101 112 { 102 DECLARE_TEMPLATE_OBJECT(obj, "result");113 DECLARE_TEMPLATE_OBJECT(obj, ProtocolType::RESULT); 103 114 104 obj[ "result"] = status;115 obj[ProtocolType::RESULT] = status; 105 116 106 117 return json::Serialize(obj); -
trunk/msg.hpp
r5 r6 8 8 #include <string> 9 9 #include <vector> 10 11 typedef struct SFriend 12 { 13 std::string id; 14 std::string name; 15 } SFriend; 16 17 // -------------------------------------------------------------- 18 19 namespace ProtocolType 20 { 21 #define DECLARE_KEY(_t) static const std::string _t = #_t 22 23 DECLARE_KEY(ID); 24 DECLARE_KEY(TYPE); 25 DECLARE_KEY(SMS); 26 DECLARE_KEY(PHONE); 27 DECLARE_KEY(JOIN); 28 DECLARE_KEY(PW); 29 DECLARE_KEY(LOGIN); 30 DECLARE_KEY(ADD_FRIEND); 31 DECLARE_KEY(OPEN_SESSION); 32 DECLARE_KEY(TO); 33 DECLARE_KEY(CHAT); 34 DECLARE_KEY(FROM); 35 DECLARE_KEY(SESSION_ID); 36 DECLARE_KEY(MESSAGE); 37 DECLARE_KEY(SENSITIVE); 38 DECLARE_KEY(GET_FRIEND_LIST); 39 DECLARE_KEY(RESULT); 40 } 41 42 namespace Protocol 43 { 44 class Message 45 { 46 private: 47 json::Object mObject; 48 49 public: 50 void parse(const std::string & message); 51 52 template<typename T> 53 inline T get(const std::string & key) const 54 { 55 return (T)mObject[key]; 56 } 57 58 std::string type() const; 59 }; 60 61 class IProtocol 62 { 63 public: 64 virtual void makeTemplate(json::Object & obj, const std::string & type) const = 0; 65 }; 66 67 class Request : public IProtocol 68 { 69 private: 70 std::string mID; 71 72 public: 73 void setUserID(const std::string & id); 74 75 const std::string & getUserID(); 76 77 void makeTemplate(json::Object & obj, const std::string & type) const; 78 79 std::string sms(const std::string & phone) const; 80 81 std::string join(const std::string & id, const std::string & pw, const std::string & sms); 82 83 std::string login(const std::string & pw) const; 84 85 std::string addFriend(const std::string & id) const; 86 87 std::string openSession(const std::string & to) const; 88 89 std::string chat(const std::string & sessid, const std::string & message, const int sensitive) const; 90 91 std::string getFriendList() const; 92 }; 93 94 class Response : public IProtocol 95 { 96 public: 97 void makeTemplate(json::Object & obj, const std::string & type) const; 98 99 std::string result(const std::string & requestType, const bool status) const; 100 101 std::string friendList(const std::vector<SFriend> & friendList) const; 102 103 std::string openSession(const std::vector<std::string> & idList) const; 104 }; 105 }; 106 107 // -------------------------------------------------------------- 10 108 11 109 #define LOG(message) log(__FILE__,__func__,__LINE__,message) … … 30 128 << message << std::endl; 31 129 } 32 33 // --------------------------------------------------------------34 namespace Message35 {36 class Parser37 {38 private:39 json::Object mObject;40 41 public:42 void parse(const std::string & message);43 44 template<typename T>45 inline T get(const std::string & key) const46 {47 return (T)mObject[key];48 }49 50 std::string type() const;51 };52 53 class IMessage54 {55 public:56 virtual void makeTemplate(json::Object & obj, const std::string & type) const = 0;57 };58 59 class Request : public IMessage60 {61 private:62 std::string mID;63 64 public:65 void setUserID(const std::string & id);66 67 const std::string & getUserID();68 69 void makeTemplate(json::Object & obj, const std::string & type) const;70 71 std::string command(const std::string & cmd) const;72 73 std::string sms(const std::string & phone) const;74 75 std::string Request::join(const std::string & id, const std::string & pw, const std::string & sms);76 77 std::string login(const std::string & pw) const;78 79 std::string Request::chat(const std::string & to, const std::string & sessid, const std::string & message) const;80 81 std::string friendList() const;82 };83 84 class Response : public IMessage85 {86 public:87 typedef struct friendInfo88 {89 std::string id;90 std::string name;91 } friendInfo;92 93 public:94 void makeTemplate(json::Object & obj, const std::string & type) const;95 96 std::string result(const bool status) const;97 };98 }; -
trunk/msgclnt.cpp
r5 r6 10 10 { 11 11 cf::network::tcp * socket; 12 SCallback * callback;12 MessageQ * messageQ; 13 13 } SWorkerArg; 14 14 … … 17 17 SWorkerArg * inst = (SWorkerArg *) arg; 18 18 19 bool isError = false; 20 Message::Parser parser; 19 Protocol::Message parser; 21 20 cf::bin raw; 22 21 … … 27 26 raw = inst->socket->receive(); 28 27 parser.parse(raw.toString()); 29 30 isError = false;31 28 } 32 29 catch (cf::exception & e) … … 37 34 if (raw.size() == 0) 38 35 break; 39 40 isError = true; 41 } 42 43 if (parser.type() == "result") 44 { 45 SResultResponse recv; 46 47 recv.result = parser.get<bool>("result"); 48 recv.isError = isError; 49 50 inst->callback->result(recv); 51 } 52 else if (parser.type() == "chat") 53 { 54 SReceivedMessage recv; 55 56 recv.sessid = parser.get<std::string>("sess-id"); 57 recv.sender = parser.get<std::string>("from"); 58 recv.message = parser.get<std::string>("message"); 59 recv.isError = isError; 60 61 inst->callback->message(recv); 62 } 63 } 64 65 free(arg); 36 } 37 38 inst->messageQ->push(parser); 39 } 40 41 free(inst); 66 42 67 43 return 0; 44 } 45 46 // -------------------------------------------------------------- 47 48 void MessageQ::push(const Protocol::Message & parser) 49 { 50 SYNCHRONIZED(mutex) 51 { 52 messageQ.push_back(parser); 53 } 54 } 55 56 Protocol::Message MessageQ::pop(const std::string & requestType) 57 { 58 while (true) 59 { 60 SYNCHRONIZED(mutex) 61 { 62 Protocol::Message parser = messageQ.front(); 63 64 if (parser.type() == requestType) 65 { 66 messageQ.erase(messageQ.begin()); 67 68 return parser; 69 } 70 } 71 } 68 72 } 69 73 … … 75 79 } 76 80 81 chev::~chev() 82 { 83 socket.close(); 84 } 85 86 const std::string & chev::getLastError() const 87 { 88 return error; 89 } 90 77 91 bool chev::connect(const std::string & host, const unsigned short port) 78 92 { … … 81 95 socket.connect(host, port); 82 96 97 SWorkerArg * arg = (SWorkerArg *)malloc(sizeof(SWorkerArg)); 98 if (!arg) 99 return false; 100 101 arg->socket = &socket; 102 arg->messageQ = &messageQ; 103 104 listener.start(arg); 105 83 106 return true; 84 107 } … … 97 120 socket.send(request.join(id, pw, sms)); 98 121 99 std::string response = socket.receive().toString(); 100 Message::Parser parser; 101 parser.parse(response); 102 103 return parser.get<bool>("result"); 122 return messageQ.pop(ProtocolType::JOIN).get<bool>(ProtocolType::RESULT); 104 123 } 105 124 catch (cf::exception & e) … … 119 138 socket.send(request.login(pw)); 120 139 121 std::string response = socket.receive().toString(); 122 Message::Parser parser; 123 parser.parse(response); 124 125 return parser.get<bool>("result"); 140 return messageQ.pop(ProtocolType::LOGIN).get<bool>(ProtocolType::RESULT); 126 141 } 127 142 catch (cf::exception & e) … … 139 154 socket.send(request.sms(phone)); 140 155 141 std::string response = socket.receive().toString(); 142 Message::Parser parser; 143 parser.parse(response); 144 145 return parser.get<bool>("result"); 146 } 147 catch (cf::exception & e) 148 { 149 LOG(e.what()); 150 151 return false; 152 } 153 } 154 155 bool chev::runReceiver(const SCallback & cb) 156 { 157 if (listener.isRunning()) 158 return true; 159 160 callback = cb; 161 162 SWorkerArg * arg = (SWorkerArg *)malloc(sizeof(SWorkerArg)); 163 if (!arg) 164 return false; 165 166 arg->socket = &socket; 167 arg->callback = &callback; 168 169 listener.start(arg); 170 171 return true; 172 } 173 174 bool chev::sendMessage(const std::string & friendid, const std::string & sessid, const std::string & message) 175 { 176 try 177 { 178 socket.send(request.chat(friendid, sessid, message)); 179 180 std::string response = socket.receive().toString(); 181 Message::Parser parser; 182 parser.parse(response); 183 184 return parser.get<bool>("result"); 185 } 186 catch (cf::exception & e) 187 { 188 LOG(e.what()); 189 190 return false; 191 } 192 } 156 return messageQ.pop(ProtocolType::SMS).get<bool>(ProtocolType::RESULT); 157 } 158 catch (cf::exception & e) 159 { 160 LOG(e.what()); 161 162 return false; 163 } 164 } 165 166 bool chev::addFriend(const std::string & id) 167 { 168 try 169 { 170 socket.send(request.addFriend(id)); 171 172 return messageQ.pop(ProtocolType::ADD_FRIEND).get<bool>(ProtocolType::RESULT); 173 } 174 catch (cf::exception & e) 175 { 176 LOG(e.what()); 177 178 return false; 179 } 180 } 181 182 std::vector<SFriend> chev::getFriendList() 183 { 184 try 185 { 186 socket.send(request.getFriendList()); 187 } 188 catch (cf::exception & e) 189 { 190 LOG(e.what()); 191 } 192 return std::vector<SFriend>(); 193 } 194 195 std::string chev::getSessionID(const std::vector<std::string> & idList) 196 { 197 try 198 { 199 std::string concat = idList[0]; 200 201 for (int iter = 1 ; iter < idList.size() ; iter++) 202 concat += "," + idList[iter]; 203 204 if (sessionMap.find(concat) == sessionMap.end()) 205 { 206 socket.send(request.openSession(concat)); 207 208 std::string response = socket.receive().toString(); 209 Protocol::Message parser; 210 parser.parse(response); 211 212 if (!parser.get<bool>("result")) 213 THROW_EXCEPTION("failed to open session id"); 214 215 sessionMap[concat] = parser.get<std::string>("sess-id"); 216 } 217 218 return sessionMap[concat]; 219 } 220 catch (cf::exception & e) 221 { 222 LOG(e.what()); 223 224 return ""; 225 } 226 } 227 228 bool chev::tell(const SConversation & conversation) 229 { 230 try 231 { 232 const SConversation & c = conversation; 233 234 socket.send(request.chat(c.sessid, c.message, c.sensitive)); 235 236 return messageQ.pop(ProtocolType::CHAT).get<bool>(ProtocolType::RESULT); 237 } 238 catch (cf::exception & e) 239 { 240 LOG(e.what()); 241 242 return false; 243 } 244 } 245 246 SConversation chev::listen() 247 { 248 SConversation c; 249 Protocol::Message parser = messageQ.pop(ProtocolType::CHAT); 250 251 c.sessid = parser.get<std::string>(ProtocolType::SESSION_ID); 252 c.message = parser.get<std::string>(ProtocolType::MESSAGE); 253 c.sensitive = parser.get<int>(ProtocolType::SENSITIVE); 254 c.isError = parser.get<bool>(ProtocolType::RESULT); 255 256 c.from = parser.get<std::string>(ProtocolType::FROM); 257 258 return c; 259 } -
trunk/msgclnt.h
r5 r6 9 9 #include "cf/task.h" 10 10 11 typedef struct S Friend11 typedef struct SConversation 12 12 { 13 std::string id; 14 std::string name; 15 } SFriend; 13 // tell and listen 14 std::string sessid; 15 std::string message; 16 int sensitive; 17 bool isError; 16 18 17 // for callback 19 // only for listen 20 std::string from; 21 } SConversation; 18 22 19 typedef struct SResultResponse 23 class MessageQ 20 24 { 21 bool result; 22 bool isError;23 } SResultResponse;25 private: 26 cf::task::mutex mutex; 27 std::vector<Protocol::Message> messageQ; 24 28 25 typedef struct SReceivedMessage 26 { 27 std::string sessid; 28 std::string sender; 29 std::string message; 30 bool isError; 31 } SReceivedMessage; 29 public: 30 void push(const Protocol::Message & parser); 32 31 33 typedef int (* callback_onResultResponse)(SResultResponse &); 34 typedef int (* callback_onReceiveMessage)(SReceivedMessage &); 35 36 typedef struct SCallback 37 { 38 callback_onResultResponse result; 39 callback_onReceiveMessage message; 40 } SCallback; 32 Protocol::Message pop(const std::string & requestType); 33 }; 41 34 42 35 class chev 43 36 { 44 37 private: 45 Message::Request request;38 Protocol::Request request; 46 39 std::string error; 47 40 cf::network::tcp socket; 48 41 cf::task::thread listener; 49 SCallback callback; 42 43 MessageQ messageQ; 44 45 std::map<std::string, std::string> sessionMap; 50 46 51 47 public: 52 48 chev(); 49 50 ~chev(); 51 52 const std::string & getLastError() const; 53 53 54 54 bool connect(const std::string & host, unsigned short port); … … 64 64 std::vector<SFriend> getFriendList(); 65 65 66 bool sendMessage(const std::string & friendid, const std::string & sessionID, const std::string & message);66 std::string getSessionID(const std::vector<std::string> & idList); 67 67 68 // call once 69 bool runReceiver(const SCallback & cb); 68 bool tell(const SConversation & conversation); 70 69 71 const std::string & getLastError();70 SConversation listen(); 72 71 }; -
trunk/msgsrv.cpp
r4 r6 283 283 } 284 284 285 static bool command(const Message::Parser& parser)285 static bool command(const Protocol::Message & parser) 286 286 { 287 287 bool isContinued = true; … … 305 305 } 306 306 307 static std::string httpSMS(const Message::Parser& parser)307 static std::string httpSMS(const Protocol::Message & parser) 308 308 { 309 309 std::string phone = parser.get<std::string>("phone"); … … 319 319 CRLF; 320 320 321 Message::Response response;321 Protocol::Response response; 322 322 cf::network::tcp smsSock; 323 323 cf::network::host smsServer(url, 80); … … 330 330 } 331 331 332 static bool join(const Message::Parser& parser, const std::string & sms, const std::string & address)332 static bool join(const Protocol::Message & parser, const std::string & sms, const std::string & address) 333 333 throw (cf::exception) 334 334 { … … 342 342 } 343 343 344 static bool login(const Message::Parser& parser)344 static bool login(const Protocol::Message & parser) 345 345 throw (cf::exception) 346 346 { … … 351 351 } 352 352 353 static bool chat(const Message::Parser& parser,353 static bool chat(const Protocol::Message & parser, 354 354 const std::string & message) 355 355 { … … 381 381 while (true) 382 382 { 383 Message::Parserparser;383 Protocol::Message parser; 384 384 parser.parse(sock.receive().toString()); 385 385 … … 417 417 workerInitiator(*sock); 418 418 419 Message::Response response;419 Protocol::Response response; 420 420 bool result = true; 421 421 … … 423 423 { 424 424 std::string message = sock->receive().toString(); 425 Message::Parserparser;425 Protocol::Message parser; 426 426 parser.parse(message); 427 427 … … 433 433 result = chat(parser, message); 434 434 435 sock->send(response.result( result));435 sock->send(response.result(parser.type(), result)); 436 436 } 437 437 }
Note:
See TracChangeset
for help on using the changeset viewer.