00001
00002
00003
00004
00005
00006
00007
00008
00009 #include "BaBar/BaBar.hh"
00010
00011 #include "CdbBdbShared/CdbBdbSCollectionP.hh"
00012
00013 #include "CdbBdbShared/CdbBdbSCollectionElementP.hh"
00014 #include "CdbBdbShared/CdbBdbSCollectionIdItr.hh"
00015 #include "CdbBdbShared/CdbBdbSCollectionNameItr.hh"
00016
00017 #include <assert.h>
00018 using std::cout;
00019 using std::endl;
00020 using std::ostream;
00021
00022 CdbBdbSCollectionP::CdbBdbSCollectionP( bool useIdFlag,
00023 bool useNameFlag ) :
00024 _treeRef(0),
00025 _mapRef(0),
00026 _elements(0)
00027 {
00028 assert( useIdFlag || useNameFlag );
00029
00030
00031 if( useIdFlag ) _treeRef = new( ooThis( )) BTreeP( );
00032 if( useNameFlag ) _mapRef = new( ooThis( )) BdbMap( );
00033 }
00034
00035 CdbBdbSCollectionP::~CdbBdbSCollectionP( )
00036 {
00037
00038
00039
00040
00041
00042
00043 if( ! BdbIsNull( _treeRef )) {
00044
00045 CdbItr< BTreeEntry > itr = _treeRef->iterator( );
00046 while( itr.next( )) {
00047 BTreeEntry e = itr.value( );
00048 BdbDelete( e.value );
00049 }
00050
00051 } else {
00052
00053 assert( ! BdbIsNull(_mapRef));
00054
00055 ooMapItr itr( _mapRef );
00056 while( itr.next( )) {
00057 BdbRef( CdbBdbSCollectionElementP ) eRef;
00058 eRef = (const BdbRef( CdbBdbSCollectionElementP )&) (itr->oid( ));
00059 BdbDelete( eRef );
00060 }
00061 }
00062
00063
00064
00065 if( ! BdbIsNull( _treeRef )) BdbDelete( _treeRef );
00066 if( ! BdbIsNull( _mapRef )) BdbDelete( _mapRef );
00067 }
00068
00069 bool
00070 CdbBdbSCollectionP::useId( ) const
00071 {
00072 return ! BdbIsNull( _treeRef );
00073 }
00074
00075 bool
00076 CdbBdbSCollectionP::useName( ) const
00077 {
00078 return ! BdbIsNull( _mapRef );
00079 }
00080
00081 d_ULong
00082 CdbBdbSCollectionP::elements( ) const
00083 {
00084 return _elements;
00085 }
00086
00087 CdbStatus
00088 CdbBdbSCollectionP::insert( const BdbRef( CdbBdbSCollectionElementP )& theRef )
00089 {
00090 const char* errorStr = "CdbBdbSCollectionP::insert() -- ERROR";
00091
00092 ooUpdate( );
00093
00094 CdbStatus result = CdbStatus::Error;
00095 do {
00096
00097
00098
00099 if( ! verifyElement( theRef )) {
00100 cout << errorStr << endl
00101 << " The specified object has not passed the general verification." << endl;
00102 break;
00103 }
00104
00105
00106
00107
00108 ooVString name = theRef->name( );
00109
00110 if( useName( )) {
00111 if( _mapRef->isMember( name.head( ))) {
00112 cout << errorStr << endl
00113 << " The collection already has an element with such name." << endl
00114 << " Passed element name: " << name.head( ) << endl;
00115 break;
00116 }
00117 }
00118
00119
00120
00121 BTreeEntry newEntry( theRef->id( ), theRef );
00122
00123 if( useId( )) {
00124 if( _treeRef->search( newEntry )) {
00125 cout << errorStr << endl
00126 << " The collection already has an element with such identifier." << endl
00127 << " Passed element identifier: " << newEntry.key << endl;
00128 break;
00129 }
00130 }
00131
00132
00133
00134 if( useName( )) {
00135 if( BdbcSuccess != _mapRef->add( name.head( ), theRef )) {
00136 cout << errorStr << endl
00137 << " Failed to insert new element into the collection's persistent map" << endl
00138 << " Passed element name: " << name.head( ) << endl
00139 << " identifier: " << newEntry.key << endl;
00140 break;
00141 }
00142 }
00143 if( useId( )) {
00144 _treeRef->insert( newEntry );
00145 }
00146
00147 ++_elements;
00148
00149
00150
00151 result = CdbStatus::Success;
00152
00153 } while( false );
00154
00155 return result;
00156 }
00157
00158 CdbStatus
00159 CdbBdbSCollectionP::find( const char* theName,
00160 BdbRef( CdbBdbSCollectionElementP )& theRef ) const
00161 {
00162
00163
00164 if( ! useName( )) {
00165 assert(0);
00166 return CdbStatus::Error;
00167 }
00168
00169
00170
00171 const char* errorStr = "CdbBdbSCollectionP::find(name) -- ERROR";
00172 const char* fatalStr = "CdbBdbSCollectionP::find(name) -- FATAL ERROR";
00173
00174 CdbStatus result = CdbStatus::Error;
00175 do {
00176
00177
00178
00179 if( 0 == theName ) {
00180 cout << errorStr << endl
00181 << " Invalid name passed to the procedure." << endl;
00182 break;
00183 }
00184
00185
00186
00187 BdbRef(BdbPersObj) oRef;
00188
00189 if( BdbcSuccess != _mapRef->lookup( theName, oRef )) {
00190 result = CdbStatus::NotFound;
00191 break;
00192 }
00193
00194
00195
00196 if( BdbIsNull(oRef) ||
00197 ! oRef.isValid( ) ||
00198 ! oRef->ooIsKindOf( ooTypeN( CdbBdbSCollectionElementP ))) {
00199
00200 cout << fatalStr << endl
00201 << " INCONSISTENT COLLECTION OR INAPPROPRIATE TYPE" << endl
00202 << " PASSED AS THE TEMPLATE PARAMETER." << endl;
00203
00204 assert(0);
00205
00206 break;
00207 }
00208 theRef = (const BdbRef( CdbBdbSCollectionElementP )&) oRef;
00209
00210
00211
00212 result = CdbStatus::Success;
00213
00214 } while( false );
00215
00216 return result;
00217 }
00218
00219 CdbStatus
00220 CdbBdbSCollectionP::find( d_UShort theId,
00221 BdbRef( CdbBdbSCollectionElementP )& theRef ) const
00222 {
00223
00224
00225 if( ! useId( )) {
00226 assert(0);
00227 return CdbStatus::Error;
00228 }
00229
00230
00231
00232 const char* fatalStr = "CdbBdbSCollectionP::find(id) -- FATAL ERROR";
00233
00234 CdbStatus result = CdbStatus::Error;
00235 do {
00236
00237
00238
00239 BTreeEntry foundEntry;
00240
00241 if( ! _treeRef->search( BTreeEntry( theId ), foundEntry )) {
00242 result = CdbStatus::NotFound;
00243 break;
00244 }
00245 BdbRef( CdbBdbSCollectionElementP ) oRef = foundEntry.value;
00246
00247
00248
00249 if( BdbIsNull(oRef) ||
00250 ! oRef.isValid( ) ||
00251 ! oRef->ooIsKindOf( ooTypeN( CdbBdbSCollectionElementP ))) {
00252
00253 cout << fatalStr << endl
00254 << " INCONSISTENT COLLECTION OR INAPPROPRIATE TYPE" << endl
00255 << " PASSED AS THE TEMPLATE PARAMETER." << endl;
00256
00257 assert(0);
00258
00259 break;
00260 }
00261 theRef = oRef;
00262
00263
00264
00265 result = CdbStatus::Success;
00266
00267 } while( false );
00268
00269 return result;
00270 }
00271
00272 CdbStatus
00273 CdbBdbSCollectionP::remove( const char* theName )
00274 {
00275
00276
00277 if( ! useName( )) {
00278 assert(0);
00279 return CdbStatus::Error;
00280 }
00281
00282
00283
00284 ooUpdate( );
00285
00286 BdbRef( CdbBdbSCollectionElementP ) pRef;
00287
00288 CdbStatus result = find( theName, pRef );
00289 if( CdbStatus::Success == result ) {
00290
00291 if( useId( )) _treeRef->remove( BTreeEntry( pRef->id( )));
00292 _mapRef->remove( theName );
00293
00294 BdbDelete( pRef );
00295
00296 --_elements;
00297 }
00298
00299 return result;
00300 }
00301
00302 CdbStatus
00303 CdbBdbSCollectionP::remove( d_UShort theId )
00304 {
00305
00306
00307 if( ! useId( )) {
00308 assert(0);
00309 return CdbStatus::Error;
00310 }
00311
00312
00313
00314 ooUpdate( );
00315
00316 BdbRef( CdbBdbSCollectionElementP ) pRef;
00317
00318 CdbStatus result = find( theId, pRef );
00319 if( CdbStatus::Success == result ) {
00320
00321 _treeRef->remove( BTreeEntry( theId ));
00322 if( useName( )) _mapRef->remove( pRef->name( ));
00323
00324 BdbDelete( pRef );
00325
00326 --_elements;
00327 }
00328
00329 return result;
00330 }
00331
00332 CdbBdbSCollectionP::IteratorOfNames
00333 CdbBdbSCollectionP::iterator_names( ) const
00334 {
00335
00336
00337 if( ! useName( )) {
00338 assert(0);
00339 return IteratorOfNames( 0 );
00340 }
00341
00342
00343
00344
00345 return IteratorOfNames( new CdbBdbSCollectionNameItr( _mapRef ));
00346 }
00347
00348 CdbBdbSCollectionP::IteratorOfIdentifiers
00349 CdbBdbSCollectionP::iterator_identifiers( ) const
00350 {
00351
00352
00353 if( ! useId( )) {
00354 assert(0);
00355 return IteratorOfIdentifiers( 0 );
00356 }
00357
00358
00359
00360
00361 return IteratorOfIdentifiers( new CdbBdbSCollectionIdItr( _treeRef->iterator( )));
00362 }
00363
00364
00365 void
00366 CdbBdbSCollectionP::dump( ostream& o ) const
00367 {
00368 if( useName( )) {
00369
00370 o << "====================================" << endl
00371 << "== ELEMENTS SORTED BY THEIR NAMES ==" << endl
00372 << "====================================" << endl
00373 << endl;
00374
00375 d_ULong num = 0;
00376
00377 IteratorOfNames itr = iterator_names( );
00378 while( itr.next( )) {
00379
00380 BdbRef( CdbBdbSCollectionElementP ) pRef;
00381 if( CdbStatus::Success != find( itr.value( ), pRef )) {
00382 o << "%%% ERROR : ELEMENT WITH NAME: \"" << itr.value( ) << "\" NOT FOUND %%%" << endl;
00383 } else {
00384 o << "\"" << pRef->name( ) << "\"" << endl;
00385 ++num;
00386 }
00387 o << endl;
00388 }
00389
00390 o << "== TOTAL OF " << num << "/" << elements( ) << " ELEMENTS WERE FOUND ==" << endl
00391 << endl;
00392 }
00393
00394 if( useId( )) {
00395
00396 o << "==========================================" << endl
00397 << "== ELEMENTS SORTED BY THEIR IDENTIFIERS ==" << endl
00398 << "==========================================" << endl
00399 << endl;
00400
00401 d_ULong num = 0;
00402
00403 IteratorOfIdentifiers itr = iterator_identifiers( );
00404 while( itr.next( )) {
00405
00406 BdbRef( CdbBdbSCollectionElementP ) pRef;
00407 if( CdbStatus::Success != find( itr.value( ), pRef )) {
00408 o << "%%% ERROR : ELEMENT WITH ID: " << itr.value( ) << " NOT FOUND %%%" << endl;
00409 } else {
00410 o << pRef->id( ) << endl;
00411 ++num;
00412 }
00413 o << endl;
00414 }
00415
00416 o << "== TOTAL OF " << num << "/" << elements( ) << " ELEMENTS WERE FOUND ==" << endl;
00417 }
00418 }
00419
00420 bool
00421 CdbBdbSCollectionP::verifyElement( const BdbRef( CdbBdbSCollectionElementP )& theRef ) const
00422 {
00423 const char* errorStr = "CdbBdbSCollectionP::verifyElement() -- ERROR";
00424
00425 bool result = false;
00426 do {
00427
00428 if( BdbIsNull( theRef )) {
00429 cout << errorStr << endl
00430 << " The 0-0-0-0 reference passed where the persistent object" << endl
00431 << " of type " << ooTypeN( CdbBdbSCollectionElementP ) << " was expected." << endl;
00432 break;
00433 }
00434 if( ! theRef.isValid( )) {
00435 cout << errorStr << endl
00436 << " Non-valid reference passed where the persistent object" << endl
00437 << " of type " << ooTypeN( CdbBdbSCollectionElementP ) << " was expected." << endl;
00438 break;
00439 }
00440 if( ! theRef->ooIsKindOf( ooTypeN( CdbBdbSCollectionElementP ))) {
00441 cout << errorStr << endl
00442 << " An object of an incompatible or inappropriate persistent type passed" << endl
00443 << " to the collection." << endl
00444 << " Passed object's type number: " << theRef->ooGetTypeN( ) << endl
00445 << " Expected type number: " << ooTypeN( CdbBdbSCollectionElementP ) << endl;
00446 break;
00447 }
00448
00449
00450
00451
00452 if( useName( )) {
00453 if( 0 == theRef->name( ).length( )) {
00454 cout << errorStr << endl
00455 << " The passed object does not have a valid name." << endl;
00456 break;
00457 }
00458 }
00459
00460 result = true;
00461
00462 } while( false );
00463
00464 return result;
00465 }
00466
00467
00468
00469