//## begin module%1.7%.codegen_version preserve=yes // Read the documentation to learn more about C++ code generator // versioning. //## end module%1.7%.codegen_version //## begin module%420720460243.cm preserve=no //## end module%420720460243.cm //## begin module%420720460243.cp preserve=no // C O P Y R I G H T N O T I C E // This material is confidential to ERG and may not be disclosed in whole // or in part to any third party nor used in any manner whatsoever other // than for the purposes expressly consented to by ERG in writing. // // This material is also copyright and may not be reproduced, stored in a // retrieval system or transmitted in any form or by any means in whole or // in part without the express written consent of ERG. //## end module%420720460243.cp //## Module: TransactionStream%420720460243; Pseudo Package body //## Subsystem: MASS::Dev::Tools::TxnTestManager::src%41F5A79001E4 //## Source file: Z:\MASS_Dev\Tools\TxnTestManager\src\TransactionStream.cpp //## begin module%420720460243.additionalIncludes preserve=no //## end module%420720460243.additionalIncludes //## begin module%420720460243.includes preserve=yes #pragma warn -com #include #pragma warn +com #include #pragma hdrstop //## end module%420720460243.includes // UdFileManifest #include "UdFileManifest.h" // TransactionStream #include "TransactionStream.h" //## begin module%420720460243.additionalDeclarations preserve=yes #if defined( WIN32 ) || defined( __BCPLUSPLUS__ ) || defined( __BORLANDC__ ) const char g_separator = '\\'; #else const char g_separator = '/'; #endif #include #include #include #include #include //## end module%420720460243.additionalDeclarations // Class TransactionStream //## Operation: TransactionStream%4207228700FB TransactionStream::TransactionStream (const std::string &folder, const std::string &batchPrefix, const std::string &batchSuffix, const bool &buildManifest, const std::string &manifestPrefix, const std::string &manifestSuffix, const std::string &pathmapTarget) //## begin TransactionStream::TransactionStream%4207228700FB.hasinit preserve=no : m_batchNumber(1), m_batchCount(0), m_batchPrefix(batchPrefix), m_batchSize(0), m_batchSuffix(batchSuffix), m_folder(folder), m_stream(0), m_manifest(0) //## end TransactionStream::TransactionStream%4207228700FB.hasinit //## begin TransactionStream::TransactionStream%4207228700FB.initialization preserve=yes //## end TransactionStream::TransactionStream%4207228700FB.initialization { //## begin TransactionStream::TransactionStream%4207228700FB.body preserve=yes if ( buildManifest ) { m_manifest = new UdFileManifest( folder, manifestPrefix, manifestSuffix, pathmapTarget ); } //## end TransactionStream::TransactionStream%4207228700FB.body } TransactionStream::~TransactionStream() { //## begin TransactionStream::~TransactionStream%420720460243_dest.body preserve=yes close(); if ( m_manifest ) { delete m_manifest; m_manifest = 0; } //## end TransactionStream::~TransactionStream%420720460243_dest.body } //## Other Operations (implementation) //## Operation: buildFileName%420821AD02EF std::string & TransactionStream::buildFileName (std::string &filename, const std::string &folder, const std::string &prefix, const std::string &suffix, const std::string &batchName, const unsigned &batchNumber) { //## begin TransactionStream::buildFileName%420821AD02EF.body preserve=yes static const int base = 62; static const char encoding[ base ] = "0123456789" "ABCDEFGHIJKLMNOPQRSTUVWXYZ" "abcdefghijklmnopqrstuvwxyz"; /** * TDateTime is in local time, and the DCE currently uses UTC. Therefore, * we use time() to get seconds since midnight in UTC, and use TDateTime * only to get msec. */ unsigned short hour; unsigned short minute; unsigned short second; unsigned short millisecond; struct stat statbuf; time_t now; char encodingTime[ 9 ]; /** * Do this until we have a filename, but no more than 10,000 iterations, * which should be a little over 10 seconds. */ for ( int safetyLimit = 10000; safetyLimit; --safetyLimit ) { TDateTime::CurrentDateTime().DecodeTime( &hour, &minute, &second, &millisecond ); time( &now ); encodingTime[ 6 ] = encoding[ millisecond % base ]; millisecond /= base; encodingTime[ 5 ] = encoding[ millisecond % base ]; encodingTime[ 4 ] = encoding[ now % base ]; now /= base; encodingTime[ 3 ] = encoding[ now % base ]; now /= base; encodingTime[ 2 ] = encoding[ now % base ]; now /= base; encodingTime[ 1 ] = encoding[ now % base ]; now /= base; encodingTime[ 0 ] = encoding[ now % base ]; for ( int counter=0; counter < base; ++counter ) { encodingTime[ 7 ] = encoding[ counter ]; encodingTime[ 8 ] = 0; std::stringstream name; if ( folder.length() ) { name << folder; if ( folder[ folder.length() - 1 ] != g_separator ) { name << g_separator; } } if ( prefix.length() ) { name << prefix; } name << encodingTime; if ( batchName.length() ) { name << '_' << batchName << '_' << std::setw( 4 ) << std::setfill( '0' ) << std::right << batchNumber; } if ( suffix.length() ) { name << suffix; } filename = name.str(); if ( stat( filename.c_str(), &statbuf ) == -1 ) { return ( filename ); } } Sleep( 1 ); } MTHROW( std::runtime_error, \ "Cannot build a filename that is not already in use in \"" \ << folder \ << "\" with prefix \"" \ << prefix \ << "\" and suffix \"" \ << suffix \ << "\"." ); //## end TransactionStream::buildFileName%420821AD02EF.body } //## Operation: close%420819C203E4 void TransactionStream::close () { //## begin TransactionStream::close%420819C203E4.body preserve=yes if ( m_stream ) { m_stream->close(); delete m_stream; m_stream = 0; } //## end TransactionStream::close%420819C203E4.body } //## Operation: incrementCount%420723C60224 void TransactionStream::incrementCount () { //## begin TransactionStream::incrementCount%420723C60224.body preserve=yes /** * When we have a batch size (and so we batch), then we may need to * start a new batch. */ if ( m_batchSize ) { if ( ++m_batchCount >= m_batchSize ) { close(); m_batchCount = 0; ++m_batchNumber; open(); } } //## end TransactionStream::incrementCount%420723C60224.body } //## Operation: newBatch%420722B50215 const bool TransactionStream::newBatch (const unsigned &size, const std::string &name) { //## begin TransactionStream::newBatch%420722B50215.body preserve=yes m_batchSize = size; m_batchCount = 0; m_batchName = name; return ( open() ); //## end TransactionStream::newBatch%420722B50215.body } //## Operation: open%420819AE03C4 const bool TransactionStream::open () { //## begin TransactionStream::open%420819AE03C4.body preserve=yes close(); // Close the stream should it be open. std::string filename; buildFileName( filename, m_folder, m_batchPrefix, m_batchSuffix, m_batchName, m_batchNumber ); m_stream = new std::ofstream( filename.c_str(), std::ios_base::binary | std::ios_base::out ); if ( m_stream->is_open() ) { if ( m_manifest ) { m_manifest->addUdFile( filename ); } return ( true ); } // When we can't open the file, then roll back. delete m_stream; m_stream = 0; MERROR( "Cannot open \"" << filename << "\" for writing." ); return ( false ); //## end TransactionStream::open%420819AE03C4.body } //## Operation: write%4207231D014A const bool TransactionStream::write (const void *buffer, const unsigned &length) { //## begin TransactionStream::write%4207231D014A.body preserve=yes if ( m_stream ) { m_stream->write( reinterpret_cast< const char * >( buffer ), length ); if ( m_stream->good() ) { return ( true ); } else { MERROR( "Cannot write " << length << " byte(s) to stream." ); } } else { MERROR( "Cannot write to stream because it is not open." ); } return ( false ); //## end TransactionStream::write%4207231D014A.body } // Additional Declarations //## begin TransactionStream%420720460243.declarations preserve=yes //## end TransactionStream%420720460243.declarations //## begin module%420720460243.epilog preserve=yes //## end module%420720460243.epilog