CMS 3D CMS Logo

Public Member Functions | Private Attributes

ora::STLContainerReader Class Reference

#include <STLContainerStreamer.h>

Inheritance diagram for ora::STLContainerReader:
ora::IRelationalReader

List of all members.

Public Member Functions

bool build (DataElement &offset, IRelationalData &relationalData)
void clear ()
void read (void *address)
 Reads a data element.
void select (int oid)
void setRecordId (const std::vector< int > &identity)
 STLContainerReader (const Reflex::Type &objectType, MappingElement &mapping, ContainerSchema &contSchema)
 Constructor.
virtual ~STLContainerReader ()

Private Attributes

std::auto_ptr< IArrayHandlerm_arrayHandler
bool m_associative
std::auto_ptr< IRelationalReaderm_dataReader
std::auto_ptr< IRelationalReaderm_keyReader
DataElement m_localElement
MappingElementm_mappingElement
Reflex::Type m_objectType
DataElementm_offset
std::auto_ptr
< MultiRecordSelectOperation
m_query
std::vector< int > m_recordId
ContainerSchemam_schema

Detailed Description

Definition at line 79 of file STLContainerStreamer.h.


Constructor & Destructor Documentation

ora::STLContainerReader::STLContainerReader ( const Reflex::Type &  objectType,
MappingElement mapping,
ContainerSchema contSchema 
)

Constructor.

Definition at line 232 of file STLContainerStreamer.cc.

ora::STLContainerReader::~STLContainerReader ( ) [virtual]

Definition at line 248 of file STLContainerStreamer.cc.

                                          {
}

Member Function Documentation

bool ora::STLContainerReader::build ( DataElement offset,
IRelationalData relationalData 
) [virtual]

Implements ora::IRelationalReader.

Definition at line 251 of file STLContainerStreamer.cc.

References ora::ClassUtils::containerDataType(), ora::ClassUtils::containerKeyType(), ora::ClassUtils::containerValueType(), i, ora::ArrayHandlerFactory::newArrayHandler(), ora::RelationalStreamerFactory::newReader(), evf::evtn::offset(), ora::ClassUtils::resolvedType(), and ora::throwException().

                                                                        {
  m_localElement.clear();
  m_recordId.clear();
  // allocate for the index...
  m_recordId.push_back(0);

  RelationalStreamerFactory streamerFactory( m_schema );
  
  // first open the insert on the extra table...
  m_query.reset( new MultiRecordSelectOperation( m_mappingElement.tableName(), m_schema.storageSchema() ));

  m_query->addWhereId( m_mappingElement.pkColumn() );
  std::vector<std::string> recIdCols = m_mappingElement.recordIdColumns();
  for( size_t i=0; i<recIdCols.size(); i++ ){
    m_query->addId( recIdCols[ i ] );
    m_query->addOrderId( recIdCols[ i ] );
  }
  
  m_offset = &offset;

  m_arrayHandler.reset( ArrayHandlerFactory::newArrayHandler( m_objectType ) );

  Reflex::Type valueType;
  if ( m_associative ){

    Reflex::Type keyType = ClassUtils::containerKeyType( m_objectType );
    Reflex::Type keyResolvedType = ClassUtils::resolvedType(keyType);

    if ( ! keyType ||!keyResolvedType ) {
      throwException( "Missing dictionary information for the key type of the container \"" +
                      m_objectType.Name(Reflex::SCOPED) + "\"",
                      "STLContainerReader::build" );
    }

    std::string keyName = keyType.Name();
    // Retrieve the relevant mapping element
    MappingElement::iterator iMe = m_mappingElement.find( keyName );
    if ( iMe == m_mappingElement.end() ) {
      throwException( "Item for \"" + keyName + "\" not found in the mapping element",
                      "STLContainerReader::build" );
    }

    m_keyReader.reset( streamerFactory.newReader( keyResolvedType, iMe->second ) );
    m_keyReader->build( m_localElement, *m_query );
    
    valueType = ClassUtils::containerDataType(m_objectType);
  } else {
    valueType = ClassUtils::containerValueType(m_objectType);
  }

  Reflex::Type valueResolvedType = ClassUtils::resolvedType(valueType);
  // Check the component type
  if ( ! valueType ||!valueResolvedType ) {
    throwException( "Missing dictionary information for the content type of the container \"" +
                    m_objectType.Name(Reflex::SCOPED) + "\"",
                    "STLContainerReader::build" );
  }
  
  std::string valueName = valueType.Name();
  // Retrieve the relevant mapping element
  MappingElement::iterator iMe = m_mappingElement.find( valueName );
  if ( iMe == m_mappingElement.end() ) {
    throwException( "Item for \"" + valueName + "\" not found in the mapping element",
                    "STLContainerReader::build" );
  }

  m_dataReader.reset( streamerFactory.newReader( valueResolvedType, iMe->second ) );
  m_dataReader->build( m_localElement, *m_query );
  return true;
}
void ora::STLContainerReader::clear ( void  ) [virtual]

Implements ora::IRelationalReader.

Definition at line 424 of file STLContainerStreamer.cc.

                                 {
  if(m_query.get()) m_query->clear();
  if(m_keyReader.get()) m_keyReader->clear();
  if(m_dataReader.get()) m_dataReader->clear();
}
void ora::STLContainerReader::read ( void *  address) [virtual]

Reads a data element.

Implements ora::IRelationalReader.

Definition at line 343 of file STLContainerStreamer.cc.

References i, and ora::throwException().

                                                        {

  if(!m_offset){
    throwException("The streamer has not been built.",
                   "STLContainerReader::read");
  }

  void* address = m_offset->address( destinationData );

  const Reflex::Type& iteratorReturnType = m_arrayHandler->iteratorReturnType();
  U_Primitives primitiveStub;
  
  Reflex::Type keyType;
  Reflex::Member firstMember;
  Reflex::Member secondMember;
  if ( m_associative ) {
    keyType = m_objectType.TemplateArgumentAt(0);
    firstMember = iteratorReturnType.MemberByName( "first" );
    if ( ! firstMember ) {
      throwException("Could not retrieve the data member \"first\" of the class \"" +
                     iteratorReturnType.Name(Reflex::SCOPED) + "\"",
                     "STLContainerReader::read" );
    }
    secondMember = iteratorReturnType.MemberByName( "second" );
    if ( ! secondMember ) {
      throwException( "Could not retrieve the data member \"second\" of the class \"" +
                      iteratorReturnType.Name(Reflex::SCOPED) + "\"",
                      "STLContainerReader::read" );
    }
  }
  
  bool isElementFundamental = iteratorReturnType.IsFundamental();
  
  m_arrayHandler->clear( address );

  size_t cursorSize = m_query->selectionSize(m_recordId, m_recordId.size()-1);
  unsigned int i=0;
  while ( i< cursorSize ){

    m_recordId[m_recordId.size()-1] = (int)i;
    m_query->selectRow( m_recordId );

    // Create a new element for the array
    void* objectData = 0;
    if(isElementFundamental){
      objectData = &primitiveStub;
    } else {
      objectData = iteratorReturnType.Construct().Address();
    }

    void* componentData = objectData;
    void* keyData = 0;

    if ( keyType ) { // treat the key object first
      keyData = static_cast< char* >( objectData ) + firstMember.Offset();
      m_keyReader->setRecordId( m_recordId );
      m_keyReader->read( keyData );
      
      componentData = static_cast< char* >( objectData ) + secondMember.Offset();
    }
    m_dataReader->setRecordId( m_recordId );
    m_dataReader->read( componentData );

    size_t prevSize = m_arrayHandler->size( address );
    m_arrayHandler->appendNewElement( address, objectData );
    bool inserted = m_arrayHandler->size( address )>prevSize;
    if ( ! ( iteratorReturnType.IsFundamental() ) ) {
      iteratorReturnType.Destruct( objectData );
    }
    if ( !inserted ) {
      throwException( "Could not insert a new element in the array type \"" +
                      m_objectType.Name(Reflex::SCOPED) + "\"",
                      "STLContainerReader::read" );
    }
    ++i;
  }

  m_arrayHandler->finalize( address );

}
void ora::STLContainerReader::select ( int  oid) [virtual]

Implements ora::IRelationalReader.

Definition at line 322 of file STLContainerStreamer.cc.

References ora::throwException().

                                           {
  if(!m_query.get()){
    throwException("The streamer has not been built.",
                   "STLContainerReader::read");
  }
  coral::AttributeList& whereData = m_query->whereData();
  whereData[ m_mappingElement.pkColumn() ].data<int>() = oid;
  m_query->execute();
  if(m_keyReader.get()) m_keyReader->select( oid );
  m_dataReader->select( oid );
}
void ora::STLContainerReader::setRecordId ( const std::vector< int > &  identity) [virtual]

Implements ora::IRelationalReader.

Definition at line 334 of file STLContainerStreamer.cc.

References i.

                                                                       {
  m_recordId.clear();
  for(size_t i=0;i<identity.size();i++) {
    m_recordId.push_back( identity[i] );
  }
  // allocate the element for the index...
  m_recordId.push_back( 0 );
}

Member Data Documentation

Definition at line 110 of file STLContainerStreamer.h.

Definition at line 107 of file STLContainerStreamer.h.

Definition at line 112 of file STLContainerStreamer.h.

Definition at line 111 of file STLContainerStreamer.h.

Definition at line 104 of file STLContainerStreamer.h.

Definition at line 101 of file STLContainerStreamer.h.

Reflex::Type ora::STLContainerReader::m_objectType [private]

Definition at line 100 of file STLContainerStreamer.h.

Definition at line 108 of file STLContainerStreamer.h.

Definition at line 109 of file STLContainerStreamer.h.

std::vector<int> ora::STLContainerReader::m_recordId [private]

Definition at line 103 of file STLContainerStreamer.h.

Definition at line 102 of file STLContainerStreamer.h.