Index Source Files Annotated Class List Alphabetical Class List Class Hierarchy Graphical Class Hierarchy

# MySQLLog.cpp

Go to the documentation of this file.

    00001 /****************************************************************************
    00002 ** Copyright (c) quickfixengine.org  All rights reserved.
    00003 **
    00004 ** This file is part of the QuickFIX FIX Engine
    00005 **
    00006 ** This file may be distributed under the terms of the quickfixengine.org
    00007 ** license as defined by quickfixengine.org and appearing in the file
    00008 ** LICENSE included in the packaging of this file.
    00009 **
    00010 ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
    00011 ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
    00012 **
    00013 ** See http://www.quickfixengine.org/LICENSE for licensing information.
    00014 **
    00015 ** Contact ask@quickfixengine.org if any conditions of this licensing are
    00016 ** not clear to you.
    00017 **
    00018 ****************************************************************************/
    00019
    00020 #ifdef _MSC_VER
    00021 #include "stdafx.h"
    00022 #else
    00023 #include "config.h"
    00024 #endif
    00025 #include "CallStack.h"
    00026
    00027 #ifdef HAVE_MYSQL
    00028
    00029 #include "MySQLLog.h"
    00030 #include "SessionID.h"
    00031 #include "SessionSettings.h"
    00032 #include "Utility.h"
    00033 #include "strptime.h"
    00034 #include <fstream>
    00035
    00036 namespace FIX
    00037 {
    00038
    00039 const std::string MySQLLogFactory::DEFAULT_DATABASE = "quickfix";
    00040 const std::string MySQLLogFactory::DEFAULT_USER = "root";
    00041 const std::string MySQLLogFactory::DEFAULT_PASSWORD = "";
    00042 const std::string MySQLLogFactory::DEFAULT_HOST = "localhost";
    00043 const short MySQLLogFactory::DEFAULT_PORT = 0;
    00044
    00045 MySQLLog::MySQLLog
    00046 ( const SessionID& s, const DatabaseConnectionID& d, MySQLConnectionPool* p )
    00047 : m_pConnectionPool( p )
    00048 {
    00049   init();
    00050   m_pSessionID = new SessionID( s );
    00051   m_pConnection = m_pConnectionPool->create( d );
    00052 }
    00053
    00054 MySQLLog::MySQLLog
    00055 ( const DatabaseConnectionID& d, MySQLConnectionPool* p )
    00056 : m_pConnectionPool( p ), m_pSessionID( 0 )
    00057 {
    00058   init();
    00059   m_pConnection = m_pConnectionPool->create( d );
    00060 }
    00061
    00062 MySQLLog::MySQLLog
    00063 ( const SessionID& s, const std::string& database, const std::string& user,
    00064   const std::string& password, const std::string& host, short port )
    00065   : m_pConnectionPool( 0 )
    00066 {
    00067   init();
    00068   m_pSessionID = new SessionID( s );
    00069   m_pConnection = new MySQLConnection( database, user, password, host, port );
    00070 }
    00071
    00072 MySQLLog::MySQLLog
    00073 ( const std::string& database, const std::string& user,
    00074   const std::string& password, const std::string& host, short port )
    00075   : m_pConnectionPool( 0 ), m_pSessionID( 0 )
    00076 {
    00077   m_pConnection = new MySQLConnection( database, user, password, host, port );
    00078 }
    00079
    00080 void MySQLLog::init()
    00081 {
    00082   setIncomingTable( "messages_log" );
    00083   setOutgoingTable( "messages_log" );
    00084   setEventTable( "event_log" );
    00085 }
    00086
    00087 MySQLLog::~MySQLLog()
    00088 {
    00089   if( m_pConnectionPool )
    00090     m_pConnectionPool->destroy( m_pConnection );
    00091   else
    00092     delete m_pConnection;
    00093   delete m_pSessionID;
    00094 }
    00095
    00096 Log* MySQLLogFactory::create()
    00097 { QF_STACK_PUSH(MySQLLogFactory::create)
    00098
    00099   std::string database;
    00100   std::string user;
    00101   std::string password;
    00102   std::string host;
    00103   short port;
    00104
    00105   init( m_settings.get(), database, user, password, host, port );
    00106   DatabaseConnectionID id( database, user, password, host, port );
    00107   MySQLLog* result = new MySQLLog( id, m_connectionPoolPtr.get() );
    00108   initLog( m_settings.get(), *result );
    00109   return result;
    00110
    00111   QF_STACK_POP
    00112 }
    00113
    00114 Log* MySQLLogFactory::create( const SessionID& s )
    00115 { QF_STACK_PUSH(MySQLLogFactory::create)
    00116
    00117   std::string database;
    00118   std::string user;
    00119   std::string password;
    00120   std::string host;
    00121   short port;
    00122
    00123   Dictionary settings;
    00124   if( m_settings.has(s) )
    00125           settings = m_settings.get( s );
    00126
    00127   init( settings, database, user, password, host, port );
    00128   DatabaseConnectionID id( database, user, password, host, port );
    00129   MySQLLog* result = new MySQLLog( s, id, m_connectionPoolPtr.get() );
    00130   initLog( settings, *result );
    00131   return result;
    00132
    00133   QF_STACK_POP
    00134 }
    00135
    00136 void MySQLLogFactory::init( const Dictionary& settings,
    00137                             std::string& database,
    00138                             std::string& user,
    00139                             std::string& password,
    00140                             std::string& host,
    00141                             short &port )
    00142 { QF_STACK_PUSH(MySQLLogFactory::init)
    00143
    00144   database = DEFAULT_DATABASE;
    00145   user = DEFAULT_USER;
    00146   password = DEFAULT_PASSWORD;
    00147   host = DEFAULT_HOST;
    00148   port = DEFAULT_PORT;
    00149
    00150   if( m_useSettings )
    00151   {
    00152     try { database = settings.getString( MYSQL_LOG_DATABASE ); }
    00153     catch( ConfigError& ) {}
    00154
    00155     try { user = settings.getString( MYSQL_LOG_USER ); }
    00156     catch( ConfigError& ) {}
    00157
    00158     try { password = settings.getString( MYSQL_LOG_PASSWORD ); }
    00159     catch( ConfigError& ) {}
    00160
    00161     try { host = settings.getString( MYSQL_LOG_HOST ); }
    00162     catch( ConfigError& ) {}
    00163
    00164     try { port = ( short ) settings.getLong( MYSQL_LOG_PORT ); }
    00165     catch( ConfigError& ) {}
    00166   }
    00167   else
    00168   {
    00169     database = m_database;
    00170     user = m_user;
    00171     password = m_password;
    00172     host = m_host;
    00173     port = m_port;
    00174   }
    00175
    00176   QF_STACK_POP
    00177 }
    00178
    00179 void MySQLLogFactory::initLog( const Dictionary& settings, MySQLLog& log )
    00180 {
    00181     try { log.setIncomingTable( settings.getString( MYSQL_LOG_INCOMING_TABLE ) ); }
    00182     catch( ConfigError& ) {}
    00183
    00184     try { log.setOutgoingTable( settings.getString( MYSQL_LOG_OUTGOING_TABLE ) ); }
    00185     catch( ConfigError& ) {}
    00186
    00187     try { log.setEventTable( settings.getString( MYSQL_LOG_EVENT_TABLE ) ); }
    00188     catch( ConfigError& ) {}
    00189 }
    00190
    00191 void MySQLLogFactory::destroy( Log* pLog )
    00192 { QF_STACK_PUSH(MySQLLogFactory::destroy)
    00193   delete pLog;
    00194   QF_STACK_POP
    00195 }
    00196
    00197 void MySQLLog::clear()
    00198 { QF_STACK_PUSH(MySQLLog::clear)
    00199
    00200   std::stringstream whereClause;
    00201
    00202   whereClause << "WHERE ";
    00203
    00204   if( m_pSessionID )
    00205   {
    00206     whereClause
    00207     << "BeginString = \"" << m_pSessionID->getBeginString().getValue() << "\" "
    00208     << "AND SenderCompID = \"" << m_pSessionID->getSenderCompID().getValue() << "\" "
    00209     << "AND TargetCompID = \"" << m_pSessionID->getTargetCompID().getValue() << "\" ";
    00210
    00211     if( m_pSessionID->getSessionQualifier().size() )
    00212       whereClause << "AND SessionQualifier = \"" << m_pSessionID->getSessionQualifier() << "\"";
    00213   }
    00214   else
    00215   {
    00216     whereClause << "BeginString = NULL AND SenderCompID = NULL && TargetCompID = NULL";
    00217   }
    00218
    00219   std::stringstream incomingQuery;
    00220   std::stringstream outgoingQuery;
    00221   std::stringstream eventQuery;
    00222
    00223   incomingQuery
    00224     << "DELETE FROM " << m_incomingTable << " " << whereClause.str();
    00225   outgoingQuery
    00226     << "DELETE FROM " << m_outgoingTable << " " << whereClause.str();
    00227   eventQuery
    00228     << "DELETE FROM " << m_eventTable << " " << whereClause.str();
    00229
    00230   MySQLQuery incoming( incomingQuery.str() );
    00231   MySQLQuery outgoing( outgoingQuery.str() );
    00232   MySQLQuery event( eventQuery.str() );
    00233   m_pConnection->execute( incoming );
    00234   m_pConnection->execute( outgoing );
    00235   m_pConnection->execute( event );
    00236
    00237   QF_STACK_POP
    00238 }
    00239
    00240 void MySQLLog::backup()
    00241 { QF_STACK_PUSH(MySQLLog::backup)
    00242   QF_STACK_POP
    00243 }
    00244
    00245 void MySQLLog::insert( const std::string& table, const std::string value )
    00246 { QF_STACK_PUSH(MySQLLog::insert)
    00247
    00248   UtcTimeStamp time;
    00249   int year, month, day, hour, minute, second, millis;
    00250   time.getYMD( year, month, day );
    00251   time.getHMS( hour, minute, second, millis );
    00252
    00253   char sqlTime[ 20 ];
    00254   STRING_SPRINTF( sqlTime, "%d-%02d-%02d %02d:%02d:%02d",
    00255            year, month, day, hour, minute, second );
    00256
    00257   char* valueCopy = new char[ (value.size() * 2) + 1 ];
    00258   mysql_escape_string( valueCopy, value.c_str(), value.size() );
    00259
    00260   std::stringstream queryString;
    00261   queryString << "INSERT INTO " << table << " "
    00262   << "(time, time_milliseconds, beginstring, sendercompid, targetcompid, session_qualifier, text) "
    00263   << "VALUES ("
    00264   << "'" << sqlTime << "','" << millis << "',";
    00265
    00266   if( m_pSessionID )
    00267   {
    00268     queryString
    00269     << "\"" << m_pSessionID->getBeginString().getValue() << "\","
    00270     << "\"" << m_pSessionID->getSenderCompID().getValue() << "\","
    00271     << "\"" << m_pSessionID->getTargetCompID().getValue() << "\",";
    00272     if( m_pSessionID->getSessionQualifier() == "" )
    00273       queryString << "NULL" << ",";
    00274     else
    00275       queryString << "\"" << m_pSessionID->getSessionQualifier() << "\",";
    00276   }
    00277   else
    00278   {
    00279     queryString << "NULL, NULL, NULL, NULL, ";
    00280   }
    00281
    00282   queryString << "\"" << valueCopy << "\")";
    00283   delete [] valueCopy;
    00284
    00285   MySQLQuery query( queryString.str() );
    00286   m_pConnection->execute( query );
    00287
    00288   QF_STACK_POP
    00289 }
    00290
    00291 } //namespace FIX
    00292
    00293 #endif //HAVE_MYSQL