Gaudi Framework, version v25r2

Home   Generated: Wed Jun 4 2014
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Groups Pages
MultiFileCatalog.cpp
Go to the documentation of this file.
3 #include <Gaudi/PluginService.h>
4 #include "MultiFileCatalog.h"
5 #include <stdexcept>
6 #include <algorithm>
7 
8 namespace Gaudi { std::string createGuidAsString(); }
9 
10 using namespace Gaudi;
11 using namespace std;
12 
14 
15 namespace {
16  template <class V,class F>
17  bool _findX0Bool(V& array, F pmf, bool invert) {
18  for(typename V::const_iterator i=array.begin(); i != array.end(); ++i) {
19  bool res = invert ? !((*i)->*pmf)() : ((*i)->*pmf)();
20  if ( !res ) return false;
21  }
22  return true;
23  }
24 }
25 // ----------------------------------------------------------------------------
26 MultiFileCatalog::MultiFileCatalog(const std::string& nam, ISvcLocator* svc)
27  : base_class(nam, svc), m_started(false), m_oldNames()
28 {
29  declareProperty("Catalogs", m_catalogNames, "The list of Catalogs")
30  -> declareUpdateHandler ( &Gaudi::MultiFileCatalog::propHandler, this ) ;
31  m_catalogNames.push_back("xmlcatalog_file:test_catalog.xml");
32 }
33 // ----------------------------------------------------------------------------
34 MultiFileCatalog::~MultiFileCatalog() {
35 }
36 // ----------------------------------------------------------------------------
38  CatalogNames::const_iterator i;
39  std::string current = "";
40  if ( !Service::initialize().isSuccess() ) {
41  printError("Failed to initialize service base class.",false);
42  return StatusCode::SUCCESS;
43  }
44  try {
45  for(i=m_catalogNames.begin(); i != m_catalogNames.end(); ++i) {
46  current = *i;
47  addCatalog(*i);
48  }
49  init();
50  return StatusCode::SUCCESS;
51  }
52  catch(const std::exception& /* e */) {
53  printError("Cannot add file catalog:"+current,false);
54  }
55  return StatusCode::FAILURE;
56 }
57 // ----------------------------------------------------------------------------
58 StatusCode MultiFileCatalog::finalize() {
59  commit();
60  _exec(&IFileCatalog::release);
61  m_catalogs.clear();
62  m_started = false;
63  return Service::finalize();
64 }
65 // ----------------------------------------------------------------------------
67 std::string MultiFileCatalog::createFID() const {
68  return createGuidAsString();
69 }
70 // ----------------------------------------------------------------------------
71 MultiFileCatalog::CSTR MultiFileCatalog::connectInfo() const {
72  static string s("MultiCatalog");
73  return s;
74 }
75 // ----------------------------------------------------------------------------
76 IFileCatalog* MultiFileCatalog::getCatalog(CSTR fid,
77  bool throw_if_not,
78  bool writable,
79  bool prt) const
80 {
81  for(Catalogs::const_iterator i=m_catalogs.begin(); i != m_catalogs.end(); ++i) {
82  IFileCatalog* c = *i;
83  if ( c ) {
84  if ( writable && c->readOnly() )
85  continue;
86  else if ( fid.empty() )
87  return c;
88  else if ( !fid.empty() && c->existsFID(fid) )
89  return c;
90  }
91  }
92  if ( prt ) {
93  printError("No writable file catalog found which contains FID:"+fid,throw_if_not);
94  }
95  else {
96  MsgStream log(msgSvc(),name());
97  log << MSG::DEBUG << "No writable file catalog found which contains FID:" << fid << endmsg;
98  }
99  return 0;
100 }
101 // ----------------------------------------------------------------------------
102 IFileCatalog* MultiFileCatalog::findCatalog(CSTR connect, bool must_be_writable) const {
103  for(Catalogs::const_iterator i=m_catalogs.begin(); i != m_catalogs.end(); ++i) {
104  if ( connect == (*i)->connectInfo() )
105  return (must_be_writable && (*i)->readOnly()) ? 0 : *i;
106  }
107  return 0;
108 }
109 // ----------------------------------------------------------------------------
110 MultiFileCatalog::Catalogs::iterator
111 MultiFileCatalog::i_findCatalog(CSTR connect, bool must_be_writable) {
112  for(Catalogs::iterator i=m_catalogs.begin(); i != m_catalogs.end(); ++i) {
113  if ( connect == (*i)->connectInfo() ) {
114  return (must_be_writable && (*i)->readOnly()) ? m_catalogs.end() : i;
115  }
116  }
117  return m_catalogs.end();
118 }
119 // ----------------------------------------------------------------------------
120 void MultiFileCatalog::printError(CSTR msg, bool rethrow) const {
121  MsgStream log(msgSvc(),name());
122  if ( rethrow ) {
123  log << MSG::FATAL << msg << endmsg;
124  throw runtime_error("Catalog> "+msg);
125  }
126  log << MSG::ERROR << msg << endmsg;
127 }
128 // ----------------------------------------------------------------------------
129 void MultiFileCatalog::addCatalog(CSTR con) {
130  if ( !con.empty() ) {
131  if ( 0 == findCatalog(con,false) ) {
132  static const string xml_typ = "Gaudi::XMLFileCatalog";
133  string::size_type id0 = con.find("_");
134  string typ = con.substr(0,id0);
135  string url = con.substr(id0+1);
136  IInterface* cat = 0;
137  if ( strncasecmp("xml",typ.c_str(),3) == 0 ) {
138  cat = IFileCatalog::Factory::create(xml_typ,url,msgSvc().get());
139  }
140  else {
141  using Gaudi::PluginService::Details::Registry;
142  Registry& registry = Registry::instance();
143  if (registry.getInfo(typ).type ==
144  typeid(Service::Factory::FuncType).name()) {
145  cat = Service::Factory::create(typ,url,serviceLocator().get());
146  } else if (registry.getInfo(typ).type ==
147  typeid(IFileCatalog::Factory::FuncType).name()) {
148  cat = IFileCatalog::Factory::create(typ,url,msgSvc().get());
149  }
150  }
151  if ( cat ) {
152  IFileCatalog* fileCat = 0;
153  if ( cat->queryInterface(IFileCatalog::interfaceID(),pp_cast<void>(&fileCat)).isSuccess() ) {
154  addCatalog(fileCat);
155  cat->release();
156  return;
157  }
158  }
159  printError("Failed to create catalog connection:"+con,true);
160  }
162  return;
163  }
164  printError("Got invalid (empty) catalog connection string.",true);
165 }
166 // ----------------------------------------------------------------------------
167 void MultiFileCatalog::addCatalog(IFileCatalog* cat) {
168  if ( cat ) {
169  cat->addRef();
170  m_catalogs.push_back(cat);
171  return;
172  }
173  printError("Got invalid catalog to be added to multi catalog.",true);
174 }
175 // ----------------------------------------------------------------------------
176 void MultiFileCatalog::removeCatalog(CSTR con) {
177  if ( con.empty() || con == "*" ) {
178  _exec(&IFileCatalog::release);
179  m_catalogs.clear();
180  return;
181  }
182  removeCatalog(findCatalog(con,false));
183 }
184 // ----------------------------------------------------------------------------
185 void MultiFileCatalog::removeCatalog(const IFileCatalog* cat) {
186  if ( cat ) {
187  Catalogs::iterator i=find(m_catalogs.begin(),m_catalogs.end(),cat);
188  if ( i != m_catalogs.end() ) {
189  (*i)->release();
190  m_catalogs.erase(i);
191  return;
192  }
193  printError("Unknown file catalog -- cannot be removed.",true);
194  }
195  printError("Invalid file catalog.",true);
196 }
197 // ----------------------------------------------------------------------------
198 void MultiFileCatalog::setWriteCatalog(IFileCatalog* cat) {
199  if ( cat ) {
200  if ( !cat->readOnly() ) {
201  Catalogs::iterator i=find(m_catalogs.begin(),m_catalogs.end(),cat);
202  if ( i != m_catalogs.end() ) {
203  m_catalogs.erase(i);
204  m_catalogs.insert(m_catalogs.begin(),cat);
205  return;
206  }
207  printError("The catalog "+cat->connectInfo()+" is not known.",true);
208  }
209  printError("The catalog "+cat->connectInfo()+" is not writable.",true);
210  }
211  printError("Invalid file catalog.",true);
212 }
213 // ----------------------------------------------------------------------------
214 void MultiFileCatalog::setWriteCatalog(CSTR connect) {
215  Catalogs::iterator i = i_findCatalog(connect,true);
216  if ( i == m_catalogs.end() ) {
217  addCatalog(connect);
218  setWriteCatalog(findCatalog(connect,true));
219  return;
220  }
221  setWriteCatalog(*i);
222 }
223 // ----------------------------------------------------------------------------
224 string MultiFileCatalog::getMetaDataItem(CSTR fid,CSTR attr) const {
225  std::string result;
226  for(Catalogs::const_iterator i=m_catalogs.begin(); i != m_catalogs.end(); ++i)
227  if ( !(result= (*i)->getMetaDataItem(fid,attr)).empty() ) break;
228  return result;
229 }
231 void MultiFileCatalog::registerPFN(CSTR fid, CSTR pfn, CSTR ftype) const {
232  IFileCatalog* c = getCatalog(fid,false,true,false);
233  if ( !c ) c = getCatalog("",true,true,true);
234  c->registerPFN(fid, pfn, ftype);
235 }
237 void MultiFileCatalog::registerLFN(CSTR fid, CSTR lfn) const {
238  IFileCatalog* c = getCatalog(fid,false,true,false);
239  if ( !c ) c = getCatalog("",true,true,true);
240  c->registerLFN(fid, lfn);
241 }
242 // ----------------------------------------------------------------------------
243 bool MultiFileCatalog::readOnly() const
244 { return _findX0Bool(m_catalogs,&IFileCatalog::readOnly,false); }
245 // ----------------------------------------------------------------------------
246 bool MultiFileCatalog::dirty() const
247 { return _findX0Bool(m_catalogs,&IFileCatalog::dirty,true); }
248 // ----------------------------------------------------------------------------
249 void MultiFileCatalog::propHandler(Property& /* p */)
250 {
251  // not yet initialized
252  if ( !m_started ) { m_oldNames = m_catalogNames; return; } // RETURN
253  // no real change - no action
254  if ( m_catalogNames == m_oldNames ) { return; }
255  m_oldNames = m_catalogNames ;
256  // remove ALL catalogs
257  removeCatalog("") ;
258  // add new catalogs
259  for ( CatalogNames::const_iterator inew = m_catalogNames.begin() ;
260  m_catalogNames.end() != inew ; ++inew ) { addCatalog ( *inew ) ; }
261  // start
262  init() ;
263  //
264  MsgStream log ( msgSvc() , name() ) ;
265  log << MSG::DEBUG
266  << "New catalogs to be used: "
267  << Gaudi::Utils::toString ( m_catalogNames ) << endmsg ;
268 }

Generated at Wed Jun 4 2014 14:48:58 for Gaudi Framework, version v25r2 by Doxygen version 1.8.2 written by Dimitri van Heesch, © 1997-2004