Main Page   Namespace List   Class Hierarchy   Compound List   File List   Namespace Members   Compound Members   File Members  

CdbBdbProxyBase.cc

Go to the documentation of this file.
00001 // File and Version Information:
00002 //      $Id: CdbBdbProxyBase.cc,v 1.15 2005/03/09 22:57:00 gapon Exp $
00003 
00004 /// The implementation of the CdbBdbProxyBase and CdbBdbProxyBaseUsingRevision classes.
00005 /**
00006   * @see CdbBdbProxyBase
00007   * @see CdbBdbProxyBaseUsingRevision
00008   */
00009 #include "BaBar/BaBar.hh"
00010 
00011 #include "CdbBdb/CdbBdbProxyBase.hh"
00012 
00013 #include "CdbBase/CdbStateId.hh"
00014 #include "CdbBase/CdbTransaction.hh"
00015 
00016 #include "BdbCond/BdbCondDefEventKey.hh"
00017 
00018 #include "AbsEnv/AbsEnv.hh"
00019 #include "GenEnv/GenEnv.hh"
00020 
00021 #include "ProxyDict/AbsArgCast.hh"
00022 
00023 #include "EidData/EidCondKeyTriplet.hh"
00024 #include "ErrLogger/ErrLog.hh"
00025 
00026 #include <assert.h>
00027 
00028 ////////////////////////////
00029 // Class: CdbBdbProxyBase //
00030 ////////////////////////////
00031 
00032 template< class T >
00033 CdbBdbProxyBase<T>::CdbBdbProxyBase( BdbCondDefStrategy* theStrategy ) :
00034     CdbBdbProxyCache( ),
00035     _strategy (theStrategy),
00036     _transient(0)
00037 {
00038   // Instantiate the default strategy to use the primary event key
00039   // if nothing else was specified
00040 
00041     if( 0 == strategy( )) setStrategy(  new BdbCondDefEventKey( ));
00042 }
00043 
00044 template< class T >
00045 CdbBdbProxyBase<T>::~CdbBdbProxyBase( )
00046 { }
00047 
00048 template< class T >
00049 T*
00050 CdbBdbProxyBase<T>::faultHandler( IfdProxyDict* theDict,
00051                                   const IfdKey& theKey,
00052                                   AbsArg&       theArg )
00053 {
00054   // Figure out what time to use...
00055 
00056     BdbTime validityTime( 0 );
00057     if( 0 != strategy( )) {
00058         validityTime = strategy( )->defaultKey( ).key( );
00059     } else {
00060         BdbTime* t = AbsArgCast< BdbTime >::value( theArg );
00061         if( 0 == t ) ErrMsg(fatal) << "unable to determine the validity time." << endmsg;
00062         validityTime = *t;
00063     }
00064 
00065   // Check if the persistent cach is still valid. If not then update it and
00066   // recalculate the transient.
00067 
00068     if( 0 == transientCache( ) || !isCacheValid( validityTime )) {
00069 
00070 
00071       // Update the persistent cache otherwise
00072       //
00073       // NOTE: We're using the artificially constructed value of the State Identifier
00074       //       as a temporary solution just because the GenEnv does not provide us with
00075       //       this information.
00076 
00077       // The subsequent code is being executed within a transaction provided
00078       // via an object of the CdbTransaction class, implementing
00079       // the "resource-acquisition-is-initialization" paradigm.
00080 
00081         {
00082             CdbTransaction transaction;
00083 
00084           // do it in the loop until complete success or failure
00085 
00086             std::vector<CdbBdbProxyElement> elements;
00087             bool gotit = false ;
00088             do {
00089 
00090               // the persisten cache needs to be updated
00091 
00092                 CdbStateId stateId( CdbId( 0, 0 ), BdbTime( 0 ));
00093 
00094                 if( CdbStatus::Success != updateCache( validityTime,
00095                                                        stateId,
00096                                                        elements )) {
00097 
00098                   // failure to access conditions db
00099 
00100                     ErrMsg(error) << "failure to access conditions information: no transient returned" << endmsg;
00101 
00102                     invalidateTransientCache( );
00103 
00104                     gotit = true;   // while it's not really true, this will stop the loop
00105 
00106                 } else {
00107 
00108                   // Let the actuall proxy to recalculate the transient, then update
00109                   // the local transient cache.
00110 
00111                     T* newtransient = this->redefinedFaultHandler( elements );
00112 
00113                     if ( 0 != newtransient ) {
00114 
00115                       // can stop at this point
00116 
00117                         gotit = true;
00118 
00119                     } else {
00120 
00121                       // can't make transient guy, try to fund different persistent guy.
00122 
00123                         BdbTime anotherTime;
00124                         if ( tryAnotherTime( validityTime,
00125                                              elements,
00126                                              anotherTime )) {
00127 
00128                           // rerun everything with the different time
00129 
00130                             validityTime = anotherTime;
00131 
00132                         } else {
00133 
00134                           // no, can't do it
00135 
00136                             gotit = true;
00137                         }
00138                     }
00139 
00140                   // Update the transient cache if got a new pointer
00141 
00142                     if( transientCache( ) != newtransient ) setTransientCache( newtransient );
00143                 }
00144 
00145             } while ( !gotit );
00146         }
00147     }
00148     setCacheIsValid();  // flag the cach as being "valid"
00149 
00150   // Return whatever we have in teh cache (even if it's a null pointer).
00151 
00152     return transientCache( );
00153 }
00154 
00155 template< class T >
00156 void
00157 CdbBdbProxyBase<T>::storeHandler( IfdProxyDict* theDict,
00158                                   const IfdKey& theKey,
00159                                   AbsArg&       theArg,
00160                                   T*            theObject )
00161 {
00162     ErrMsg(warning) << "this is just a dummy method. It does nothing except printing this message." << endmsg;
00163 }
00164 
00165 template< class T >
00166 void
00167 CdbBdbProxyBase<T>::testCache( )
00168 {
00169     setCacheInvalid( );
00170 }
00171 
00172 template< class T >
00173 BdbTime
00174 CdbBdbProxyBase<T>::faultTime( ) const
00175 {
00176     assert( 0 != strategy( ));  // It's either a bug in the class's implementation or a memory
00177                                 // corruption problem. This pointer should never be the null one.
00178 
00179     return strategy( )->defaultKey( ).key( );    
00180 }
00181 
00182 template< class T >
00183 bool 
00184 CdbBdbProxyBase<T>::tryAnotherTime( const BdbTime&                         theOriginalTime, 
00185                                     const std::vector<CdbBdbProxyElement>& theListOfElements,
00186                                     BdbTime&                               TheOtherTime ) 
00187 {
00188     return false;
00189 }
00190 
00191 
00192 /////////////////////////////////////////
00193 // Class: CdbBdbProxyBaseUsingRevision //
00194 /////////////////////////////////////////
00195 
00196 template< class T >
00197 CdbBdbProxyBaseUsingRevision<T>::CdbBdbProxyBaseUsingRevision( const std::string&  theRevisionName,
00198                                                                unsigned int        thePartitionId,
00199                                                                BdbCondDefStrategy* theStrategy ) :
00200     CdbBdbProxyBase<T>( theStrategy ),
00201     _revisionName(theRevisionName),
00202     _partitionId (thePartitionId)
00203 { }
00204 
00205 template< class T >
00206 CdbBdbProxyBaseUsingRevision<T>::~CdbBdbProxyBaseUsingRevision( )
00207 { }
00208 
00209 template< class T >
00210 T*
00211 CdbBdbProxyBaseUsingRevision<T>::faultHandler( IfdProxyDict* theDict,
00212                                                const IfdKey& theKey,
00213                                                AbsArg&       theArg )
00214 {
00215   // Figure out what time to use...
00216 
00217     BdbTime validityTime( 0 );
00218     if( 0 != strategy( )) {
00219         validityTime = strategy( )->defaultKey( ).key( );
00220     } else {
00221         BdbTime* t = AbsArgCast< BdbTime >::value( theArg );
00222         if( 0 == t ) ErrMsg(fatal) << "unable to determine the validity time." << endmsg;
00223         validityTime = *t;
00224     }
00225 
00226   // Check if the persistent cach is still valid. If not then update it and
00227   // recalculate the transient.
00228 
00229     if( 0 == transientCache( ) || !isCacheValid( validityTime )) {
00230 
00231 
00232       // Update the persistent cache otherwise
00233       //
00234       // NOTE: We're using the artificially constructed value of the State Identifier
00235       //       as a temporary solution just because the GenEnv does not provide us with
00236       //       this information.
00237 
00238       // The subsequent code is being executed within a transaction provided
00239       // via an object of the CdbTransaction class, implementing
00240       // the "resource-acquisition-is-initialization" paradigm.
00241 
00242         {
00243             CdbTransaction transaction;
00244 
00245           // do it in the loop until complete success or failure
00246 
00247             std::vector<CdbBdbProxyElement> elements;
00248             bool gotit = false ;
00249             do {
00250 
00251               // the persisten cache needs to be updated
00252 
00253                 if( CdbStatus::Success != updateCache( validityTime,
00254                                                        _revisionName.c_str( ),
00255                                                        _partitionId,
00256                                                        elements )) {
00257 
00258                   // failure to access conditions db
00259 
00260                     ErrMsg(error) << "failure to access conditions information: no transient returned" << endmsg;
00261 
00262                     invalidateTransientCache( );
00263 
00264                     gotit = true;   // while it's not really true, this will stop the loop
00265 
00266                 } else {
00267 
00268                   // Let the actuall proxy to recalculate the transient, then update
00269                   // the local transient cache.
00270 
00271                     T* newtransient = this->redefinedFaultHandler( elements );
00272 
00273                     if ( 0 != newtransient ) {
00274 
00275                       // can stop at this point
00276 
00277                         gotit = true;
00278 
00279                     } else {
00280 
00281                       // can't make transient guy, try to fund different persistent guy.
00282 
00283                         BdbTime anotherTime;
00284                         if ( tryAnotherTime( validityTime,
00285                                              elements,
00286                                              anotherTime )) {
00287 
00288                           // rerun everything with the different time
00289 
00290                             validityTime = anotherTime;
00291 
00292                         } else {
00293 
00294                           // no, can't do it
00295 
00296                             gotit = true;
00297                         }
00298                     }
00299 
00300                   // Update the transient cache if got a new pointer
00301 
00302                     if( transientCache( ) != newtransient ) setTransientCache( newtransient );
00303                 }
00304 
00305             } while ( !gotit );
00306         }
00307     }
00308     setCacheIsValid();  // flag the cach as being "valid"
00309 
00310   // Return whatever we have in teh cache (even if it's a null pointer).
00311 
00312     return transientCache( );
00313 }
00314 
00315 /////////////////
00316 // End Of File //
00317 /////////////////

Generated on Mon Dec 5 18:22:00 2005 for CDB by doxygen1.3-rc3