CMS 3D CMS Logo

CMSSW_4_4_3_patch1/src/CondCore/ORA/src/Monitoring.cc

Go to the documentation of this file.
00001 #include "CondCore/ORA/interface/Monitoring.h"
00002 // externals
00003 #include "uuid/uuid.h"
00004 //
00005 #include <string.h>
00006 #include <cstdlib>
00007 #include <fstream>
00008 
00009 namespace ora {
00010   static char const* fmt_Guid = 
00011     "%08lX-%04hX-%04hX-%02hhX%02hhX-%02hhX%02hhX%02hhX%02hhX%02hhX%02hhX";  
00012 
00013   std::string guidFromTime(){
00014     uuid_t me_;
00015     ::uuid_generate_time(me_);
00016     unsigned int*  tmp = reinterpret_cast<unsigned int*>(me_);
00017     unsigned int d1 = *tmp;
00018     unsigned short d2 = *reinterpret_cast<unsigned short*>(me_+4);
00019     unsigned short d3 = *reinterpret_cast<unsigned short*>(me_+6);
00020     unsigned char  d4[8];
00021     for (int i = 0; i < 8; ++i){
00022       d4[i]=me_[i+8];
00023     }
00024     
00025     char text[128];
00026     ::sprintf(text, fmt_Guid,
00027               d1, d2, d3, 
00028               d4[0], d4[1], d4[2], d4[3], 
00029               d4[4], d4[5], d4[6], d4[7]);
00030     return std::string(text);
00031   }
00032 }
00033 
00034 ora::TransactionMonitoringData::TransactionMonitoringData( boost::posix_time::ptime start ):
00035   m_start(start),
00036   m_stop(boost::posix_time::neg_infin),
00037   m_status(false){
00038 }
00039 
00040 void ora::TransactionMonitoringData::stop(bool commit_status){
00041   m_stop = boost::posix_time::microsec_clock::universal_time();
00042   m_status = commit_status;
00043 }
00044 
00045 ora::SessionMonitoringData::SessionMonitoringData( boost::posix_time::ptime start, const std::string& connectionString ):
00046   m_connectionString( connectionString ),
00047   m_start(start),
00048   m_stop(boost::posix_time::neg_infin),
00049   m_currentTransaction(0),
00050   m_transactions(),
00051   m_ncur(0){
00052 }
00053 
00054 ora::SessionMonitoringData::~SessionMonitoringData(){
00055   for(std::map<std::string,TransactionMonitoringData*>::const_iterator iT = m_transactions.begin();
00056       iT != m_transactions.end();iT++ ){
00057     delete iT->second;
00058   }
00059 }
00060 
00061 size_t ora::SessionMonitoringData::newTransaction(){
00062   m_currentTransaction = new TransactionMonitoringData( boost::posix_time::microsec_clock::universal_time() );
00063   m_transactions.insert(std::make_pair(guidFromTime(),m_currentTransaction));
00064   m_ncur = m_transactions.size();
00065   return m_ncur;
00066 }
00067 
00068 size_t ora::SessionMonitoringData::stopTransaction( bool commit_status ){
00069   size_t ncur = 0;
00070   if(m_currentTransaction){
00071     m_currentTransaction->stop( commit_status );
00072     m_currentTransaction = 0;
00073     ncur = m_ncur;
00074     m_ncur = 0;
00075   }
00076   return ncur;
00077 }
00078 
00079 void ora::SessionMonitoringData::stop(){
00080   m_stop = boost::posix_time::microsec_clock::universal_time();
00081   m_currentTransaction = 0;
00082   m_ncur = 0;
00083 }
00084 
00085 size_t ora::SessionMonitoringData::numberOfTransactions() const{
00086   return m_transactions.size();
00087 }
00088 
00089 void ora::SessionMonitoringData::report( std::ostream& out ) const {
00090   size_t i=1;
00091   for(std::map<std::string,TransactionMonitoringData*>::const_iterator iT = m_transactions.begin();
00092       iT != m_transactions.end();iT++ ){
00093     TransactionMonitoringData& data = *iT->second;
00094     boost::posix_time::time_duration duration;
00095     if( !data.m_stop.is_neg_infinity() ){
00096       duration = data.m_stop-data.m_start;
00097     }
00098     out <<"   -> Transaction #"<<i<<" duration="<<boost::posix_time::to_simple_string(duration)<<" status="<<(data.m_status?std::string("COMMIT"):std::string("ROLLBACK"))<<std::endl;
00099     i++;
00100   }  
00101 }
00102 
00103 bool ora::Monitoring::s_enabled = false;
00104 
00105 ora::Monitoring& ora::Monitoring::get(){
00106   static ora::Monitoring s_mon;
00107   return s_mon;
00108 }
00109 
00110 bool ora::Monitoring::isEnabled(){
00111   if(! s_enabled ){
00112     const char* envVar = ::getenv( "ORA_MONITORING_LEVEL" );
00113     if( envVar && ::strcmp(envVar,"SESSION")==0 ) s_enabled = true;
00114   }
00115   return s_enabled;
00116 }
00117 
00118 void ora::Monitoring::enable(){
00119   s_enabled = true;
00120 }
00121 
00122 std::string& ora::Monitoring::outFileName(){
00123   static std::string s_outFileName("");
00124   if( s_outFileName.empty() ){
00125     const char* fileEnvVar = ::getenv( "ORA_MONITORING_FILE" );
00126     if( fileEnvVar ){
00127       s_outFileName = fileEnvVar;
00128     }
00129   }
00130   return s_outFileName;
00131 }
00132 
00133 ora::Monitoring::~Monitoring() throw(){
00134   if( isEnabled() ){
00135     try {
00136       if( !outFileName().empty() ){
00137         std::ofstream outFile;
00138         outFile.open(  outFileName().c_str() );
00139         if(outFile.good()){
00140           report( outFile );
00141           outFile.flush();
00142         }
00143         outFile.close();
00144         
00145       } else {
00146         report( std::cout );
00147       }
00148     } catch ( const std::exception& e ){
00149       std::cout <<"ORA_MONITORING Error: "<<e.what()<<std::endl;
00150     }
00151   }
00152   // clean up memory
00153   for(std::map<std::string,SessionMonitoringData*>::const_iterator iS = m_sessions.begin();
00154       iS != m_sessions.end();iS++ ){
00155     delete iS->second;
00156   }
00157 }
00158 
00159 ora::SessionMonitoringData* ora::Monitoring::startSession( const std::string& connectionString ){
00160   ora::SessionMonitoringData* ret = new SessionMonitoringData( boost::posix_time::microsec_clock::universal_time(), connectionString );
00161   m_sessions.insert(std::make_pair(guidFromTime(),ret));
00162   return ret;
00163 }
00164 
00165 void ora::Monitoring::report( std::ostream& out ){
00166   out << "### ---------------------------------------------------------------------- "<<std::endl;
00167   out << "### ORA Monitoring Summary "<<std::endl;
00168   out << "### "<<m_sessions.size()<<" session(s) registered."<<std::endl;
00169   size_t j = 1;
00170   for( std::map<std::string,SessionMonitoringData*>::const_iterator iS = m_sessions.begin();
00171        iS != m_sessions.end(); ++iS ){
00172     SessionMonitoringData& data = *iS->second;
00173     boost::posix_time::time_duration duration;
00174     if( !data.m_stop.is_neg_infinity() ){
00175       duration = data.m_stop-data.m_start;
00176     }
00177     out <<" -> Session #"<<j<<": connection=\""<<data.m_connectionString<<"\" duration="<<boost::posix_time::to_simple_string(duration)<<" transactions="<<(iS->second)->numberOfTransactions()<<std::endl;
00178     (iS->second)->report(out);
00179     j++;
00180   }
00181   out << "### ---------------------------------------------------------------------- "<<std::endl;
00182 
00183 }
00184  
00185 ora::Monitoring::Monitoring():
00186   m_sessions(){
00187 }