| Classes | Job Modules | Data Objects | Services | Algorithms | Tools | Packages | Directories | Tracs |

In This Package:

StatsServerAlg.cc

Go to the documentation of this file.
00001 #include "StatsServerAlg.h"
00002 
00003 #include "StatisticsSvc/IStatisticsSvc.h"
00004 #include "TSocket.h"
00005 #include "TServerSocket.h"
00006 #include "TMap.h"
00007 #include "TList.h"
00008 #include "TMonitor.h"
00009 #include "TObjString.h"
00010 #include "TObjArray.h"
00011 #include "TMessage.h"
00012 
00013 StatsServerAlg::StatsServerAlg(const std::string& name, 
00014                                ISvcLocator* pSvcLocator)
00015   : GaudiAlgorithm(name,pSvcLocator),
00016     m_statsSvc(0),
00017     m_server(0),
00018     m_monitor(0),
00019     m_clients(0)
00020 {
00021   declareProperty("ProcessInterval",
00022                   m_processInterval=1,
00023                   "Interval for processing requests to server");
00024   declareProperty("PortNumber",
00025                   m_portNumber=9090,
00026                   "Port Number for server");
00027 }
00028 
00029 StatsServerAlg::~StatsServerAlg()
00030 {
00031 }
00032 
00033 StatusCode StatsServerAlg::initialize()
00034 {
00035   // Initialize the necessary services
00036   StatusCode sc = this->service("StatisticsSvc",m_statsSvc,true);
00037   if(sc.isFailure()){
00038     error() << "Failed to get StatisticsSvc" << endreq;
00039     return sc;
00040   }
00041 
00042   // Start the server
00043   sc = startServer();
00044   return sc;
00045 }
00046 
00047 StatusCode StatsServerAlg::execute()
00048 {
00049   static int currentCycle = 0;
00050   currentCycle += 1;
00051   StatusCode sc = StatusCode::SUCCESS;
00052   // Process server requests every 'n' event cycles
00053   if( currentCycle % m_processInterval == 0 ){
00054     info() << "Processing requests to server" << endreq;
00055     sc = processRequests();
00056   }
00057   return StatusCode::SUCCESS;
00058 }
00059 
00060 StatusCode StatsServerAlg::finalize()
00061 {
00062   if( m_statsSvc ) m_statsSvc->release();
00063   StatusCode sc = stopServer();
00064   return sc;
00065 }
00066 
00068 
00069 StatusCode StatsServerAlg::startServer(){
00070   // Start the Server
00071 
00072   m_server = new TServerSocket(m_portNumber, kTRUE);
00073   if (!m_server->IsValid()){
00074     error() << "Failed to start server on port " << m_portNumber << endreq;
00075     return StatusCode::FAILURE;
00076   }
00077   m_monitor = new TMonitor;
00078   m_monitor->Add( m_server );
00079   m_clients = new TList;
00080   
00081   return StatusCode::SUCCESS;
00082 }
00083 
00084 StatusCode StatsServerAlg::stopServer(){
00085   // Stop the Server
00086   m_clients->Delete();
00087   delete m_clients;
00088   delete m_server;
00089   delete m_monitor;
00090   return StatusCode::SUCCESS;
00091 }
00092 
00093 StatusCode StatsServerAlg::processRequests(){
00094   // Process any requests from clients
00095   int timeout = 20; // timeout if no requests after 20ms 
00096   TSocket* s = m_monitor->Select(timeout);
00097   if( !s ){
00098     error() << "Failure in client socket monitor." << endreq;
00099     return StatusCode::FAILURE;
00100   }
00101   if( s == (TSocket*)-1 ){
00102     // No pending requests before timeout
00103     return StatusCode::SUCCESS;
00104   }
00105 
00106   // Found a request
00107   if( s->IsA() == TServerSocket::Class() ){
00108     // New connection
00109     TSocket* sock = ((TServerSocket*)s)->Accept();
00110     m_monitor->Add(sock);
00111     m_clients->Add(sock);
00112     info() << "Accepted connection from client: " 
00113            << sock->GetInetAddress().GetHostName() << endreq;
00114     return StatusCode::SUCCESS;
00115   }
00116 
00117   // Request for statistics service
00118   char request[1024];
00119   if (s->Recv(request, sizeof(request)) <= 0) {
00120     // Closing connection
00121     m_monitor->Remove(s);
00122     m_clients->Remove(s);
00123     info() << "Closed connection from client: " 
00124            << s->GetInetAddress().GetHostName() << endreq;
00125     delete s;
00126     return StatusCode::SUCCESS;
00127   }
00128 
00129   info() << "Received request: " << request << endreq;
00130 
00131   // Respond to actual request (white-space separated list of paths)
00132   // Return a TMap of path/result pairs
00133   
00134   TMap itemMap;
00135   TList cleanupList;
00136   cleanupList.SetOwner();
00137   TObjString* nullObject = new TObjString("NULL");
00138   cleanupList.Add( nullObject );
00139 
00140   TString reqStr( request );
00141   TObjArray* paths = reqStr.Tokenize( " " );
00142   info() << "Number of requested paths: " << paths->GetEntriesFast() << endreq;
00143   for(int pathIdx=0; pathIdx<paths->GetEntriesFast(); pathIdx++){
00144 
00145     TObjString* path = new TObjString( *(dynamic_cast<TObjString*>(paths->At(pathIdx))));
00146     cleanupList.Add( path );
00147     std::string pathStr( path->GetName() );
00148     info() << "Retrieving path: \"" << pathStr << "\"" << endreq;
00149 
00150     // Check if path exists
00151     if(! m_statsSvc->exists( pathStr ) ){
00152       warning() << "Request for invalid path: " << pathStr << endreq;
00153       itemMap.Add( path, nullObject );
00154       continue;
00155     }
00156 
00157     // Check if path has an object
00158     TObject* object = m_statsSvc->get( pathStr );
00159     if( object ){
00160       info() << "Found object at path: " << pathStr << endreq;
00161       itemMap.Add( path, object );
00162       continue;
00163     }
00164 
00165     // Path is not an object, must be a directory
00166     std::vector<std::string> subFolds = m_statsSvc->getSubFolders( pathStr );
00167     TList* subFolders = new TList();
00168     subFolders->SetName("subFolders");
00169     subFolders->SetOwner();
00170     for(size_t idx=0; idx<subFolds.size(); idx++){
00171       subFolders->Add( new TObjString( subFolds[idx].c_str() ) );
00172     }
00173 
00174     std::vector<std::string> conts = m_statsSvc->getContents( pathStr );
00175     TList* contents = new TList();
00176     contents->SetName("contents");
00177     contents->SetOwner();
00178     for(size_t idx=0; idx<conts.size(); idx++){
00179       contents->Add( new TObjString( conts[idx].c_str() ) );
00180     }
00181 
00182     TMap* directory = new TMap();
00183     directory->SetName("directory");
00184     directory->SetOwner();
00185     directory->Add(new TObjString("subFolders"),subFolders);
00186     directory->Add(new TObjString("contents"),contents);
00187     itemMap.Add( path, directory );
00188     cleanupList.Add( directory );
00189   }
00190   delete paths;
00191 
00192   // Send requested items to client
00193   TMessage answer(kMESS_OBJECT);
00194   answer.WriteObject( &itemMap );
00195   s->Send(answer);
00196 
00197   cleanupList.Delete();
00198 
00199   return StatusCode::SUCCESS;
00200 }
| Classes | Job Modules | Data Objects | Services | Algorithms | Tools | Packages | Directories | Tracs |

Generated on Mon Apr 11 20:10:01 2011 for StatisticsSvc by doxygen 1.4.7