CMS 3D CMS Logo

/data/refman/pasoursint/CMSSW_5_2_9/src/EventFilter/SMProxyServer/src/SMProxyServer.cc

Go to the documentation of this file.
00001 // $Id: SMProxyServer.cc,v 1.47 2011/08/22 14:21:00 mommsen Exp $
00003 
00004 #include "EventFilter/SMProxyServer/interface/Exception.h"
00005 #include "EventFilter/SMProxyServer/interface/SMProxyServer.h"
00006 #include "EventFilter/SMProxyServer/interface/StateMachine.h"
00007 #include "EventFilter/StorageManager/interface/SoapUtils.h"
00008 #include "EventFilter/StorageManager/src/ConsumerUtils.icc"
00009 
00010 #include "FWCore/Utilities/interface/EDMException.h"
00011 
00012 #include "xcept/tools.h"
00013 #include "xdaq/NamespaceURI.h"
00014 #include "xdata/InfoSpaceFactory.h"
00015 #include "xgi/Method.h"
00016 #include "xoap/Method.h"
00017 
00018 #include <cstdlib>
00019 
00020 using namespace std;
00021 using namespace smproxy;
00022 
00023 
00024 SMProxyServer::SMProxyServer(xdaq::ApplicationStub * s) :
00025   xdaq::Application(s)
00026 {  
00027   LOG4CPLUS_INFO(this->getApplicationLogger(),"Making SMProxyServer");
00028 
00029   // bind all callback functions
00030   bindStateMachineCallbacks();
00031   bindWebInterfaceCallbacks();
00032   bindConsumerCallbacks();
00033 
00034   std::string errorMsg = "Exception in SMProxyServer constructor: ";
00035   try
00036   {
00037     initializeSharedResources();
00038   }
00039   catch(std::exception &e)
00040   {
00041     errorMsg += e.what();
00042     LOG4CPLUS_FATAL( getApplicationLogger(), e.what() );
00043     XCEPT_RAISE( exception::Exception, e.what() );
00044   }
00045   catch(...)
00046   {
00047     errorMsg += "unknown exception";
00048     LOG4CPLUS_FATAL( getApplicationLogger(), errorMsg );
00049     XCEPT_RAISE( exception::Exception, errorMsg );
00050   }
00051 
00052   startWorkerThreads();
00053 }
00054 
00055 
00056 void SMProxyServer::bindStateMachineCallbacks()
00057 {
00058   xoap::bind( this,
00059               &SMProxyServer::handleFSMSoapMessage,
00060               "Configure",
00061               XDAQ_NS_URI );
00062   xoap::bind( this,
00063               &SMProxyServer::handleFSMSoapMessage,
00064               "Enable",
00065               XDAQ_NS_URI );
00066   xoap::bind( this,
00067               &SMProxyServer::handleFSMSoapMessage,
00068               "Stop",
00069               XDAQ_NS_URI );
00070   xoap::bind( this,
00071               &SMProxyServer::handleFSMSoapMessage,
00072               "Halt",
00073               XDAQ_NS_URI );
00074 }
00075 
00076 
00077 void SMProxyServer::bindWebInterfaceCallbacks()
00078 {
00079   xgi::bind(this,&SMProxyServer::css,                      "styles.css");
00080   xgi::bind(this,&SMProxyServer::defaultWebPage,           "Default");
00081   xgi::bind(this,&SMProxyServer::dataRetrieverWebPage,     "dataRetriever");
00082   xgi::bind(this,&SMProxyServer::dqmEventStatisticsWebPage,"dqmEventStatistics");
00083   xgi::bind(this,&SMProxyServer::consumerStatisticsWebPage,"consumerStatistics" );
00084 }
00085 
00086 
00087 void SMProxyServer::bindConsumerCallbacks()
00088 {
00089   // event consumers
00090   xgi::bind( this, &SMProxyServer::processConsumerRegistrationRequest, "registerConsumer" );
00091   xgi::bind( this, &SMProxyServer::processConsumerHeaderRequest, "getregdata" );
00092   xgi::bind( this, &SMProxyServer::processConsumerEventRequest, "geteventdata" );
00093 
00094   // dqm event consumers
00095   xgi::bind(this,&SMProxyServer::processDQMConsumerRegistrationRequest, "registerDQMConsumer");
00096   xgi::bind(this,&SMProxyServer::processDQMConsumerEventRequest, "getDQMeventdata");
00097 }
00098 
00099 
00100 void SMProxyServer::initializeSharedResources()
00101 {
00102   stateMachine_.reset( new StateMachine(this) );
00103   
00104   consumerUtils_.reset( new ConsumerUtils_t (
00105       stateMachine_->getConfiguration(),
00106       stateMachine_->getRegistrationCollection(),
00107       stateMachine_->getRegistrationQueue(),
00108       stateMachine_->getInitMsgCollection(),
00109       stateMachine_->getEventQueueCollection(),
00110       stateMachine_->getDQMEventQueueCollection(),
00111       stateMachine_->getStatisticsReporter()->alarmHandler()
00112     ) );
00113 
00114   smpsWebPageHelper_.reset( new SMPSWebPageHelper(
00115       getApplicationDescriptor(), stateMachine_));
00116 }
00117 
00118 
00119 void SMProxyServer::startWorkerThreads()
00120 {
00121   // Start the workloops
00122   try
00123   {
00124     stateMachine_->getStatisticsReporter()->startWorkLoop("theStatisticsReporter");
00125   }
00126   catch(xcept::Exception &e)
00127   {
00128     stateMachine_->moveToFailedState(e);
00129   }
00130   catch(std::exception &e)
00131   {
00132     XCEPT_DECLARE(exception::Exception,
00133       sentinelException, e.what());
00134     stateMachine_->moveToFailedState(sentinelException);
00135   }
00136   catch(...)
00137   {
00138     std::string errorMsg = "Unknown exception when starting the workloops";
00139     XCEPT_DECLARE(exception::Exception,
00140       sentinelException, errorMsg);
00141     stateMachine_->moveToFailedState(sentinelException);
00142   }
00143 }
00144 
00145 
00147 // Web interface call back functions //
00149 
00150 void SMProxyServer::css(xgi::Input *in, xgi::Output *out)
00151 throw (xgi::exception::Exception)
00152 {
00153   smpsWebPageHelper_->css(in,out);
00154 }
00155 
00156 
00157 void SMProxyServer::defaultWebPage(xgi::Input *in, xgi::Output *out)
00158 throw (xgi::exception::Exception)
00159 {
00160   std::string errorMsg = "Failed to create the default webpage";
00161   
00162   try
00163   {
00164     smpsWebPageHelper_->defaultWebPage(out);
00165   }
00166   catch(std::exception &e)
00167   {
00168     errorMsg += ": ";
00169     errorMsg += e.what();
00170     
00171     LOG4CPLUS_ERROR(getApplicationLogger(), errorMsg);
00172     XCEPT_RAISE(xgi::exception::Exception, errorMsg);
00173   }
00174   catch(...)
00175   {
00176     errorMsg += ": Unknown exception";
00177     
00178     LOG4CPLUS_ERROR(getApplicationLogger(), errorMsg);
00179     XCEPT_RAISE(xgi::exception::Exception, errorMsg);
00180   }
00181 }
00182 
00183 
00184 void SMProxyServer::dataRetrieverWebPage(xgi::Input* in, xgi::Output* out)
00185 throw( xgi::exception::Exception )
00186 {
00187 
00188   std::string err_msg =
00189     "Failed to create data retriever web page";
00190 
00191   try
00192   {
00193     smpsWebPageHelper_->dataRetrieverWebPage(out);
00194   }
00195   catch( std::exception &e )
00196   {
00197     err_msg += ": ";
00198     err_msg += e.what();
00199     LOG4CPLUS_ERROR( getApplicationLogger(), err_msg );
00200     XCEPT_RAISE( xgi::exception::Exception, err_msg );
00201   }
00202   catch(...)
00203   {
00204     err_msg += ": Unknown exception";
00205     LOG4CPLUS_ERROR( getApplicationLogger(), err_msg );
00206     XCEPT_RAISE( xgi::exception::Exception, err_msg );
00207   }
00208 }
00209 
00210 
00211 void SMProxyServer::consumerStatisticsWebPage(xgi::Input* in, xgi::Output* out)
00212 throw( xgi::exception::Exception )
00213 {
00214 
00215   std::string err_msg =
00216     "Failed to create consumer web page";
00217 
00218   try
00219   {
00220     smpsWebPageHelper_->consumerStatisticsWebPage(out);
00221   }
00222   catch( std::exception &e )
00223   {
00224     err_msg += ": ";
00225     err_msg += e.what();
00226     LOG4CPLUS_ERROR( getApplicationLogger(), err_msg );
00227     XCEPT_RAISE( xgi::exception::Exception, err_msg );
00228   }
00229   catch(...)
00230   {
00231     err_msg += ": Unknown exception";
00232     LOG4CPLUS_ERROR( getApplicationLogger(), err_msg );
00233     XCEPT_RAISE( xgi::exception::Exception, err_msg );
00234   }
00235 }
00236 
00237 
00238 void SMProxyServer::dqmEventStatisticsWebPage(xgi::Input *in, xgi::Output *out)
00239 throw (xgi::exception::Exception)
00240 {
00241   std::string errorMsg = "Failed to create the DQM event statistics webpage";
00242 
00243   try
00244   {
00245     smpsWebPageHelper_->dqmEventStatisticsWebPage(out);
00246   }
00247   catch(std::exception &e)
00248   {
00249     errorMsg += ": ";
00250     errorMsg += e.what();
00251     
00252     LOG4CPLUS_ERROR(getApplicationLogger(), errorMsg);
00253     XCEPT_RAISE(xgi::exception::Exception, errorMsg);
00254   }
00255   catch(...)
00256   {
00257     errorMsg += ": Unknown exception";
00258     
00259     LOG4CPLUS_ERROR(getApplicationLogger(), errorMsg);
00260     XCEPT_RAISE(xgi::exception::Exception, errorMsg);
00261   }
00262 }
00263 
00264 
00266 // State Machine call back functions //
00268 
00269 xoap::MessageReference SMProxyServer::handleFSMSoapMessage( xoap::MessageReference msg )
00270   throw( xoap::exception::Exception )
00271 {
00272   std::string errorMsg;
00273   xoap::MessageReference returnMsg;
00274 
00275   try {
00276     errorMsg = "Failed to extract FSM event and parameters from SOAP message: ";
00277     std::string command = stor::soaputils::extractParameters(msg, this);
00278     std::string newState = "unknown";  
00279 
00280     errorMsg = "Failed to process '" + command + "' state machine event: ";
00281     if (command == "Configure")
00282     {
00283       newState = stateMachine_->processEvent( Configure() );
00284     }
00285     else if (command == "Enable")
00286     {
00287       newState = stateMachine_->processEvent( Enable() );
00288     }
00289     else if (command == "Stop")
00290     {
00291       newState = stateMachine_->processEvent( Stop() );
00292     }
00293     else if (command == "Halt")
00294     {
00295       newState = stateMachine_->processEvent( Halt() );
00296     }
00297     else
00298     {
00299       XCEPT_RAISE(exception::StateMachine,
00300         "Received an unknown state machine event '" + command + "'.");
00301     }
00302 
00303     errorMsg = "Failed to create FSM SOAP reply message: ";
00304     returnMsg = stor::soaputils::createFsmSoapResponseMsg(command, newState);
00305   }
00306   catch (cms::Exception& e) {
00307     errorMsg += e.explainSelf();
00308     XCEPT_DECLARE(xoap::exception::Exception,
00309       sentinelException, errorMsg);
00310     stateMachine_->moveToFailedState(sentinelException);
00311   }
00312   catch (xcept::Exception &e) {
00313     XCEPT_DECLARE_NESTED(xoap::exception::Exception,
00314       sentinelException, errorMsg, e);
00315     stateMachine_->moveToFailedState(sentinelException);
00316   }
00317   catch (std::exception& e) {
00318     errorMsg += e.what();
00319     XCEPT_DECLARE(xoap::exception::Exception,
00320       sentinelException, errorMsg);
00321     stateMachine_->moveToFailedState(sentinelException);
00322   }
00323   catch (...) {
00324     errorMsg += "Unknown exception";
00325     XCEPT_DECLARE(xoap::exception::Exception,
00326       sentinelException, errorMsg);
00327     stateMachine_->moveToFailedState(sentinelException);
00328   }
00329 
00330   return returnMsg;
00331 }
00332 
00333 
00337 
00338 void
00339 SMProxyServer::processConsumerRegistrationRequest( xgi::Input* in, xgi::Output* out )
00340   throw( xgi::exception::Exception )
00341 {
00342   consumerUtils_->processConsumerRegistrationRequest(in,out);
00343 }
00344 
00345 
00346 void
00347 SMProxyServer::processConsumerHeaderRequest( xgi::Input* in, xgi::Output* out )
00348   throw( xgi::exception::Exception )
00349 {
00350   consumerUtils_->processConsumerHeaderRequest(in,out);
00351 }
00352 
00353 
00354 void
00355 SMProxyServer::processConsumerEventRequest( xgi::Input* in, xgi::Output* out )
00356   throw( xgi::exception::Exception )
00357 {
00358   consumerUtils_->processConsumerEventRequest(in,out);
00359 }
00360 
00361 
00362 void
00363 SMProxyServer::processDQMConsumerRegistrationRequest( xgi::Input* in, xgi::Output* out )
00364   throw( xgi::exception::Exception )
00365 {
00366   consumerUtils_->processDQMConsumerRegistrationRequest(in,out);
00367 }
00368 
00369 
00370 void
00371 SMProxyServer::processDQMConsumerEventRequest( xgi::Input* in, xgi::Output* out )
00372   throw( xgi::exception::Exception )
00373 {
00374   consumerUtils_->processDQMConsumerEventRequest(in,out);
00375 }
00376 
00377 namespace stor {
00379   // Specialization for ConsumerUtils //
00381   template<>
00382   void
00383   ConsumerUtils<smproxy::Configuration,smproxy::EventQueueCollection>::
00384   writeConsumerEvent(xgi::Output* out, const smproxy::EventMsg& evt) const
00385   {
00386     writeHTTPHeaders( out );
00387     out->write( (char*)evt.dataLocation(), evt.totalDataSize() );
00388   }
00389 }
00390 
00391 
00393 // *** Provides factory method for the instantiation of SM applications //
00395 // This macro is depreciated:
00396 XDAQ_INSTANTIATE(SMProxyServer)
00397 
00398 // One should use the XDAQ_INSTANTIATOR() in the header file
00399 // and this one here. But this breaks the backward compatibility,
00400 // as all xml configuration files would have to be changed to use
00401 // 'stor::SMProxyServer' instead of 'SMProxyServer'.
00402 // XDAQ_INSTANTIATOR_IMPL(stor::SMProxyServer)
00403 
00404 
00405 
00406 
00407 
00408 
00409 
00410