¿ªÔÆÌåÓý

ctrl + shift + ? for shortcuts
© 2025 Groups.io
Date

Re: TickByTick or TickPrice?

 

Thank you for your input.
I have done some experimenting with both and reqTickByTickData generates much less callbacks which is good for me in Python. Strangely the timestamp they provide is up to a second, so yes, I use my own.
I am not quite sure how do they calculate limits. For example right now I can use up to six reqTickByTickData, trying more than that raises an error: 10190,Max number of tick-by-tick requests has been reached, so I can fallback on the reqMktData in this case.
Information about a limit of 5 is from here:?


Re: Correlate orders and fills from the API to those in Flex Report

 

IBKR no longer fill the OrderRef field in flex reports. They certainly used to, some time ago. Now the field is still there but the content is not carried over from TWS to daily reports any more, unfortunately, so it's always empty.

--
Best,
DS


Re: updateMktDepthL2 missing data points

 

´³¨¹°ù²µ±ð²Ô,

i really like that heart-beat idea and i will implement it too as it will simplify my commit-forcing logic and it will also provide some insights into the health of the system. it will also give me slightly faster commits on idle times. thank you again for sharing your knowledge and experience.

i also agree with you that transaction boundaries can also be deducted from the received data. what i can see in the data is that (by change?below i mean any operation):
  • bid (1) changes always come before ask (0) changes within a single transaction, but transaction does not have to contain both sides
  • the changes always come with ascending position within a single transaction, though they don't have to be always increased continuously by one (that is the changes might come as 2, 3, 7, 8)
  • deletes and inserts always come last in the transaction = after updates
so if i should write the supposed rules in my own words, based on the observations above, then
  • there is no transaction boundary if the side is the same and the position of the current change is higher than the position of the previous change
  • there is no transaction boundary if side switched from bid to ask
  • all other cases should imo trigger a transaction commit before the current change, that is
    • the side is the same but the position of the current change is not higher than the position of the previous change (so the position is the same or lower)
    • the side switches from ask to bid
it is important to note that imo the operation type does not really matter with regard to transaction boundaries (even though inserts and deletes seem to appear as the last operations, it is not known ahead how many there will be).
with regard to forex market depth, i have no idea how the book is composed as it is not a centralized market like cme or cbot, it is decentralized, and ib does not even have complete coverage of the market (it cannot have it because of its decentralization). my main concern is where the book is in fact composed. there are generally two possibilities:
  1. this is just the book at ib (i tend to think this is more probable)
  2. they get all the visible orders from the decentralized market (that i doubt)
  3. it can also be a mix of both
so, currently, i can see the data, but i have no idea what it represents.


Re: updateMktDepthL2 missing data points

 

Very nice, fordfrog, and it all makes a lot of sense to me. I think our approaches are identical on the "what" level, but there are minor implementation differences on the "how" level.

For example, as part of my general client connection logic, I already start a heart-beat thread (independent of MarketDepth feeds) that monitors the connection with TWS/IBGW by issuing a request once a second. That means I always have at least one response message from TWS/IBGW every second that can be used for MarketDepth update transaction boundary detection. That heart-beat thread:
  • locks onto a specific offset from the top of the second (say 100ms) and monitors how precisely it gets activated. That is a good measure for how responsive (or possibly overloaded) the client is.
  • makes sure every request gets an callback (e.g. TWS/IBGW are indeed responsive)
  • makes sure the returned server time is identical to the one expected
  • measures and monitors the response time to determine how responsive (or possibly overloaded) TWS/IBGW are

There can be only one outstanding request per connected client (as you found out) since it is one of the few requests that have no reqId. But I am digressing.

The approach you have outlined is based on only one (well informed) assumption: TWS/IBGW do not split market book update transactions. In other words, the sequence of MarketDepth messages that make up one update will not be interrupted by one or more other TWS API messages. There is a second (also well informed) assumption that could enable us to detect even more transaction boundaries (sub-second), but it may need some more thought:
  • A market book update will often consist of changes for only a subset of all positions, and may sometimes even be limited to a single side (Buy or Sell).
  • But? updates (operation==1) and inserts (operation==0) do take place in numerically increasing position order (first side 0, ..., n then possibly other side 0, ..., m) and no position is updated more than once between two transaction boundaries. Deletes (operation==2) are performed in reverse numeric position order.
With that in mind, it feels safe to declare additional transaction boundaries like this:
  • When a new MarketDepth message arrives, check whether the new message and the last message in the queue of uncommitted MarketDepth messages have the same operation ("update") and operate on the same side (Buy or Sell).
  • If not, check whether the new MarketDepth message and first message in that queue are both "update" operations for the same side.
  • A new transaction boundary exists before the new MarketDepth message iff:
    • one of those two checks passes
    • and the position in the new message is equal to or smaller than the position in the queued message

This holds true at least for the CME and CBOT based futures I have been looking at for a long time. Maybe you can check whether that would work for FOREX, too.

Well done again,

´³¨¹°ù²µ±ð²Ô


On Thu, Nov 16, 2023 at 01:47 PM, fordfrog wrote:
@´³¨¹°ù²µ±ð²Ô

i mostly finished my implementation and i'm just reviewing the code, probably for the last time. in the text below i'll use word commit?to indicate the supposed end of transaction (end of market depth update items batch/transaction). by transaction?i mean supposed transaction boundary, end of the batch that creates a consistent state of the book. commit item is an instruction to issue a commit for market depth updates. market depth item is the update message received. market depth (message) processor is a class running in a separate thread and handling all market depth messages (updates and book reset). commit callback is a method defined on the listener interface and is used to pass the commit information to the listener. commit message generator is a class running in a separate thread and handling requests for commit messages, eventually sending a message to tws/gw to trigger some response.

i did it the same way as you did, that is an incoming message from a different topic commits the updates from the market depth request id that was processed the last.

i also implemented some additions:
  • if a market depth update to a different request id comes, it commits previous request updates (you probably have this coded too as it seems a logical conclusion from your observations). (it is important to check the request id against the last request id added to the queue, not the last request id processed, and queue the commit item before the market depth item?just being added.)
  • i did not implement triggering commit from book reset message as the state before the reset does not have to be at the end of a transaction.
  • when processing the queue, market depth update sets uncommitted request id, and commit item commits the last uncommitted request?and resets the uncommitted request id.
  • when commit occurs, it always commits the last market depth request if it is not committed yet. in the market depth processor i can have only one uncommitted request because (1) a different request id triggers a commit?and/or (2) a different message triggers a commit. so there can only be zero or one uncommitted request in the processor.
  • before the commit callback is called, i also check whether there are more items in the queue with the same request id (i set parameter hasMoreItems?on the callback to true on first occurrence of the same request id in the queue, it's just an on/off flag, no need to report how many items are in the queue). this is to inform the listener that though the market depth data might be in a consistent state, more updates arrived in the meantime which makes the data obsolete.
  • if market depth processor queue empties without issuing a commit (the last item retrieved from the queue before the queue becomes empty is not a commit item), a request for commit message is issued (more on that below). this i need in cases where there is no other traffic as i would otherwise get no commits. this would happen in my automated test of market depth as i don't issue any other request in parallel so i would get no commits which would cause the test to fail.
commit message request?is a message being sent to tws/gw to trigger a response message. here are the details:
  • only one message per second can be triggered, even if more commit message requests are fired (in case of current time request / see below / it also happens that more frequent requests are simply ignored and not answered at all by tws/gw).
  • the request is queued in the commit message generator. once an item is added to its queue, it is woken up (if waiting for a queue signal) and waits until the specified timeout (1000ms in my case) elapses. then the queue is inspected, the queued market depth message processor is asked whether it still needs a commit (for details see below), and if so, a request is sent to tws/gw.
  • market depth message processor still wants a commit if the last request id was not committed and the queue is empty (the request came after the queue was emptied) or there was no commit yet (there are some items in the queue but there was so far no commit) or the last commit was triggered longer than a specified interval ago (in my tests 100ms - so there are still items in the queue, we already had at least one commit, but it's a long time since the last commit). this way relatively frequent commits should be triggered. the commit callback though still depends on messages incoming for other topics or a different request id.
  • the commit message request?itself is issued only after the queue gets empty. it's just a request though, not sending of a message, that is handled by commit message generator.
  • as the commit message request, i tried request for current time and request for managed accounts. both behaved the same and had pretty much the same response times. i'm really not sure that the request for current time is being sent to ib servers, i rather think that tws/gw syncs the time occasionally from ib servers and the response is generated directly from gw/tws (at least this is how i would probably code it myself). but the response times for managed accounts were pretty much the same. so either managed accounts are cached on login and never requested again (more probable), or both the requests are sent to ib servers (i doubt as the response times were pretty short, as short as 8ms what i've seen, and my gw is running on a server several hops away from my laptop where i ran the tests which adds some delay). anyway, i just tried to use a cheap request/response message. still, i saw a cases when i issued current time request, and then i received several market depth updates before i got the current time response (also occurs in the attached log). in most cases though there were no messages between the request and response. my conclusion is that at least the response is placed at the end of the tws/gw output buffer (towards the client). so the response (1) imo marks the end of buffered messages in tws/gw and (2) triggers commit in my code. also, if tws/gw would receive all updates as a single batch, it would also mark the end of the batch (as it would be placed at the output buffer?as a single unit), but this is an if.
i'm also attaching the log from my test case which shows the behavior. in the process, market depth request is issued, then the listener waits for 5 commits and cancels the request. there are no messages omitted (except two "error" messages at the beginning reporting market data farm statuses). logging times are not that important, more important are times in the square brackets just after the message type name, those indicate the timestamp when the message was sent/received. content of messages is displayed in standard ib format.

i hope it all makes some sense. i tried to be both as clear as possible and also as brief as possible, but i'm not sure i achieved that...


Re: TickByTick or TickPrice?

 

IMHO but as you may see other are ok too this is more a question of the issue to solve.
You need to tell us more about your intent, it is difficult to give pro/con as there are too many factors involved to debate that in this thread.

Food for thoughts:

1 - There are various tick API because it make sense in different situation, so it depend about what you want to do with the outcome of the info.
Back to what do you want to achieve by listening to ticks.

2 - The language you use may influence your choice if performance is an issue (in Python you should give privilege to the method that lower the number of call backs or collating process)
And a warning, ticks are not precisely time stamped. You may need to implement your own stamping in the callback.
This could be a reason to prefer as it maybe that arrival time reveal a certain reality (not guaranteed as it goes trough many bucket before reaching your callback)

3- I never saw a limitation as low as 5. Where did you read this ?
Anyway no secret, if there is a limitation on one API there is the about the same limitation on the other variants, just less explicit in doc or less critical probably because people didn't use it in same condition that may reach the limits or that this API callback is slower or aggregated and you rarely reach it.

This may even give you a 'trend' about methods: the more IB talks about limitations, the faster/heavier/peculiar are the usages of it.
Also you can buy Booster Pack from IB to raise volume limitations.


Re: updateMktDepthL2 missing data points

 

@´³¨¹°ù²µ±ð²Ô

i mostly finished my implementation and i'm just reviewing the code, probably for the last time. in the text below i'll use word commit?to indicate the supposed end of transaction (end of market depth update items batch/transaction). by transaction?i mean supposed transaction boundary, end of the batch that creates a consistent state of the book. commit item is an instruction to issue a commit for market depth updates. market depth item is the update message received. market depth (message) processor is a class running in a separate thread and handling all market depth messages (updates and book reset). commit callback is a method defined on the listener interface and is used to pass the commit information to the listener. commit message generator is a class running in a separate thread and handling requests for commit messages, eventually sending a message to tws/gw to trigger some response.

i did it the same way as you did, that is an incoming message from a different topic commits the updates from the market depth request id that was processed the last.

i also implemented some additions:
  • if a market depth update to a different request id comes, it commits previous request updates (you probably have this coded too as it seems a logical conclusion from your observations). (it is important to check the request id against the last request id added to the queue, not the last request id processed, and queue the commit item before the market depth item?just being added.)
  • i did not implement triggering commit from book reset message as the state before the reset does not have to be at the end of a transaction.
  • when processing the queue, market depth update sets uncommitted request id, and commit item commits the last uncommitted request?and resets the uncommitted request id.
  • when commit occurs, it always commits the last market depth request if it is not committed yet. in the market depth processor i can have only one uncommitted request because (1) a different request id triggers a commit?and/or (2) a different message triggers a commit. so there can only be zero or one uncommitted request in the processor.
  • before the commit callback is called, i also check whether there are more items in the queue with the same request id (i set parameter hasMoreItems?on the callback to true on first occurrence of the same request id in the queue, it's just an on/off flag, no need to report how many items are in the queue). this is to inform the listener that though the market depth data might be in a consistent state, more updates arrived in the meantime which makes the data obsolete.
  • if market depth processor queue empties without issuing a commit (the last item retrieved from the queue before the queue becomes empty is not a commit item), a request for commit message is issued (more on that below). this i need in cases where there is no other traffic as i would otherwise get no commits. this would happen in my automated test of market depth as i don't issue any other request in parallel so i would get no commits which would cause the test to fail.
commit message request?is a message being sent to tws/gw to trigger a response message. here are the details:
  • only one message per second can be triggered, even if more commit message requests are fired (in case of current time request / see below / it also happens that more frequent requests are simply ignored and not answered at all by tws/gw).
  • the request is queued in the commit message generator. once an item is added to its queue, it is woken up (if waiting for a queue signal) and waits until the specified timeout (1000ms in my case) elapses. then the queue is inspected, the queued market depth message processor is asked whether it still needs a commit (for details see below), and if so, a request is sent to tws/gw.
  • market depth message processor still wants a commit if the last request id was not committed and the queue is empty (the request came after the queue was emptied) or there was no commit yet (there are some items in the queue but there was so far no commit) or the last commit was triggered longer than a specified interval ago (in my tests 100ms - so there are still items in the queue, we already had at least one commit, but it's a long time since the last commit). this way relatively frequent commits should be triggered. the commit callback though still depends on messages incoming for other topics or a different request id.
  • the commit message request?itself is issued only after the queue gets empty. it's just a request though, not sending of a message, that is handled by commit message generator.
  • as the commit message request, i tried request for current time and request for managed accounts. both behaved the same and had pretty much the same response times. i'm really not sure that the request for current time is being sent to ib servers, i rather think that tws/gw syncs the time occasionally from ib servers and the response is generated directly from gw/tws (at least this is how i would probably code it myself). but the response times for managed accounts were pretty much the same. so either managed accounts are cached on login and never requested again (more probable), or both the requests are sent to ib servers (i doubt as the response times were pretty short, as short as 8ms what i've seen, and my gw is running on a server several hops away from my laptop where i ran the tests which adds some delay). anyway, i just tried to use a cheap request/response message. still, i saw a cases when i issued current time request, and then i received several market depth updates before i got the current time response (also occurs in the attached log). in most cases though there were no messages between the request and response. my conclusion is that at least the response is placed at the end of the tws/gw output buffer (towards the client). so the response (1) imo marks the end of buffered messages in tws/gw and (2) triggers commit in my code. also, if tws/gw would receive all updates as a single batch, it would also mark the end of the batch (as it would be placed at the output buffer?as a single unit), but this is an if.
i'm also attaching the log from my test case which shows the behavior. in the process, market depth request is issued, then the listener waits for 5 commits and cancels the request. there are no messages omitted (except two "error" messages at the beginning reporting market data farm statuses). logging times are not that important, more important are times in the square brackets just after the message type name, those indicate the timestamp when the message was sent/received. content of messages is displayed in standard ib format.

i hope it all makes some sense. i tried to be both as clear as possible and also as brief as possible, but i'm not sure i achieved that...


Re: TickByTick or TickPrice?

 

For most purposes reqMktData works fine. I never needed tick by tick data.?


Specific error message needs to be given for these requests!

 

Hi All,

i have this problem on windows 2019 server:

Sometimes i got this error:

2023-11-16 13:02:34.781|[ERROR]|Error. Id: -1, Code: -1, Msg: Specific error message needs to be given for these requests!

After this i can't connect again on TWS even if i restart the platform, the only solution is restart server.

Could help me to solve this error?

Davide


Re: How to catch liquidation warnings and liquidation events?

 

I found the liquidation order flag by looking in here:




Re: How to catch liquidation warnings and liquidation events?

 

Hi ´³¨¹°ù²µ±ð²Ô,

I was looking at it this afternoon and provoked the warning.

I used ib_insync accountValues to see what was in there:



There is 139 tags to look through. At that time the margin 'Cushion' was less than 10% and I later saw a spike in 'PostExpirationMargin' when it got over the maintenance margin.
Could catch that with:

float([v.value for v in ibis.accountValues() if v.tag == 'Cushion'][0])
float([v.value for v in ibis.accountValues() if v.tag == 'PostExpirationMargin'][0])


Re: How to get market data, specifying exchange=NASDAQ, when ssh to a server that the TWS application is running on

 

On Wed, Nov 15, 2023 at 04:54 AM, misantroop wrote:
As I understand, primary exchange is the native exchange for the instrument, regardless where it could be trading. IBM is trading in USD on LSE, so a contract request for (symbol: IBM, currency: USD) would be ambiguous. IBM/SMART would cause even more issues as there are many IBMs listed. The only way to get NYSE listed IBM without fail is to specify NYSE as primaryExchange.
One silly foolproof option is to keep a static list of primaryExchanges, so every rejection for ambiguity will be retried with the next primaryExchange in the list until a match is made. Alternative for US equity markets is to use the ftp.nasdaqtrader.com symbol files and make a query there.

Very Good point, I hit that one too.
Note:
BTW was on IBM too!
I wonder why IB isn't adding LSE to resolution under SMART as what LSE does trade as IBM have same ISIN as the NYSE one. (different Trading hours ?)


Re: How to catch liquidation warnings and liquidation events?

 

I was just looking at that last week and did some data gathering. I found two sources of information to tap into:

  • A subscription to provides a variety of account related values. For example, "LookAheadMaintMarginReq" seems to flag the upcoming overnight requirements before that margin is actually enforced (around the time TWS adds little flags to the position). In addition to the total margin there are also the "-C" and "-S" versions that focus separately on requirements for commodities and securities.

  • My client also received error callbacks at times with the (undocumented) error code 2148. They came in as "global errors" (meaning id was -1 so that they were not related to a specific requestId or orderId) and had three different messages (there could be more):

    • Based upon a review of your positions and qualifying equity, your account is not projected to be in compliance? with the daily increase in margin requirements from intraday to overnight levels. Note that accounts which? report a margin deficiency when overnight requirements go into effect are subject to forced liquidation of? positions to ensure margin compliance. To avoid this action, please review your "Look Ahead" account balances? within the TWS Account Window and take the steps necessary to reduce margin exposure.? Account: XXXXXXXX

    • ALERT: Your account, while currently margin compliant, maintains qualifying equity (i.e., Equity with Loan? Value) at a level only 10% above that which is required.? Please note that we do not issue margin calls and? should this cushion erode and your account no longer remain margin compliant, it will be subject to forced? position liquidations. To ensure continued compliance, please consider depositing additional funds to increase? equity and/or closing or hedging positions to lessen margin exposure. Further note that funds in transit or? subject to a credit hold are not considered when liquidating positions.? Account: XXXXXXXX

    • URGENT: Please note that the qualifying equity within your account (i.e., Equity with Loan Value) is? insufficient to satisfy the margin requirement and, to restore margin compliance, liquidation of positions may? commence without further notice.? Account: XXXXXXXX

There may also be margin related Bulletins you can catch if you subscribe to but they may be more challenging to parse since they come in as HTML documents with quite some styling and structure tags and are probably subject to change more frequently than error message text.

Your discovery of the "Liquidation" flag in the Excecution class is a good one, too, in case your margin management was unsuccessful and IBKR did close a position for you.

´³¨¹°ù²µ±ð²Ô


How to catch liquidation warnings and liquidation events?

 

Hi guys,

I algo trade 0DTE option combos on ETFs and I would like to be able to take action when a liquidation warning happens or when a position is liquidated due to unsufficient margin.

If these messages can't be caught through API, how could I monitor margin?

I know that the Execution class has a liquidation property set to 1 if the execution was an IB liquidation:






I would something to continuously monitor for warning/liquidation in order to take action when it happens.

How could this be approached?

Thank you!
F


Re: How to get market data, specifying exchange=NASDAQ, when ssh to a server that the TWS application is running on

 

On Wed, Nov 15, 2023 at 06:29 AM, <dungtran0127@...> wrote:

Hi all. Thanks for helping me out. I tested with exchange=ISLAND and it worked on my server. I'm about using exchange=SMART and?primaryExch=NASDAQ but now I understand it is wrong setting.

My TWS version on MacOS is 10.26.2023, while the server version is 10.25.2023.?

Be careful that one day IB may ask you to switch to NASDAQ instead of ISLAND (I guess your good for 1 or 2 years)

Also: SMART is Ok to fetch market data unless you look for very specific exchange volumes (as opposed to prices which seems nearly always same across exchanges when looking historical)
BUT if you use SMART for placeOrder that is a different story, as SMART allow variation on the theme (preference to speed/preference to lower commission/better price/ etc...)
see TWS->File->Global Configuration->Orders->Smart Routing . In general SMART default is the safest choice, especially for low liquidity instrument. Just be aware of what is SMART doing.


Re: How to get market data, specifying exchange=NASDAQ, when ssh to a server that the TWS application is running on

 

Hi all. Thanks for helping me out. I tested with exchange=ISLAND and it worked on my server. I'm about using exchange=SMART and?primaryExch=NASDAQ but now I understand it is wrong setting.

My TWS version on MacOS is 10.26.2023, while the server version is 10.25.2023.?


TickByTick or TickPrice?

 

What is the best way to obtain bid/ask real-time data in your experience?
It looks like TickByTick answers are more concise, but then it is mentioned in the documentation that only 5 concurrent subscriptions are possible.
Any pro/con input is highly appreciated.


Re: How to get market data, specifying exchange=NASDAQ, when ssh to a server that the TWS application is running on

 

As I understand, primary exchange is the native exchange for the instrument, regardless where it could be trading. IBM is trading in USD on LSE, so a contract request for (symbol: IBM, currency: USD) would be ambiguous. IBM/SMART would cause even more issues as there are many IBMs listed. The only way to get NYSE listed IBM without fail is to specify NYSE as primaryExchange.
One silly foolproof option is to keep a static list of primaryExchanges, so every rejection for ambiguity will be retried with the next primaryExchange in the list until a match is made. Alternative for US equity markets is to use the ftp.nasdaqtrader.com symbol files and make a query there.


Re: updateMktDepthL2 missing data points

 

thank you again ´³¨¹°ù²µ±ð²Ô for this great insight. it definitely makes sense to me. if i should paraphrase the issue, we get transaction items without transaction boundaries. it works fine for transactions with only one update, but for transaction with more than one update we get a consistent state of the data only when the last update within the transaction is processed. so we must guess where the transaction boundary is to work with data for which there is a high probability that they are consistent and not broken (in case of a transaction being processed only partially).

i will definitely implement it as i don't want to leave this issue in my code. i thought about it a lot since the last night when i read your post. i will definitely implement it the way you did it as (1) it makes sense to me and (2) you tested it yourself and it works for you (thanks again for sharing your knowledge and experience). i have some minor improvements on my mind that i will try to implement and want to verify whether they really make sense. once i finish my implementation, i'll post here an update with my implementation details and improvements, if they would work. i would like to finish it this week if time permits, i just have some more stuff to resolve on my tws api client implementation.


Re: How to get market data, specifying exchange=NASDAQ, when ssh to a server that the TWS application is running on

 

I don't know. Not seen on TWS.
The logical place should be under Configuration->API but nothing visible about that
Whoever get a clue please share it, I am Interested to not be the last one to know it.

Only place I saw a trace about that is with Gateway ->File->Gateway Layout/Settings, Then grab the XML
in <ApiSettings, look for "sendIslandForUsStocksTradingOnNasdaq"? but this seems more like a provision or unused rubric. It is set with "false" on my machines.

The only 'flags' still raised in my mind is to be careful that an install of latest code on a clean new machine may behave differently than latest code but as an update of a years old installed.


Re: How to get market data, specifying exchange=NASDAQ, when ssh to a server that the TWS application is running on

 

¿ªÔÆÌåÓý

So where is this ¡°Compatibility Mode: Send ISLAND for US Stocks trading on NASDAQ" setting? I can¡¯t find it anywhere (on 10.19 or 10.25).

?

From: [email protected] <[email protected]> On Behalf Of Gordon Eldest via groups.io
Sent: Tuesday, November 14, 2023 9:33 PM
To: [email protected]
Subject: Re: [TWS API] How to get market data, specifying exchange=NASDAQ, when ssh to a server that the TWS application is running on

?

What caught my attention were:

1- This issue is mentioned on Update 20.05.2022 (and the one before too)
2- NASDAQ seems already working in many calls, executing call as they should if set with ISLAND.

And more specifically

This article deal with a settings in TWS 10.16+ which is needed to keep compatibility with ISLAND, (unclear what is the default on new install)
This could explain the issue raised in this thread if dungtran0127@... used 2 different TWS settings, as he seems able to use NASDAQ successfully for data call, on at least one of his platform.

My take is that without IB specific notice, as long as I will see contractDetails() returning ISLAND and not NASDAQ I can keep using ISLAND, but I felt compelled to also implement such a switch.