OnixS C++ FIX Engine 4.14.0
Users' manual and API documentation
Loading...
Searching...
No Matches
Throttling BuySide Sample

This sample demonstrates the throttling of outgoing messages on the initiator's side.

Source code

Listener.h

class Listener : public OnixS::FIX::ISessionListener
{
public:
Listener() : orderHandlingComplete_(0), totalOrdersHandled_(0), totalMessagesRejected_(0), failed_(false) {}
void onInboundApplicationMsg(OnixS::FIX::Message & msg, OnixS::FIX::Session * sn) final;
void onInboundSessionMsg(OnixS::FIX::Message & msg, OnixS::FIX::Session * sn) final;
void onStateChange(OnixS::FIX::SessionState::Enum newState, OnixS::FIX::SessionState::Enum prevState, OnixS::FIX::Session * sn) final;
void onError(OnixS::FIX::ErrorReason::Enum reason, const std::string & description, OnixS::FIX::Session * sn) final;
void onWarning(OnixS::FIX::WarningReason::Enum reason, const std::string & description, OnixS::FIX::Session * sn) final;
bool failed() const;
OnixS::Threading::Semaphore orderHandlingComplete_;
size_t totalOrdersHandled_;
size_t totalMessagesRejected_;
private:
void recordFailure();
mutable OnixS::Threading::Mutex failureMutex_;
bool failed_;
};

Listener.cpp

#include "Listener.h"
#include "../../Common/Helpers.h"
#include <iostream>
#include <string>
using namespace OnixS::FIX;
using namespace OnixS::FIX::FIX44;
using namespace OnixS::FIX::FIX44::Values;
bool Listener::failed() const
{
OnixS::Threading::MutexGuard guard(failureMutex_);
return failed_;
}
void Listener::recordFailure()
{
OnixS::Threading::MutexGuard guard(failureMutex_);
failed_ = true;
}
void Listener::onInboundApplicationMsg(Message & msg, Session * )
{
std::clog << "\nIncoming application-level message:\n" << msg << std::endl;
if(msg.type() == MsgType::ExecutionReport)
{
++totalOrdersHandled_;
orderHandlingComplete_.release();
}
}
void Listener::onInboundSessionMsg(Message & msg, Session * )
{
std::clog << "\nIncoming session-level message:\n" << msg << std::endl;
if(msg.type() == MsgType::Reject)
{
++totalMessagesRejected_;
std::clog << "Rejection " << totalMessagesRejected_ << ": message " << msg.get(Tags::RefSeqNum).toString() << " rejected." << std::endl;
orderHandlingComplete_.release();
}
}
void Listener::onStateChange(SessionState::Enum newState, SessionState::Enum prevState,
Session * )
{
std::clog
<< "\nSession's state is changed, prevState="
<< SessionState::toString(prevState)
<< ", newState="
<< std::endl;
}
void Listener::onError(ErrorReason::Enum , const std::string & description, Session * )
{
recordFailure();
orderHandlingComplete_.release();
std::cerr << "\nSession-level error:" << description << std::endl;
}
void Listener::onWarning(WarningReason::Enum , const std::string & description,
Session * )
{
std::cerr << "\nSession-level warning:" << description << std::endl;
}

ThrottlingBuySide.cpp

#include "Listener.h"
#include "../../Common/Helpers.h"
#include "../../Common/Settings.h"
using namespace Settings;
using namespace OnixS::FIX;
using namespace OnixS::FIX::FIX44;
using namespace OnixS::FIX::FIX44::Values;
int main()
{
std::clog << "ThrottlingBuySide sample." << std::endl << std::endl;
try
{
EngineSettings settings;
settings.licenseStore(LicenseStore);
Engine::init(settings);
EngineShutdownGuard engineShutdownGuard;
Listener listener;
Session session(SenderCompId, TargetCompId, FixProtocolVersion, &listener);
const std::string CounterpartyHost = "localhost";
const int CounterpartyPort = ListenPort;
const int HeartBtInt = 5;
const size_t MessagesPerSecondLimitDelta = 3;
const size_t MessagesPerSecondLimit = 10 - MessagesPerSecondLimitDelta;
const size_t ThrottlingIntervalMillisecond = 1000;
session.throttlingLimit(MessagesPerSecondLimit, ThrottlingIntervalMillisecond);
session.logonAsInitiator(CounterpartyHost, CounterpartyPort, HeartBtInt);
std::clog << "Press any key to send throttled orders..." << std::endl;
waitForAnyKey();
Message order(MsgType::NewOrderSingle, FixProtocolVersion);
setOrderFields(&order);
const int NumOfMessages = 100;
for(int msgCounter = 0; msgCounter < NumOfMessages; ++msgCounter)
{
session.throttle();
session.send(&order);
listener.orderHandlingComplete_.acquire();
if(listener.failed())
throw std::runtime_error("Throttling session failed.");
}
std::clog << "Orders handled: " << listener.totalOrdersHandled_ << ", messages rejected: " << listener.totalMessagesRejected_ << std::endl;
std::clog << "Press any key to disconnect the session and terminate the application." << std::endl;
waitForAnyKey();
session.logout("The session is disconnected by ThrottlingBuySide").shutdown();
if(listener.failed())
return 1;
}
catch(const std::exception & ex)
{
processSampleException(ex.what());
return 1;
}
return 0;
}