B2BITS FIX Antenna C++ 2.32.1
|
Customization is required when changes that are to be made do not fit into the user defined fields approach (see User defined fields). For example:
FIX Antenna adopts the notion of "additional fields" to create FIX dialects. The configuration parameter can be used to customize the standard FIX version.
Protocol ID / Parser Name | XML File |
FIX40 | fixdic40.xml |
FIX41 | fixdic41.xml |
FIX42 | fixdic42.xml |
FIX43 | fixdic43.xml |
FIX44 | fixdic44.xml |
FIX50 | fixdic50.xml |
FIX50SP1 | fixdic50sp1.xml |
FIX50SP2 | fixdic50sp2.xml |
FIXLatest | fixdiclatest.xml |
Perform dictionaries configuration in engine.properties file before starting application.
It is also possible to load additional dictionaries customizations in runtime.
The protocol customization is specified in a separate XML file. There are two types of protocol updates:
To perform update of the exiting protocol, the id
of the fixdic
field must be set to id of protocol you want to change. The example of FIX Dialect:
This example will update the FIX 4.3 protocol message Order Cancel Request (F) with a new non-required repeating group NoLegs (555)
To create a new FIX dialect, set parent_id
property to base protocol id and id
to new dialect id. Note, that id
value must be unique for FIX Antenna instance
The example of FIX Dialect:
Call one of the methods below to create a session:
To create session based on one of default protocols, it is enough to pass Engine::FixVersion
to ver
parameter of FixEngine::createSession
function. FIXAntenna will automatically convert FixVersion
to appropriate ParserID
. But for creating session based on a custom FIX dialect, it is needed to convert string name of a protocol to an internal ParserID handle:
The example below shows how to create both kinds of sessions:
Refer to the section FIX Session for additional information about sessions.
The sample below illustrates all abovementioned instructions combined in one application.
engine.properties
# # The FIX Engine configuration file. # # $Revision: 1.6 $ # # For UNIX platforms, the filename-separator character is "/". # For Win32 platforms, the filename-separator character is "//" or "/". # The top of the directory tree under which the engine's configuration, # and log files are kept. # # Do NOT add a slash at the end of the directory path. EngineRoot = . # Engine's listen port. Must be > 0. ListenPort = 9021 # Engine's local IP address to bind to. It can be used on a multi-homed host # for a FIX Engine that will only accept connect requests to one of its addresses. # If this parameter is commented, the engine will accept connections to any/all # local addresses. # ListenAddress = localhost # Engine's local IP address to send from. It can be used on a multi-homed host # for a FIX Engine that will only send IP datagrams from one of its addresses. # If this parameter is commented, the engine will send IP datagrams from any/all # local addresses. # ConnectAddress = localhost # Number of threads that serve FIX sessions. # # Changing this value will impact upon the performance of FIX Engine. # The recommended value is 10. The value must be integer and greater than zero. NumberOfWorkers = 10 # This property is the path of the directory in which the logs for all incoming # (if LogIncomingMessages is set to "true") and outgoing FIX messages are stored. # It is possible to specify a path related to the EngineRoot directory or an absolute path. # For example if LogDirectory is set to /"logs/" then the real path is $(EngineRoot)/logs. # The specified directory must exist. LogDirectory = logs # This property provides an option to log incoming FIX messages (those received) from # a counterparty FIX Engine. They will be stored in the directory specified by # the LogDirectory parameter in a file with extension "in". LogIncomingMessages = false # This parameter sets the time period after which a session is non-gracefully terminated # if a response is not received to a first "Logon" message (message type A). # The corresponding Logout message is sent to the counterparty. # This value is in seconds. # The recommended value is 30 seconds for dedicated connections or private networks. # Trading connections via the internet will require calibration. # If it is set to "0", then the time period is unlimited. # The value must be integer and not negative. LogonTimeFrame = 30 # This parameter sets the time period after which a session is automatically terminated # if a response is not received to a "Logout message" (message type 5). # This value is in seconds. # The recommended value is 10 seconds for dedicated connections or private networks. # Trading connections via the internet will require calibration. # The value must be integer and greater than 0. LogoutTimeFrame = 10 # An option not to reset sequence numbers after Logout. # Logout sender should initiate session recovery by sending Logon message # with SeqNum = <last outgoing SeqNum> + 1; # expecting reply Logon with SeqNum = <last incoming SeqNum> + 1. # If a gap is detected, standard message recovery or gap filling process # takes place. IntradayLogoutTolerance = true # This parameter controls existance of required tags in application level messages. # The possible values are "true" and "false". If set to "true" then all application # level messages are validated. If set to "false" then the responsibility for message validity # rests with the counterparty. Please note that session level messages are validated in # all cases. The recommended setting is "true". MessageMustBeValidated = false # This parameter specifies the delta (increment) to the Heartbeat interval between # a TestRequest message being sent by FIX Engine and a Response Heartbeat being received. # The session attains a "telecommunication failed state" if no Response Heartbeat message # is received after the normal Heartbeat interval plus delta. For example if no message # (application or session level) is received during the Heartbeat interval then Engine sends # a TestRequest message. If the required Response Heartbeat message is not received during # Heartbeat interval plus Delta then the session moves to the state "Telecommunication link # failed". This parameter is specified in (Heartbeat Interval/100). The recommended value is # twenty percent. ReasonableTransmissionTime = 20 # FIX Engine has inbuilt FIX message routing capability and fully supports # the "Deliver To On Behalf Of" mechanism as specified by the FIX protocol. # If this parameter is set to "True" then Engine will redirect FIX messages automatically # to other FIX sessions it maintains. # If this parameter is set to "False" Engine directs all messages received to the client # application. ThirdPartyRoutingIsEnabled = false # This parameter provides an option whereby FIX Engine will accept a FIX session for which it # has no registered application (an acceptor). If set to "true" Engine establishes a session, # all application level messages are rejected (Application Level Reject - type 3). When # an application is registered behaviour is as standard. If set to false then Logon messages # are ignored. UnregisteredAcceptor.CreateSession = true # This parameter specifies the time interval between attempts to deliver an application level # message to a registered client application in the event the application does not confirm # receipt and operation upon the message. The value is specified in milliseconds. # The value must be integer and greater than 0. # This parameter is required ony if the DelayedProcessing.MaxDeliveryTries # parameter is specified. DelayedProcessing.DeliveryTriesInterval = 500 # This parameter specifies the number of attempts that will be made to deliver an application # level message to the registered client application. If this value is exceeded then # the session will be closed with the logout reason "Application not available". The recommended value is 10. # The value must be integer and not negative. DelayedProcessing.MaxDeliveryTries = 2 # This parameter specifies the number of attempts to restore the session. # The session is considered as restored if the telecommunication link was # restored and the exchange of Logon messages was successful. # If it is set to "-1", then the number of attempts is unlimited. # This value is integer. # This parameter is optional. Reconnect.MaxTries = 3 # This parameter specifies the time interval between reconnection attempts in order to restore # a communications link. This value is specified in milliseconds (seconds*10-3). # The recommended value is 1000 for dedicated connections and private networks. # Internet connections require calibration. The value must be integer and greater than 0. Reconnect.Interval = 1000 # The license file name. LicenseFile=../../../engine.license # This parameter defines the upper limit to the number of outgoing messages that are resent # in the event of a Resend Request. The recommended value is 20000 if no data on mean activity is known. # WARNING: Changing this value will impact upon the performance of FIX Engine. # Larg storage increases application working set. OutgoingMessagesStorageSize = 1000 # This parameter is an option whereby the version of FIX protocol used for the outgoing message # is validated against that of the established session. If set to "true" then the application # must use the same version of the protocol as the established session otherwise an error # occurs. If set to false then the application level message will be sent to the counterparty. # The recommended value is "true". CheckVersionOfOutgoingMessages = true # If this parameter is true than file streams are flushed after each I/O operation. ExtraSafeMode = true # This parameter allow to automaticaly resolve sequence gap problem. # When parameter is true and outgoing SeqNum is 0, session use 141(ResetSeqNumFlag) # tag in sending/confirming Logon message to reset seqNum at the initiator or acceptor. ForceSeqNumReset=false # Default storage type of the created sessions. By default persistent storage # type used. Use "transient" value to use transient storage for the sessions. #UnregisteredAcceptor.SessionStorageType = # This parameter contains name of the XML file with extensions of the FIX protocols. DictionariesFilesList = ../../../data/fixdic43.xml;../../../data/fixdic44.xml;custom_fix43.xml UnregisteredAcceptor.IgnoreSeqNumTooLowAtLogon = true BackupDirectory = logs/backup UnregisteredAcceptor.RejectMessageWhileNoConnection = false ResetSeqNumAfter24hours = false Validation.CheckRequiredGroupFields = true MessageTimeToLive = 1000 AllowZeroNumInGroup = false Log.Device = File Log.DebugIsOn = true Log.NoteIsOn = true Log.WarnIsOn = true Log.ErrorIsOn = true Log.FatalIsOn = true Log.Cycling = false Log.File.RootDir = ./logs/ Log.File.Locked = false Log.File.Rotate = false Log.File.Backup.Time = Log.File.Name = _log Log.File.Recreate = true Log.File.AutoFlush = true Log.EventLog.EventSource = TestService # Monitoring Monitoring.Enable = true Monitoring.AdminSessionNames = AdminClient # ## User monitoring tool (TargetCompId = AdminClient) Monitoring.AdminSession.AdminClient.TargetCompId = AdminClient Monitoring.AdminSession.AdminClient.Version = FIX44 Monitoring.AdminSession.AdminClient.Username = user Monitoring.AdminSession.AdminClient.Password = pass Monitoring.AdminSession.AdminClient.IntradayLogoutToleranceMode = true Monitoring.AdminSession.AdminClient.ForceSeqNumResetMode = true Monitoring.AdminSession.AdminClient.IgnoreSeqNumTooLowAtLogon = true Monitoring.AdminSession.AdminClient.DisableTCPBuffer = false Monitoring.AdminSession.AdminClient.MaxMessagesAmountInBunch = 10 Monitoring.AdminSession.AdminClient.SocketOpPriority = AGGRESSIVE_SEND
custom_fix43.xml
<?xml version="1.0" encoding="UTF-8"?> <fixdics> <update> <fixdic fixversion="4.3" title="FIX 4.3" date="2007/03/22" id="FIX43"> <msgdic> <msgdef msgtype="F" > <field tag="555" /> <group nofield="555" startfield="600"> <field tag="600" req="N"/> <field tag="608" req="N"/> <field tag="610" req="N"/> <field tag="616" req="N"/> <field tag="624" req="N"/> </group> </msgdef> </msgdic> </fixdic> </update> </fixdics>
custom_fix44.xml
<?xml version="1.0" encoding="UTF-8"?> <fixdics> <update> <fixdic fixversion="4.4" title="FIX 4.4" date="2009/12/07" id="FIX44_MY" parent_id="FIX44"> <fielddic> <fielddef tag="5001" name="field5001" type="NumInGroup"/> <fielddef tag="5002" name="field5002" type="String"/> </fielddic> <msgdic> <msgdef msgtype="X" > <field tag="5001" /> <group nofield="5001" startfield="5002"> <field tag="5002" req="Y"/> </group> </msgdef> </msgdic> </fixdic> </update> </fixdics>
sender.cpp
/* <copyright> $Revision: 1.3 $ (c) B2BITS EPAM Systems Company 2000-2017. "Licensor" shall mean B2BITS EPAM Systems Company (B2BITS). This software is for the use of the paying client of B2BITS (which may be a corporation, business area, business unit or single user) to whom it was delivered (the "Licensee"). The use of this software is subject to license terms. The Licensee acknowledges and agrees that the Software and Documentation (the "Confidential Information") is confidential and proprietary to the Licensor and the Licensee hereby agrees to use the Confidential Information only as permitted by the full license agreement between the two parties, to maintain the confidentiality of the Confidential Information and not to disclose the confidential information, or any part thereof, to any other person, firm or corporation. The Licensee acknowledges that disclosure of the Confidential Information may give rise to an irreparable injury to the Licensor in-adequately compensable in damages. Accordingly the Licensor may seek (without the posting of any bond or other security) injunctive relief against the breach of the forgoing undertaking of confidentiality and non-disclosure, in addition to any other legal remedies which may be available, and the licensee consents to the obtaining of such injunctive relief. All of the undertakings and obligations relating to confidentiality and non-disclosure, whether contained in this section or elsewhere in this agreement, shall survive the termination or expiration of this agreement for a period of five (5) years. The Licensor agrees that any information or data received from the Licensee in connection with the performance of the support agreement relating to this software shall be confidential, will be used only in connection with the performance of the Licensor's obligations hereunder, and will not be disclosed to third parties, including contractors, without the Licensor's express permission in writing. Information regarding the software may be provided to the Licensee's outside auditors and attorneys only to the extent required by their respective functions. </copyright> */ #include <iostream> #include <string> #include <memory> #include <B2BITS_V12.h> #include "FixApp.h" using namespace std; const char* LISTENER_IP = "127.0.0.1"; const int LISTENER_PORT = 9022; int main() { cout << "starting FIX Sender..." << endl; try { // Initializes engine. // If error appears during initialization (properties file is not found, required property is missing, etc.) then exception is thrown. Engine::FixEngine::init( "sender.engine.properties" ); // Create Application instance. CFIXApp class derived from Engine::Application CFIXApp application; cout << "starting FIX Sender session..." << endl; Engine::SessionExtraParameters params; params.intradayLogoutToleranceMode_ = true; // Create FIX 4.3 session instance Engine::Session* pSIFIX43 = Engine::FixEngine::singleton()->createSession( &application, "TargetCompID_FIX43", "SenderCompID_FIX43", Engine::FIX43, ¶ms ); // Connect session as initiator pSIFIX43->connect( 30, LISTENER_IP, LISTENER_PORT ); // create FIX 4.3 Order Cancel Request using the Flat model std::auto_ptr<Engine::FIXMessage> pFIX43Message( Engine::FIXMsgFactory::singleton()->newSkel( Engine::FIX43, "F" ) ); // Fill required by FIX 4.3 fields std::string clrodid; Engine::UTCTimestamp::now().toFixString( &clrodid ); pFIX43Message->set( FIXField::OrigClOrdID, clrodid ); pFIX43Message->set( FIXField::ClOrdID, clrodid ); pFIX43Message->set( FIXField::Symbol, "MSFT" ); pFIX43Message->set( FIXField::Side, '1' ); // Buy pFIX43Message->set( FIXField::OrderQty, 400 ); pFIX43Message->set( FIXField::OrdType, '2' ); // Limit pFIX43Message->set( FIXField::TransactTime, Engine::UTCTimestamp::now() ); // Fill custom fields pFIX43Message->set( 555, 1 ); pFIX43Message->getGroup( 555 )->set( 600, "MSFS", 0 ); pFIX43Message->getGroup( 555 )->set( 616, "XAMS", 0 ); pFIX43Message->getGroup( 555 )->set( 624, '2', 0 ); pFIX43Message->getGroup( 555 )->set( 600, "MSFT", 0 ); pFIX43Message->getGroup( 555 )->set( 616, "XAMS", 0 ); pFIX43Message->getGroup( 555 )->set( 624, '1', 0 ); cout << "sending the message: " << *pFIX43Message->toString( '|' ) << endl << endl; // Send order to session initiator pSIFIX43->put( pFIX43Message.get() ); // Wait for trade application.tradeReceived_.wait(); // Closing the session pSIFIX43->disconnect(); application.logoutReceived_.wait(); // Releasing resources pSIFIX43->registerApplication( NULL ); pSIFIX43->release(); // Load new FIX protocol dialect from XML file and store ParserID Engine::FixEngine::singleton()->loadProtocolFile( "custom_fix44.xml" ); Engine::ParserID pid = Engine::FixEngine::singleton()->createFixParser( "FIX44_MY" ); // Create session using customized FIX44 protocol Engine::Session* pSIFIX44 = Engine::FixEngine::singleton()->createSession( &application, "TargetCompID_FIX44", "SenderCompID_FIX44", pid, ¶ms ); // Start session as initiator pSIFIX44->connect( 30, LISTENER_IP, LISTENER_PORT ); // Create and fill default "X" message fields std::auto_ptr<Engine::FIXMessage> pFIX44Message( Engine::FIXMsgFactory::singleton()->newSkel( pid, "X" ) ); pFIX44Message->set( FIXField::NoMDEntries, 1 ); pFIX44Message->getGroup( FIXField::NoMDEntries )->set( FIXField::MDUpdateAction, '0', 0 ); pFIX44Message->getGroup( FIXField::NoMDEntries )->set( FIXField::Symbol, "MSTS", 0 ); pFIX44Message->getGroup( FIXField::NoMDEntries )->set( FIXField::NoUnderlyings, 1, 0 ); pFIX44Message->getGroup( FIXField::NoMDEntries )->getGroup( FIXField::NoUnderlyings, 0 )->set( FIXField::UnderlyingSymbol, "MSTS", 0 ); // Fill customized fields pFIX44Message->set( 5001, 1 ); pFIX44Message->getGroup( 5001 )->set( 5002, "APL", 0 ); cout << "sending the message: " << *pFIX44Message->toString( '|' ) << endl << endl; // Send message to session initiator pSIFIX44->put( pFIX44Message.get() ); // Wait for response application.tradeReceived_.wait(); // Closing the session pSIFIX44->disconnect(); application.logoutReceived_.wait(); // Releasing resources pSIFIX44->registerApplication( NULL ); pSIFIX44->release(); // Destroying the engine Engine::FixEngine::destroy(); } catch( const std::exception& ex ) { cout << "Error: " << ex.what() << endl; // Destroying the engine Engine::FixEngine::destroy(); } catch ( ... ) { cout << "Unknown error." << endl; // Destroying the engine Engine::FixEngine::destroy(); } return 0; }
The format below is deprecated and cannot be used. The value syntax is the following:
The example below means: