AlgoTraderAlgoTrader Documentation

Chapter 21. Market Data

21.1. Creation of Bars based on Ticks
21.2. Numeric Precision
21.3. Price normalization
21.4. Market Data Gap Checking
21.5. Generic Events

AlgoTrader provides Market Data Interfaces with the following market data providers:

AlgoTrader allows having multiple market data interfaces active at the same time so market data received from different market data providers can be compared in real-time.

To enable either of those Market Data Interfaces the following two steps have to be executed:

  1. The correct Spring Profile has to be activated according to Section 27.3, “Spring Profiles”

  2. For Bloomberg market-data-bb and for InteractiveBrokers market-data-ib has to be added to the VM argument server-engine.init when running the AlgoTrader server.

All Market Data Interfaces have a set of unique artifacts:

Market Data Events itself are available in different types:

As the following diagram shows, market data providers deliver Price Events (TradeVO, BidVO & AskVO) or individual TickVO Fields.

In back testing AlgoTrader supports both Ticks or Bars. In both live trading and back testing Price events and Tick events can be aggregated into Bar events

Market Data Event Types

Figure 21.1. Market Data Event Types


Processing of Market Data is handled through the MarketDataService, which calls the market data provider specific ExternalMarketDataService implementations. Every market data service has to provide implementation of this interface e.g. (e.g. IBMarketDataServiceImpl or BBMarketDataServiceImpl).

The most important methods provided by the MarketDataService are subscribe and unsubscribe. Through the use of these methods new Market Data can be subscribed and unsubscribed. Subscribed securities are persisted within the DB-table subscription. The actual subscription of securities to the external broker is done through the market data provider specific MarketDataService.

Market data provider interfaces are responsible for receiving market data provider specific Market Data and sending them into the Esper Service Instance of the AlgoTrader Server. The Esper Service Instance will then convert these Events into generic MarketDataEvents (i.e. Ticks or Bars) which will be propagated to subscribed Strategies.

Inside each strategy the MarketDataCacheService keeps a copy of the last MarketDataEvent for each Security. For further details see Section 5.3.1.2, “MarketDataCacheService”.

In both Simulation and Live Trading, Bars can be generated from Ticks or Price Events through the use of Esper Statements: use the time_batch to create bars:

select
  first(last) as open,
  max(last) as high,
  min(last) as low,
  last(last) as close
from
  TickVO.win:time_batch(1 min)
group by
  securityId;

and expr_batch for constant volume bars:

select
  max(last) as high,
  min(last) as low,
  first(last) as open,
  last(last) as close
from
  TickVO.win:expr_batch(sum(volume) > 1000)
group by
  securityId;

In General different Securities are traded with different numeric precision (e.g. S&P Futures prices are two digits, whereas FX prices are usually 5-6 digits and crypto currencies are up to 8 digits). To accommodate different numeric precisions, AlgoTrader provides the following fields inside the class SecurityFamily:

Price normalization comes into play when multiple market data and/or trading adapters are in use that use different price multipliers / contract sizes for the same instrument. For example one adapter might quote prices in dollars with a contract size of 10 where as another one might quote them in cents with a contract size of 1000. The default contract size will be stored in the security_family table with all other cases (i.e. exceptions) stored using the broker_parameters table.

Since a continuous data feed of market data is essential for most trading strategies, AlgoTrader contains a feature that automatically warns if no market data has been received for a prolonged period of time. For this purpose the class SecurityFamily has a property maxGap, that defines the maximum number of minutes allowed without any market data updates. This is enforced by the CHECK_TICK_GAPS statement which can be turned on via the VM argument:

-Dstatement.marketDataGap=true

In addition to MarketDataEvents (i.e. TickVOs and BarVOs) there are general purpose Generic Events that can contain any type of information (e.g. virtual market data, signals, exposure values, etc.). In contrary to MarketDataEvents, which are sent from the AlgoTrader Server to subscribed strategies, these Generic Events are sent from one strategy to one or more receiving strategies. A Generic Event class has to subclass GenericEventVO. Subscription to Generic Events is based on the class of the Generic Event.

Example: To subscribe to a Generic Event of type Signal (which is a subclass of GenericEventVO), the following needs to be done:

getSubscriptionService().subscribeGenericEvents(Collections.singleton(Signal.class));

To send a GenericEvent, use the following method:

getEventDispatcher().broadcast(signal, EventRecipient.REMOTE_ONLY);

GenericEvents are automatically propagated to the Strategy Esper Engine where they can be accessed as follows (the event type Signal needs to be added to the Esper config file):

select * from Signal;

In addition it is possible to handle incoming GenericEvents through the onGenericEvents method:

@Override

public void onGenericEvent(GenericEventVO event) {
    ...
}

It is also possible to feed Generic Events via CSV Files in Simulation Mode. To enable this, the following VM argument has to be set:

-DdataSource.feedGenericEvents = true

The file name of the CSV File has to be according to this schema: