demo/c++/MultiConnectDemo.cpp

Go to the documentation of this file.
00001 /*------------------------------------------------------------------------------
00002 Name:      xmlBlaster/demo/c++/MultiConnectDemo.cpp
00003 Project:   xmlBlaster.org
00004 Comment:   C++ client example
00005 Author:    Marcel Ruff
00006 ------------------------------------------------------------------------------*/
00007 #include <client/XmlBlasterAccess.h>
00008 #include <util/Global.h>
00009 #include <vector>
00010 
00011 using namespace std;
00012 using namespace org::xmlBlaster::util;
00013 using namespace org::xmlBlaster::util::qos;
00014 using namespace org::xmlBlaster::util::dispatch;
00015 using namespace org::xmlBlaster::client;
00016 using namespace org::xmlBlaster::client::qos;
00017 using namespace org::xmlBlaster::client::key;
00018 
00027 class SpecificCallback : public I_Callback, public I_ConnectionProblems
00028 {
00029  private:
00030    const string ME;
00031    I_Log& log_;
00032  public:
00033    SpecificCallback(const GlobalRef global) : ME(global->getInstanceName()),
00034                                               log_(global->getLog("MultiConnectDemo"))
00035    {}
00036 
00040    string update(const string& sessionId, UpdateKey& updateKey,
00041                  const unsigned char* content,
00042                  long contentSize, UpdateQos& updateQos)
00043    {
00044       string contentStr(reinterpret_cast<char *>(const_cast<unsigned char *>(content)), contentSize);
00045       log_.info(ME, "Received update message with secret sessionId '" + sessionId + "':" +
00046                     updateKey.toXml() +
00047                     "\n content=" + contentStr +
00048                     updateQos.toXml());
00049       return "";
00050    }
00051 
00052    bool reachedAlive(StatesEnum /*oldState*/, I_ConnectionsHandler* /*connectionsHandler*/)
00053    {
00054       log_.info(ME, "reconnected");
00055       return true;
00056    }
00057 
00058    void reachedDead(StatesEnum /*oldState*/, I_ConnectionsHandler* /*connectionsHandler*/)
00059    {
00060       log_.info(ME, "lost connection");
00061    }
00062 
00063    void reachedPolling(StatesEnum /*oldState*/, I_ConnectionsHandler* /*connectionsHandler*/)
00064    {
00065       log_.info(ME, "going to poll modus");
00066    }
00067 };
00068 
00069 
00082 class MultiConnectDemo
00083 {
00084 private:
00085    string  ME;      
00086    Global& global_; 
00087    I_Log& log_;     
00089 public:
00090    MultiConnectDemo(Global& glob) : ME("MultiConnectDemo"), global_(glob), 
00091                                     log_(glob.getLog("MultiConnectDemo")) {}
00092 
00093    virtual ~MultiConnectDemo() {}
00094 
00095    void execute()
00096    {
00097       const int NUM_CONN = global_.getProperty().get("numConn", 10);
00098       long sleepMillis = global_.getProperty().get("sleep", 1000L);
00099       try {
00100          vector<XmlBlasterAccessRef> connVec; // Holding all connections to xmlBlaster
00101          // Connect 5 times to xmlBlaster
00102          for (int i=0; i<NUM_CONN; i++) {
00103             string instanceName = string("connection-") + lexical_cast<std::string>(i);
00104             Property::MapType propMap;
00105             propMap["session.name"] = instanceName; // Set a unique login name
00106             GlobalRef globalRef = Global::getInstance().createInstance(instanceName, &propMap);
00107             connVec.push_back(XmlBlasterAccessRef(new XmlBlasterAccess(globalRef)));
00108 
00109             SpecificCallback* cbP = new SpecificCallback(globalRef);
00110             //connVec[i]->initFailsafe(cbP);
00111             ConnectQos qos(*globalRef);
00112             ConnectReturnQos retQos = connVec[i]->connect(qos, cbP);
00113             log_.info(ME, "Successfully connected to xmlBlaster as " +
00114                       retQos.getSessionQos().getSessionName()->getAbsoluteName());
00115          }
00116 
00117          // Subscribe 5 times
00118          for (int i=0; i<NUM_CONN; i++) {
00119             SubscribeKey subKey(connVec[i]->getGlobal());
00120             subKey.setOid("MultiConnectDemo");
00121             SubscribeQos subQos(connVec[i]->getGlobal());
00122             log_.info(ME, "Subscribing to xmlBlaster"); // + subKey.toXml() +
00123             SubscribeReturnQos subRetQos = connVec[i]->subscribe(subKey, subQos);
00124             log_.info(ME, "Successfully subscribed to xmlBlaster: " + subRetQos.getSubscriptionId());
00125          }
00126 
00127          // Publish a message with the oid 'MultiConnectDemo'
00128          // all subscribers should receive it
00129          PublishQos publishQos(connVec[0]->getGlobal());
00130          PublishKey publishKey(connVec[0]->getGlobal());
00131          publishKey.setOid("MultiConnectDemo");
00132          MessageUnit msgUnit(publishKey, string("Hi"), publishQos);
00133          log_.info(ME, "Publishing to xmlBlaster");
00134          PublishReturnQos pubRetQos = connVec[0]->publish(msgUnit);
00135          log_.info(ME, "Successfully published to xmlBlaster: " + pubRetQos.getKeyOid());
00136          try {
00137             log_.info(ME, "Sleeping now for " + lexical_cast<string>(sleepMillis) + " msec ...");
00138             org::xmlBlaster::util::thread::Thread::sleep(sleepMillis);
00139          }
00140          catch(const XmlBlasterException &e) {
00141             log_.error(ME, e.toXml());
00142          }
00143 
00144          // Erase the topic
00145          EraseKey eraseKey(connVec[0]->getGlobal());
00146          eraseKey.setOid("MultiConnectDemo");
00147          EraseQos eraseQos(connVec[0]->getGlobal());
00148          log_.info(ME, "Erasing the published message");
00149          connVec[0]->erase(eraseKey, eraseQos);
00150 
00151          // Disconnect all clients
00152          for (int i=0; i<NUM_CONN; i++) {
00153             connVec[i]->disconnect(DisconnectQos(connVec[i]->getGlobal()));
00154             delete connVec[i]->getCallback();
00155          }
00156 
00157          connVec.clear();
00158          log_.info(ME, "Done, resources are released");
00159       }
00160       catch (const XmlBlasterException &e) {
00161          log_.error(ME, e.toXml());
00162       }
00163    }
00164 };
00165 
00166 #include <iostream>
00167 
00175 int main(int args, char ** argv)
00176 {
00177    try {
00178       org::xmlBlaster::util::Object_Lifetime_Manager::init();
00179       Global& glob = Global::getInstance();
00180       glob.initialize(args, argv);
00181       
00182       string intro = "XmlBlaster C++ client " + glob.getReleaseId() +
00183                      ", try option '-help' if you need usage informations.";
00184       glob.getLog().info("MultiConnectDemo", intro);
00185 
00186       if (glob.wantsHelp()) {
00187          cout << Global::usage() << endl;
00188          cout << endl << "MultiConnectDemo";
00189          cout << endl << "   -sleep              Sleep after publishing [1000 millisec]" << endl;
00190          cout << endl << "Example:" << endl;
00191          cout << endl << "MultiConnectDemo -trace true -sleep 2000";
00192          cout << endl << "MultiConnectDemo -dispatch/connection/delay 10000 -sleep 2000000" << endl << endl;
00193          org::xmlBlaster::util::Object_Lifetime_Manager::fini();
00194          return 1;
00195       }
00196 
00197       MultiConnectDemo hello(glob);
00198       hello.execute();
00199    }
00200    catch (XmlBlasterException &e) {
00201       std::cerr << "Caught exception: " << e.getMessage() << std::endl;
00202    }
00203    catch (...) {
00204       std::cerr << "Caught exception, exit" << std::endl;
00205    }
00206    org::xmlBlaster::util::Object_Lifetime_Manager::fini();
00207    return 0;
00208 }