![]() |
|
|
Generated: 8 Jan 2009 |
00001 // $Id: PoolDbEvtSelector.cpp,v 1.8 2008/01/17 13:20:51 marcocle Exp $ 00002 //==================================================================== 00003 // PoolDbEvtSelector.cpp 00004 //-------------------------------------------------------------------- 00005 // 00006 // Package : PoolDbEvtSelector 00007 // 00008 // Description: The PoolDbEvtSelector component is able 00009 // to produce a list of event references given 00010 // a set of "selection criteria". 00011 // 00012 // Author : M.Frank 00013 //==================================================================== 00014 00015 // Include files 00016 #include "GaudiPoolDb/PoolDbEvtSelector.h" 00017 #include "GaudiPoolDb/PoolDbAddress.h" 00018 #include "GaudiPoolDb/IPoolDbMgr.h" 00019 00020 #include "GaudiKernel/ClassID.h" 00021 #include "GaudiKernel/MsgStream.h" 00022 #include "GaudiKernel/SvcFactory.h" 00023 #include "GaudiKernel/Tokenizer.h" 00024 #include "GaudiKernel/IDataManagerSvc.h" 00025 #include "POOLCore/Token.h" 00026 #include "StorageSvc/DbSelect.h" 00027 #include "StorageSvc/DbInstanceCount.h" 00028 00029 00030 DECLARE_SERVICE_FACTORY(PoolDbEvtSelector); 00031 00037 class PoolDbContext : public IEvtSelector::Context { 00038 public: 00039 typedef std::list<std::string> ListName; 00040 private: 00041 const PoolDbEvtSelector* m_pSelector; 00042 mutable pool::DbSelect* m_iterator; 00043 mutable pool::Token* m_token; 00044 ListName m_files; 00045 std::string m_criteria; 00046 ListName::const_iterator m_fileIterator; 00047 std::string m_currentInput; 00048 00049 public: 00051 PoolDbContext(const PoolDbEvtSelector* pSelector); 00053 virtual ~PoolDbContext(); 00054 const std::string& currentInput() const { 00055 return m_currentInput; 00056 } 00057 void setCurrentInput(const std::string& v) { 00058 m_currentInput = v; 00059 } 00060 ListName& files() { 00061 return m_files; 00062 } 00063 virtual void* identifier() const { 00064 return (void*)m_pSelector; 00065 } 00066 void setCriteria(const std::string& crit) { 00067 m_criteria = crit; 00068 } 00069 pool::Token* token() const { 00070 return m_token; 00071 } 00072 void setToken(pool::Token* p) { 00073 pool::releasePtr(m_token); 00074 m_token = p; 00075 } 00076 ListName::const_iterator fileIterator() { 00077 return m_fileIterator; 00078 } 00079 void setFileIterator(ListName::const_iterator new_iter) { 00080 m_fileIterator = new_iter; 00081 } 00082 pool::DbSelect* iterator() const { 00083 return m_iterator; 00084 } 00085 void setIterator(pool::DbSelect* new_iter) { 00086 pool::deletePtr(m_iterator); 00087 m_iterator = new_iter; 00088 } 00089 pool::DbSelect* selectInput(IPoolDbMgr* mgr, 00090 const std::string& sel, 00091 const std::string& input, 00092 const std::string& cnt); 00093 }; 00094 00095 00096 static pool::DbInstanceCount::Counter* s_countPoolDbContext = 00097 pool::DbInstanceCount::getCounter(typeid(PoolDbContext)); 00098 00099 PoolDbContext::~PoolDbContext() { 00100 pool::deletePtr(m_iterator); 00101 pool::releasePtr(m_token); 00102 s_countPoolDbContext->decrement(); 00103 } 00104 00105 PoolDbContext::PoolDbContext(const PoolDbEvtSelector* pSelector) 00106 : m_pSelector(pSelector), m_iterator(0), m_token(0) 00107 { 00108 s_countPoolDbContext->increment(); 00109 } 00110 00111 pool::DbSelect* 00112 PoolDbContext::selectInput( IPoolDbMgr* mgr, 00113 const std::string& sel, 00114 const std::string& input, 00115 const std::string& cnt) 00116 { 00117 setIterator(mgr->createSelect(sel,input,cnt)); 00118 iterator() ? setCurrentInput(input) : setCurrentInput(""); 00119 return iterator(); 00120 } 00121 00122 PoolDbEvtSelector::PoolDbEvtSelector(const std::string& name, 00123 ISvcLocator* svcloc ) 00124 : Service( name, svcloc), 00125 m_dbMgr(0), m_rootCLID(CLID_NULL) 00126 { 00127 declareProperty("CnvService", m_cnvSvcName); 00128 pool::DbInstanceCount::increment(this); 00129 } 00130 00131 PoolDbEvtSelector::~PoolDbEvtSelector() { 00132 pool::DbInstanceCount::decrement(this); 00133 } 00134 00135 // IInterface::queryInterface 00136 StatusCode PoolDbEvtSelector::queryInterface(const InterfaceID& riid, void** ppvIf) { 00137 if ( riid == IID_IEvtSelector ) { 00138 *ppvIf = (IEvtSelector*)this; 00139 addRef(); 00140 return SUCCESS; 00141 } 00142 return Service::queryInterface( riid, ppvIf ); 00143 } 00144 00146 StatusCode PoolDbEvtSelector::initialize() { 00147 // Initialize base class 00148 StatusCode status = Service::initialize(); 00149 MsgStream log(messageService(), name()); 00150 if ( !status.isSuccess() ) { 00151 log << MSG::ERROR << "Error initializing base class Service!" << endreq; 00152 return status; 00153 } 00154 // Retrieve conversion service handling event iteration 00155 status = serviceLocator()->service(m_cnvSvcName, m_dbMgr); 00156 if( !status.isSuccess() ) { 00157 log << MSG::ERROR 00158 << "Unable to localize interface IID_IPoolDbMgr from service:" 00159 << m_cnvSvcName << endreq; 00160 return status; 00161 } 00162 // Get DataSvc 00163 IDataManagerSvc* eds = 0; 00164 status = serviceLocator()->service("EventDataSvc", eds); 00165 if( !status.isSuccess() ) { 00166 log << MSG::ERROR 00167 << "Unable to localize interface IID_IDataManagerSvc " 00168 << "from service EventDataSvc" 00169 << endreq; 00170 return status; 00171 } 00172 m_rootCLID = eds->rootCLID(); 00173 m_rootName = eds->rootName(); 00174 eds->release(); 00175 log << MSG::DEBUG << "Selection root:" << m_rootName 00176 << " CLID:" << m_rootCLID << endreq; 00177 return status; 00178 } 00179 00181 StatusCode PoolDbEvtSelector::finalize() { 00182 // Initialize base class 00183 MsgStream log(messageService(), name()); 00184 pool::releasePtr(m_dbMgr); 00185 StatusCode status = Service::finalize(); 00186 if ( !status.isSuccess() ) { 00187 log << MSG::ERROR << "Error initializing base class Service!" << endreq; 00188 } 00189 return status; 00190 } 00191 00192 StatusCode 00193 PoolDbEvtSelector::createContext(Context*& refpCtxt) const 00194 { 00195 refpCtxt = new PoolDbContext(this); 00196 return StatusCode::SUCCESS; 00197 } 00198 00200 StatusCode PoolDbEvtSelector::last(Context& /*refContext*/) const { 00201 return StatusCode::FAILURE; 00202 } 00203 00204 StatusCode 00205 PoolDbEvtSelector::next(Context& ctxt) const 00206 { 00207 PoolDbContext* pCtxt = dynamic_cast<PoolDbContext*>(&ctxt); 00208 if ( pCtxt != 0 ) { 00209 pool::DbSelect* it = pCtxt->iterator(); 00210 if ( !it ) { 00211 PoolDbContext::ListName::const_iterator fileit = pCtxt->fileIterator(); 00212 if ( pCtxt->currentInput().length() > 0 ) { 00213 pCtxt->setToken(0); 00214 m_dbMgr->disconnect(pCtxt->currentInput()); 00215 } 00216 if ( fileit != pCtxt->files().end() ) { 00217 std::string input = *fileit; 00218 pCtxt->setFileIterator(++fileit); 00219 it = pCtxt->selectInput(m_dbMgr, "", input, m_rootName); 00220 } 00221 } 00222 if ( it ) { 00223 pool::Token* token = 0; 00224 if ( it->next(token).isSuccess() ) { 00225 pCtxt->setToken(token); 00226 if( 0 == pCtxt->token() ) { 00227 pCtxt->setIterator(0); 00228 return next(ctxt); 00229 } 00230 return StatusCode::SUCCESS; 00231 } 00232 return StatusCode::FAILURE; 00233 } 00234 } 00235 if ( pCtxt ) { 00236 if ( pCtxt->currentInput().length() > 0 ) { 00237 m_dbMgr->disconnect( pCtxt->currentInput() ); 00238 } 00239 pCtxt->setToken(0); 00240 pCtxt->setIterator(0); 00241 pCtxt->setCurrentInput(""); 00242 pCtxt->setFileIterator(pCtxt->files().end()); 00243 } 00244 return StatusCode::FAILURE; 00245 } 00246 00247 StatusCode 00248 PoolDbEvtSelector::next(Context& ctxt,int jump) const 00249 { 00250 if ( jump > 0 ) { 00251 for ( int i = 0; i < jump; ++i ) { 00252 StatusCode status = next(ctxt); 00253 if ( !status.isSuccess() ) { 00254 return status; 00255 } 00256 } 00257 return StatusCode::SUCCESS; 00258 } 00259 return StatusCode::FAILURE; 00260 } 00261 00262 StatusCode 00263 PoolDbEvtSelector::previous(Context& /* ctxt */) const 00264 { 00265 MsgStream log(msgSvc(), name()); 00266 log << MSG::FATAL 00267 << " EventSelector Iterator, operator -- not supported " << endreq; 00268 return StatusCode::FAILURE; 00269 } 00270 00271 StatusCode 00272 PoolDbEvtSelector::previous(Context& ctxt, int jump) const 00273 { 00274 if ( jump > 0 ) { 00275 for ( int i = 0; i < jump; ++i ) { 00276 StatusCode status = previous(ctxt); 00277 if ( !status.isSuccess() ) { 00278 return status; 00279 } 00280 } 00281 return StatusCode::SUCCESS; 00282 } 00283 return StatusCode::FAILURE; 00284 } 00285 00286 StatusCode 00287 PoolDbEvtSelector::rewind(Context& ctxt) const 00288 { 00289 PoolDbContext* pCtxt = dynamic_cast<PoolDbContext*>(&ctxt); 00290 if ( pCtxt ) { 00291 if ( pCtxt->currentInput().length() > 0 ) { 00292 m_dbMgr->disconnect( pCtxt->currentInput() ); 00293 } 00294 pCtxt->setToken(0); 00295 pCtxt->setIterator(0); 00296 pCtxt->setCurrentInput(""); 00297 pCtxt->setFileIterator(pCtxt->files().begin()); 00298 return StatusCode::SUCCESS; 00299 } 00300 return StatusCode::FAILURE; 00301 } 00302 00303 StatusCode 00304 PoolDbEvtSelector::createAddress(const Context& ctxt, IOpaqueAddress*& pAddr) const 00305 { 00306 const PoolDbContext* pctxt = dynamic_cast<const PoolDbContext*>(&ctxt); 00307 if ( pctxt ) { 00308 pool::Token* tok = pctxt->token(); 00309 if ( 0 != tok ) { 00310 PoolDbAddress* pA = 0; 00311 if ( m_dbMgr->createAddress(tok, &pA).isSuccess() ) { 00312 pAddr = pA; 00313 return StatusCode::SUCCESS; 00314 } 00315 pool::releasePtr(tok); 00316 } 00317 } 00318 pAddr = 0; 00319 return StatusCode::FAILURE; 00320 } 00321 00322 StatusCode 00323 PoolDbEvtSelector::releaseContext(Context*& ctxt) const 00324 { 00325 PoolDbContext* pCtxt = dynamic_cast<PoolDbContext*>(ctxt); 00326 if ( pCtxt ) { 00327 pool::deletePtr(pCtxt); 00328 return StatusCode::SUCCESS; 00329 } 00330 return StatusCode::FAILURE; 00331 } 00332 00333 StatusCode 00334 PoolDbEvtSelector::resetCriteria(const std::string& criteria, 00335 Context& context) const 00336 { 00337 MsgStream log(messageService(), name()); 00338 PoolDbContext* ctxt = dynamic_cast<PoolDbContext*>(&context); 00339 std::string db, typ, item, sel, stmt, aut, addr; 00340 if ( ctxt ) { 00341 if ( criteria.substr(0,5) == "FILE " ) { 00342 // The format for the criteria is: 00343 // FILE filename1, filename2 ... 00344 db = criteria.substr(5); 00345 } 00346 else { 00347 Tokenizer tok(true); 00348 tok.analyse(criteria," ","","","=","'","'"); 00349 for(Tokenizer::Items::iterator i=tok.items().begin(); i!=tok.items().end();i++) { 00350 std::string tmp = (*i).tag().substr(0,3); 00351 if(tmp=="DAT") { 00352 db = (*i).value(); 00353 } 00354 if(tmp=="OPT") { 00355 if((*i).value() != "REA") { 00356 log << MSG::ERROR << "Option:\"" << (*i).value() << "\" not valid" << endreq; 00357 return StatusCode::FAILURE; 00358 } 00359 } 00360 if (tmp=="TYP") { 00361 typ = (*i).value(); 00362 } 00363 if(tmp=="ADD") { 00364 item = (*i).value(); 00365 } 00366 if(tmp=="SEL") { 00367 sel = (*i).value(); 00368 } 00369 if(tmp=="FUN") { 00370 stmt = (*i).value(); 00371 } 00372 if(tmp=="AUT") { 00373 aut = (*i).value(); 00374 } 00375 if(tmp=="COL") { 00376 addr = (*i).value(); 00377 } 00378 } 00379 } 00380 // It's now time to parse the criteria for the event selection 00381 // The format for the criteria is: 00382 // FILE filename1, filename2 ... 00383 // JOBID number1-number2, number3, ... 00384 std::string rest = db; 00385 ctxt->files().clear(); 00386 while(true) { 00387 int ipos = rest.find_first_not_of(" ,"); 00388 if (ipos == -1 ) break; 00389 rest = rest.substr(ipos, std::string::npos);// remove blanks before 00390 int lpos = rest.find_first_of(" ,"); // locate next blank 00391 ctxt->files().push_back( rest.substr(0,lpos )); // insert in list 00392 if (lpos == -1 ) break; 00393 rest = rest.substr(lpos, std::string::npos);// get the rest 00394 } 00395 ctxt->setFileIterator(ctxt->files().begin()); 00396 ctxt->setCriteria(criteria); 00397 return StatusCode::SUCCESS; 00398 } 00399 log << MSG::ERROR << "Invalid iteration context." << endreq; 00400 return StatusCode::FAILURE; 00401 } 00402