EventCollectionSelector.cpp
Go to the documentation of this file.00001
00002
00003
00004 #include "GaudiKernel/SmartIF.h"
00005 #include "GaudiKernel/SvcFactory.h"
00006 #include "GaudiKernel/ObjectFactory.h"
00007 #include "GaudiKernel/GenericAddress.h"
00008 #include "GaudiKernel/MsgStream.h"
00009 #include "GaudiKernel/IRegistry.h"
00010 #include "GaudiKernel/INTupleSvc.h"
00011 #include "GaudiKernel/ISvcLocator.h"
00012 #include "GaudiKernel/IDataSourceMgr.h"
00013 #include "GaudiKernel/IAddressCreator.h"
00014 #include "GaudiKernel/ISelectStatement.h"
00015 #include "GaudiKernel/NTuple.h"
00016 #include "GaudiKernel/EventSelectorDataStream.h"
00017
00018 #include "EventCollectionSelector.h"
00019
00020 #include <memory>
00021
00022 DECLARE_SERVICE_FACTORY(EventCollectionSelector)
00023
00024
00029 class EventCollectionContext : public IEvtSelector::Context {
00030 public:
00031 typedef std::list<std::string> ListName;
00032 private:
00033 GenericAddress* m_pAddressBuffer;
00034 const EventCollectionSelector* m_pSelector;
00035 ListName m_files;
00036 std::string m_criteria;
00037 ListName::const_iterator m_fileIterator;
00038 std::string m_currentInput;
00039
00040 public:
00042 EventCollectionContext(const EventCollectionSelector* pSelector);
00044 virtual ~EventCollectionContext();
00045 const std::string& currentInput() const {
00046 return m_currentInput;
00047 }
00048 void setCurrentInput(const std::string& v) {
00049 m_currentInput = v;
00050 }
00051 ListName& files() {
00052 return m_files;
00053 }
00054 virtual void* identifier() const {
00055 return (void*)m_pSelector;
00056 }
00057 void setCriteria(const std::string& crit) {
00058 m_criteria = crit;
00059 }
00060 ListName::const_iterator fileIterator() {
00061 return m_fileIterator;
00062 }
00063 void setFileIterator(ListName::const_iterator new_iter)
00064 { m_fileIterator = new_iter; }
00065 };
00066
00067 EventCollectionContext::~EventCollectionContext() {
00068 m_pAddressBuffer->release();
00069 }
00070
00071 EventCollectionContext::EventCollectionContext(const EventCollectionSelector* pSelector)
00072 : m_pSelector(pSelector)
00073 {
00074 m_pAddressBuffer = new GenericAddress();
00075 m_pAddressBuffer->addRef();
00076 }
00077
00078
00079 EventCollectionSelector::EventCollectionSelector(const std::string& name, ISvcLocator* svcloc )
00080 : base_class(name, svcloc)
00081 {
00082 declareProperty("CnvService", m_tupleSvcName = "EvtTupleSvc");
00083 declareProperty("Authentication",m_authentication= "");
00084 declareProperty("Container", m_cntName = "B2PiPi");
00085 declareProperty("Item", m_itemName = "Address");
00086 declareProperty("Criteria", m_criteria = "");
00087 declareProperty("DB", m_database = "");
00088 declareProperty("DbType", m_dbType = "");
00089 declareProperty("Function", m_statement= "NTuple::Selector");
00090 }
00091
00092 EventCollectionSelector::~EventCollectionSelector() {
00093 }
00094
00095
00096 StatusCode EventCollectionSelector::initialize() {
00097
00098 StatusCode status = Service::initialize();
00099 MsgStream log(msgSvc(), name());
00100 if ( !status.isSuccess() ) {
00101 log << MSG::ERROR << "Error initializing base class Service!" << endmsg;
00102 return status;
00103 }
00104 m_pAddrCreator = serviceLocator()->service("EventPersistencySvc");
00105 if(!m_pAddrCreator.isValid()) {
00106 log << MSG::ERROR << "Unable to locate IAddressCreator interface of " << "EventPersistencySvc" << endmsg;
00107 return status;
00108 }
00109 m_tupleSvc = serviceLocator()->service(m_tupleSvcName);
00110 if( !m_tupleSvc.isValid() ) {
00111 log << MSG::ERROR << "Unable to locate INTupleSvc interface of " << m_tupleSvcName << endmsg;
00112 return status;
00113 }
00114 return status;
00115 }
00116
00117
00118 StatusCode
00119 EventCollectionSelector::connectDataSource(const std::string& db, const std::string& ) const {
00120 StatusCode status = StatusCode::FAILURE;
00121 SmartIF<IDataSourceMgr> svc(m_tupleSvc);
00122 if ( svc.isValid( ) && db.length() > 0 ) {
00123 std::string ident = name() + ' ';
00124 ident += "DATAFILE='" + m_database.substr(5,m_database.length()) + "' ";
00125 ident += "TYP='" + m_dbType + "' ";
00126 ident += "OPT='READ' ";
00127 if ( m_authentication.length() > 0 ) {
00128 ident += "AUTH='" + m_authentication + "' ";
00129 }
00130 status = svc->connect(ident);
00131 }
00132 return status;
00133 }
00134
00136 StatusCode
00137 EventCollectionSelector::connectTuple(const std::string& nam, const std::string& itName, NTuple::Tuple*& tup, NTuple::Item<IOpaqueAddress*>*& item) const {
00138 std::string top = "/NTUPLES/" + name() + '/' + nam;
00139 StatusCode status = m_tupleSvc->retrieveObject(top, (DataObject*&)tup);
00140 if ( status.isSuccess() ) {
00141 item = new NTuple::Item<IOpaqueAddress*>();
00142 status = tup->item(itName, *item);
00143 if ( status.isSuccess() ) {
00144 return status;
00145 }
00146 else {
00147 MsgStream log(msgSvc(), name());
00148 log << MSG::ERROR << "Item " << itName << " is not part of the collection:" << top << endmsg;
00149 }
00150 delete item;
00151 item = 0;
00152 }
00153 else {
00154 MsgStream err(msgSvc(), name());
00155 err << MSG::ERROR << "Cannot connect to collection:" << top << endmsg;
00156 }
00157 tup = 0;
00158 return status;
00159 }
00160
00162 StatusCode
00163 EventCollectionSelector::connectStatement(const std::string& typ, const std::string& crit, INTuple* tuple) const {
00164 std::string seltyp = typ;
00165 if ( seltyp.length() > 0 || crit.length() > 0 ) {
00166 if ( crit.length() > 0 && seltyp.length() == 0 ) seltyp = "NTuple::Selector";
00167 SmartIF<ISelectStatement> stmt(ROOT::Reflex::PluginService::Create<IInterface*>(seltyp, (IInterface*)serviceLocator()));
00168 if ( stmt.isValid( ) ) {
00169 if ( crit.length() > 0 ) stmt->setCriteria(crit);
00170 tuple->attachSelector(stmt).ignore();
00171 return StatusCode::SUCCESS;
00172 }
00173 return StatusCode::FAILURE;
00174 }
00175 return StatusCode::SUCCESS;
00176 }
00177
00179 StatusCode EventCollectionSelector::getNextRecord(NTuple::Tuple* tuple) const {
00180 StatusCode status = StatusCode::FAILURE;
00181 if ( 0 != tuple ) {
00182 do {
00183 status = m_tupleSvc->readRecord(tuple);
00184 if ( status.isSuccess() ) {
00185 ISelectStatement* statement = tuple->selector();
00186 bool use_it = (statement) ? (*statement)(tuple) : true;
00187 if ( use_it ) {
00188 return status;
00189 }
00190 }
00191 } while ( status.isSuccess() );
00192 }
00193 return status;
00194 }
00195
00197 StatusCode EventCollectionSelector::getPreviousRecord(NTuple::Tuple* tuple ) const {
00198 StatusCode status = StatusCode::FAILURE;
00199 if ( tuple ) {
00200 IRegistry* pReg = tuple->registry();
00201 if ( pReg ) {
00202 IOpaqueAddress* pAddr = pReg->address();
00203 if ( pAddr ) {
00204 long* ip = (long*)pAddr->ipar();
00205 do {
00206 if ( ip[1] > 1 ) {
00207 ip[1] -= 2;
00208 status = m_tupleSvc->readRecord(tuple);
00209 if ( status.isSuccess() ) {
00210 ISelectStatement* statement = tuple->selector();
00211 bool use_it = (statement) ? (*statement)(tuple) : true;
00212 if ( use_it ) {
00213 return status;
00214 }
00215 }
00216 }
00217 else {
00218 return StatusCode::FAILURE;
00219 }
00220 } while ( status.isSuccess() );
00221 }
00222 }
00223 }
00224 return StatusCode::FAILURE;
00225 }
00226
00227
00228 StatusCode EventCollectionSelector::connectCollection(MyContextType* ctxt) const
00229 {
00230 if ( ctxt ) {
00231 StatusCode status = connectDataSource(m_database, m_dbType);
00232 if ( status.isSuccess() ) {
00233 status = connectTuple(m_cntName, m_itemName, ctxt->tuple, ctxt->item);
00234 if ( status.isSuccess() ) {
00235 status = connectStatement(m_statement, m_criteria, ctxt->tuple);
00236 if ( status.isSuccess() ) {
00237 *(ctxt->item) = 0;
00238 return status;
00239 }
00240 }
00241 }
00242 return status;
00243 }
00244 return StatusCode::FAILURE;
00245 }
00246
00247
00248 StatusCode EventCollectionSelector::finalize() {
00249
00250 m_pAddrCreator = 0;
00251 m_tupleSvc = 0;
00252 return Service::finalize();
00253 }
00254
00256 StatusCode
00257 EventCollectionSelector::createContext(Context*& refpCtxt) const
00258 {
00259 refpCtxt = 0;
00260 std::auto_ptr<MyContextType> ctxt(new MyContextType());
00261 StatusCode status = connectCollection(ctxt.get());
00262 if( !status.isSuccess() ) {
00263 MsgStream log(msgSvc(), name());
00264 log << MSG::ERROR << "Unable to connect Collection file \"" << m_database << "\"" << endmsg;
00265 return status;
00266 }
00267 refpCtxt = ctxt.release();
00268 return StatusCode::SUCCESS;
00269 }
00270
00272 StatusCode
00273 EventCollectionSelector::next(Context& refCtxt) const
00274 {
00275 return next(refCtxt, 1);
00276 }
00277
00279 StatusCode
00280 EventCollectionSelector::next(Context& refCtxt,int jump) const
00281 {
00282 MyContextType *ctxt = dynamic_cast<MyContextType*>(&refCtxt);
00283 if ( ctxt ) {
00284 *(ctxt->item) = ctxt->addressBuffer;
00285 StatusCode sc = StatusCode::SUCCESS;
00286 for ( int i=0; i<jump && sc.isSuccess(); ++i ) {
00287 sc = getNextRecord(ctxt->tuple);
00288 }
00289 return sc;
00290 }
00291 return StatusCode::FAILURE;
00292 }
00293
00295 StatusCode
00296 EventCollectionSelector::previous(Context& refCtxt) const
00297 {
00298 return previous(refCtxt, 1);
00299 }
00300
00302 StatusCode
00303 EventCollectionSelector::previous(Context& refCtxt,int jump) const
00304 {
00305 MyContextType *ctxt = dynamic_cast<MyContextType*>(&refCtxt);
00306 if ( ctxt ) {
00307 *(ctxt->item) = ctxt->addressBuffer;
00308 StatusCode sc = StatusCode::SUCCESS;
00309 for ( int i=0; i<jump && sc.isSuccess(); ++i ) {
00310 sc = getPreviousRecord(ctxt->tuple);
00311 }
00312 return sc;
00313 }
00314 return StatusCode::FAILURE;
00315 }
00316
00318 StatusCode
00319 EventCollectionSelector::rewind(Context& ) const
00320 {
00321 return StatusCode::FAILURE;
00322 }
00323
00325 StatusCode
00326 EventCollectionSelector::createAddress(const Context& refCtxt, IOpaqueAddress*& refpAddr) const
00327 {
00328 const MyContextType* ctxt = dynamic_cast<const MyContextType*>(&refCtxt);
00329 if ( ctxt ) {
00330 IOpaqueAddress* pA = *(ctxt->item);
00331 if ( pA ) {
00332 IOpaqueAddress* pAddress = 0;
00333 StatusCode status = m_pAddrCreator->createAddress(pA->svcType(),
00334 pA->clID(),
00335 pA->par(),
00336 pA->ipar(),
00337 pAddress);
00338 if ( status.isSuccess() ) {
00339 refpAddr = pAddress;
00340 return StatusCode::SUCCESS;
00341 }
00342 else {
00343 MsgStream log(msgSvc(), name());
00344 log << MSG::ERROR << "Failed to access " << pA->par()[0]
00345 << ":" << pA->par()[1]
00346 << " SvcTyp:" << long(pA->svcType())
00347 << " CLID:" << pA->clID()
00348 << endmsg;
00349 }
00350 }
00351 }
00352 return StatusCode::FAILURE;
00353 }
00354
00356 StatusCode
00357 EventCollectionSelector::releaseContext(Context*& refCtxt) const
00358 {
00359 MyContextType *ctxt = dynamic_cast<MyContextType*>(refCtxt);
00360 if ( ctxt ) {
00361 delete ctxt;
00362 ctxt = 0;
00363 return StatusCode::SUCCESS;
00364 }
00365 return StatusCode::FAILURE;
00366 }
00367
00370 StatusCode
00371 EventCollectionSelector::resetCriteria(const std::string& cr,Context& refCtxt) const
00372 {
00373 MyContextType *ctxt = dynamic_cast<MyContextType*>(&refCtxt);
00374 if ( ctxt ) {
00375 ctxt->criteria = cr;
00376 return StatusCode::SUCCESS;
00377 }
00378 return StatusCode::FAILURE;
00379 }
00380
00382 StatusCode
00383 EventCollectionSelector::last(Context& ) const
00384 {
00385 return StatusCode::FAILURE;
00386 }