I am trying to understand the IBrokers package, and when reading its Real Time vignettes, at the end of section 2.4.1, the author of the package, Jeffrey A. Ryan, wrote:
[...] to request the current time from the TWS, one needs to send the code for "Current Time"(.twsOutgoingMSG$REQ CURRENT TIME): "49" and the current version number of the specific request. In the case of current time, the version is simply the character "1".
Scanning through the source code of the IBrokers package, i have noticed that the author uses different VERSION number for different requests (e.g. for reqMrktData, VERSION = 9). Whoever, when I, looked at the Interactive Brokers API document, for the reqMktData() function, i see that the function doesn't require a "version number" as a parameter.
I have also tried to look for a general explanation to what a version number of a specific request, and when/where we might need it, but i couldn't find any.
I would appreciate if someone can provide me with an explanation to that "VERSION" variable, what it's meant to do/achieve, and how/where we can find a list of version number for various request to the Interactive Brokers API.
Thank you in advance
I would appreciate if someone can provide me with an explanation to that "VERSION" variable, what it's meant to do/achieve, and how/where we can find a list of version number for various request to the Interactive Brokers API.
API evolution issues.
Look at class EClientSocket
in the Java (or C++) API client library code. Jeff Ryan probably picked up / had to pick up the VERSION numbers from here.
Basically, as the IB Platform / Servers' capabilities evolved, there were older as well as newer versions of Client APIs in use by customers. Thus, the IB server is able to handle requests from older versions of IB API Clients as well as newer ones. The VERSION helps the server distinguish which version of the API call it's dealing with.
For example, newer versions of the IB Client API can reqMktData()
for entire Combos with multiple Legs in one shot, which older Clients could not do. Thus, as you noted, it is 1 for the simpler API which did not evolve, such as cancelHistoricalData()
, cancelScannerSubscription()
etc;, but can be as high as 7 or 9 for the APIs which tend to evolve with time, such as reqMktData().
In more low-level terms, the VERSION tells the server what parameters the Client is going to pass on the Socket immediately after send()
-ing the VERSION
. Below is a code excerpt from reqScannerSubscription()
. Note the send(VERSION);
right after the send(REQ_SCANNER_SUBSCRIPTION);
(Note that there are TWO other types of version numbers : the server-side (IB Server / Platform) version number, and the IB TWS Client API version number! These are separate from the per-API VERSION that you are concerned with. Whether IB really needs a per API call VERSION which is separate from the IB Client version is not immediately obvious to me, but that's how they roll right now).
Apologies for a rambling answer; one look at EClientSocket.java
will clear it up! :-)
public synchronized void reqScannerSubscription( int tickerId,
ScannerSubscription subscription) {
// not connected?
if (!m_connected) {
error(EClientErrors.NO_VALID_ID, EClientErrors.NOT_CONNECTED, "");
return;
}
if (m_serverVersion < 24) {
error(EClientErrors.NO_VALID_ID, EClientErrors.UPDATE_TWS,
" It does not support API scanner subscription.");
return;
}
final int VERSION = 3;
try {
send(REQ_SCANNER_SUBSCRIPTION);
send(VERSION);
send(tickerId);
sendMax(subscription.numberOfRows());
send(subscription.instrument());
send(subscription.locationCode());
Client version history at the top of EClientSocket.
public class EClientSocket {
// Client version history
//
// 6 = Added parentId to orderStatus
// 7 = The new execDetails event returned for an order filled status and reqExecDetails
// Also market depth is available.
// 8 = Added lastFillPrice to orderStatus() event and permId to execution details
// 9 = Added 'averageCost', 'unrealizedPNL', and 'unrealizedPNL' to updatePortfolio event
// 10 = Added 'serverId' to the 'open order' & 'order status' events.
// We send back all the API open orders upon connection.
// Added new methods reqAllOpenOrders, reqAutoOpenOrders()
// Added FA support - reqExecution has filter.
// - reqAccountUpdates takes acct code.
// 11 = Added permId to openOrder event.
// 12 = requsting open order attributes ignoreRth, hidden, and discretionary
// 13 = added goodAfterTime
// 14 = always send size on bid/ask/last tick
// 15 = send allocation description string on openOrder
// 16 = can receive account name in account and portfolio updates, and fa params in openOrder
// 17 = can receive liquidation field in exec reports, and notAutoAvailable field in mkt data
// 18 = can receive good till date field in open order messages, and request intraday backfill
// 19 = can receive rthOnly flag in ORDER_STATUS
// 20 = expects TWS time string on connection after server version >= 20.
// 21 = can receive bond contract details.
// 22 = can receive price magnifier in version 2 contract details message
// 23 = support for scanner
// 24 = can receive volatility order parameters in open order messages
// 25 = can receive HMDS query start and end times
// 26 = can receive option vols in option market data messages
// 27 = can receive delta neutral order type and delta neutral aux price in place order version 20: API 8.85
// 28 = can receive option model computation ticks: API 8.9
// 29 = can receive trail stop limit price in open order and can place them: API 8.91
// 30 = can receive extended bond contract def, new ticks, and trade count in bars
// 31 = can receive EFP extensions to scanner and market data, and combo legs on open orders
// ; can receive RT bars
// 32 = can receive TickType.LAST_TIMESTAMP
// ; can receive "whyHeld" in order status messages
// 33 = can receive ScaleNumComponents and ScaleComponentSize is open order messages
// 34 = can receive whatIf orders / order state
// 35 = can receive contId field for Contract objects
// 36 = can receive outsideRth field for Order objects
// 37 = can receive clearingAccount and clearingIntent for Order objects
private static final int CLIENT_VERSION = 37;
private static final int SERVER_VERSION = 38;
private static final byte[] EOL = {0};
private static final String BAG_SEC_TYPE = "BAG";