Order Book

Gateways

The order books are always cached by the gateways.

These are the scenarios

  • The exchange publish a snapshot. This will replace the content of the cached object.

    • There is some minor normalization happening such as sorting prices for MarketByPrice.

  • The exchange publish an incremental update. This will apply the changes to the cached order book.

    • Real changes will be kept.

    • Changes having no effect will be discarded.

    • Artifical changes may be added, e.g. when a price drops out of a fixed-depth order book.

    • Updates are enriched with additional information, e.g. the index where the change has to be applied.

The summary of this is that the client will receive a clean feed up incremental changes which can efficiently be applied to their own cached order book objects.

Efficiency

There may be other approaches, but the following are often encountered

  • Gateway publish fixed depth snapshots, e.g. 10 price levels.

  • Gateway uses shared memory to allow clients to directly access a order book object.

  • Gateway publish snapshot and incremental updates so the client can maintain their own view of the order book.

Fixed Depth Snapshots

Pros

  • Fixed length messages.

  • A simple memcpy can be used by client to maintain state.

Cons

  • Harder to detect what has changed.

  • Not possible for client to maintain a deep order book (perhaps an issue for illiquid markets).

Shared Objects

Pros

  • Can’t see any, this is the case of trying to be too smart…?

Cons

  • Harder to detect what has changed.

  • Requires some kind of locking, either mutex-style or some kind of versioning. Gets complex and introduces unpredictable access time.

Snapshot / Incremental

Pros

  • Data flows one-way (gateway to clients) and locks can be avoided. (See reference to the MOESI protocol.)

cons

  • duplication of work (clients repeat what gateway already does).

client

you need this

#include "roq/cache/market_by_price.hpp"

then you can create an order book object like this

auto market_by_price_ = client::marketbypricefactory::create("deribit", "btc-perpetual");

in your event handler you now do this

void MyHandler::operator()(Event<MarketByPriceUpdate> const &event) {
  auto& [message_info, market_by_price_update = event;
  (*market_by_price_)(market_by_price_update);
}

References