Module: sems Branch: master Commit: 96b1e816e4ccf9f588f790525f331245c0653a3c URL: http://git.sip-router.org/cgi-bin/gitweb.cgi/sems/?a=commit;h=96b1e816e4ccf9f588f790525f331245c0653a3c
Author: Raphael Coeffic <[email protected]> Committer: Raphael Coeffic <[email protected]> Date: Mon Sep 27 17:29:59 2010 +0200 adds MWI support through PUBLISH The mwi plug-in uses the event notification from the msg_storage plug-in and sends PUBLISH requests to a presence server. Thanks to Anton Zagorskiy for this contribution. --- apps/mwi/CMakeLists.txt | 7 +++ apps/mwi/Makefile | 7 +++ apps/mwi/etc/mwi.conf | 2 + apps/mwi/mwi.cpp | 126 +++++++++++++++++++++++++++++++++++++++++++++++ apps/mwi/mwi.h | 41 +++++++++++++++ 5 files changed, 183 insertions(+), 0 deletions(-) diff --git a/apps/mwi/CMakeLists.txt b/apps/mwi/CMakeLists.txt new file mode 100644 index 0000000..80dd6a2 --- /dev/null +++ b/apps/mwi/CMakeLists.txt @@ -0,0 +1,7 @@ +set (mwi_SRCS +mwi.cpp +) + +SET(sems_module_name mwi) +INCLUDE(${CMAKE_SOURCE_DIR}/cmake/module.rules.txt) +INCLUDE(${CMAKE_SOURCE_DIR}/cmake/config.rules.txt) diff --git a/apps/mwi/Makefile b/apps/mwi/Makefile new file mode 100644 index 0000000..cec8b8d --- /dev/null +++ b/apps/mwi/Makefile @@ -0,0 +1,7 @@ +plug_in_name = mwi + +module_ldflags = +module_cflags = -DMOD_NAME=\"$(plug_in_name)\" + +COREPATH ?=../../core +include $(COREPATH)/plug-in/Makefile.app_module diff --git a/apps/mwi/etc/mwi.conf b/apps/mwi/etc/mwi.conf new file mode 100644 index 0000000..13fcce6 --- /dev/null +++ b/apps/mwi/etc/mwi.conf @@ -0,0 +1,2 @@ +# Presence Server: +presence_server=127.0.0.1 \ No newline at end of file diff --git a/apps/mwi/mwi.cpp b/apps/mwi/mwi.cpp new file mode 100644 index 0000000..8597234 --- /dev/null +++ b/apps/mwi/mwi.cpp @@ -0,0 +1,126 @@ +/* + Copyright (C) Anton Zagorskiy [email protected] + Oyster-Telecom Laboratory + + Published under BSD License +*/ + +#include "AmPlugIn.h" +#include "AmSession.h" +#include "AmConfigReader.h" +#include "AmUtils.h" +#include "log.h" +#include "mwi.h" +#include <string> + +MWI* MWI::_instance = 0; +AmDynInvoke* MWI::MessageStorage = 0; + +EXPORT_PLUGIN_CLASS_FACTORY(MWI, MOD_NAME); + +MWI::MWI(const string& name) + : AmDynInvokeFactory(name) { + _instance = this; +}; + +MWI::~MWI() { }; + + +int MWI::onLoad() +{ + AmDynInvokeFactory* ms_fact = + AmPlugIn::instance()->getFactory4Di("msg_storage"); + + if(!ms_fact || !(MessageStorage = ms_fact->getInstance())) { + ERROR("could not load msg_storage. Load a msg_storage implementation module.\n"); + return -1; + }; + + // register the publish method as event sink for msg_storage events + AmArg es_args,ret; + es_args.push(this); + es_args.push("publish"); + MessageStorage->invoke("events_subscribe",es_args,ret); + + AmConfigReader cfg; + if(cfg.loadFile(AmConfig::ModConfigPath + "mwi.conf")) { + ERROR("can not load configuration file\n"); + return -1; + }; + + presence_server = cfg.getParameter("presence_server"); + if (presence_server.length()) + DBG("set presence server '%s'\n", presence_server.c_str()); + else { + ERROR("parameter 'presence_server' did not found in the configuration file\n"); + return -1; + } + + DBG("MWI module loaded.\n"); + return 0; +}; + + +void MWI::publish(const string& user, const string& domain) +{ + int new_msgs = 0; + int all_msgs = 0; + string headers, body; + + AmArg di_args, ret; + di_args.push(domain.c_str()); + di_args.push(user.c_str()); + + MessageStorage->invoke("userdir_open",di_args,ret); + + if (!ret.size() || !isArgInt(ret.get(0))) { + ERROR("userdir_open for user '%s' domain '%s' returned no (valid) result.\n", user.c_str(), domain.c_str()); + return; + }; + + all_msgs = ret.get(1).size(); + for (size_t i = 0; i < ret.get(1).size(); i++) { + AmArg& elem = ret.get(1).get(i); + + if (elem.get(2).asInt()) // skip empty messages + new_msgs += elem.get(1).asInt(); + else + all_msgs--; + }; + + DBG("Found %d new and %d old messages\n", new_msgs, all_msgs - new_msgs); + string vm_buf = int2str(new_msgs) + "/" + int2str(all_msgs - new_msgs); + + headers = "Event: message-summary\r\n"; + headers += "Subscription-State: active\r\n"; + + if (new_msgs > 0) + body = "Messages-Waiting: yes\r\n"; + else + body = "Messages-Waiting: no\r\n"; + + body += "Message-Account: sip:" + user + "@" + domain + "\r\n"; + body += "Voice-Message: " + vm_buf + " (" + vm_buf + ")\r\n"; + + AmSipDialog tmp_d(NULL); + tmp_d.local_party = string("<sip:mwi-publisher@") + presence_server + ">"; + tmp_d.remote_party = domain.c_str(); + tmp_d.route = "sip:" + presence_server; + tmp_d.remote_uri = "sip:" + user + "@" + domain; + tmp_d.callid = AmSession::getNewId() + "@" + presence_server; + tmp_d.local_tag = AmSession::getNewId(); + tmp_d.sendRequest("PUBLISH", "application/simple-message-summary", body, headers); +}; + +void MWI::invoke(const string& method, const AmArg& args, AmArg& ret) +{ + if (method == "publish") { + string user, domain; + user = args.get(1).asCStr(); + domain = args.get(0).asCStr(); + publish(user, domain); + ret.push(0); + } + else + throw AmDynInvoke::NotImplemented(method); +}; diff --git a/apps/mwi/mwi.h b/apps/mwi/mwi.h new file mode 100644 index 0000000..c1d7f1d --- /dev/null +++ b/apps/mwi/mwi.h @@ -0,0 +1,41 @@ +/* + Copyright (C) Anton Zagorskiy [email protected] + Oyster-Telecom Laboratory + + Published under BSD License +*/ + +#ifndef _MWI_H +#define _MWI_H + +#include "AmApi.h" +#include <string> + +class MWI : public AmDynInvokeFactory, public AmDynInvoke +{ +private: + static MWI* _instance; + static AmDynInvoke* MessageStorage; + + string presence_server; + + typedef struct + { + unsigned int new_msgs; + unsigned int saved_msgs; + } msg_info_struct; + + void getMsgInfo (const string& name, const string& domain, msg_info_struct& msg_info); + void publish (const string& name, const string& domain); + +public: + MWI(const string& name); + ~MWI(); + + AmDynInvoke* getInstance(){ return _instance; } + + int onLoad(); + void invoke(const string& method, const AmArg& args, AmArg& ret); +}; + +#endif _______________________________________________ Semsdev mailing list [email protected] http://lists.iptel.org/mailman/listinfo/semsdev
