Keyboard Shortcuts
Likes
- Twsapi
- Messages
Search
Re: C++ preventing EReader reading when socket is closed
@Gordon, @Buddy,
"mountain"?? : hardly. There is no impact to existing code with this proposed change (tested). I am simply adding functionality that allows users to manually stop the thread that they started manually.? In fact I can leave the destructor of EReader the same as it was without swapping anything and just create a new function "stop()" which will allow users to disconnect cleanly if they desire to, (Note to Gordon on your concern about the initial use of EReader during the connection, this is what the "if (m_hReadThread)" statement takes care of in the original TWS API code which is still there in my proposed change.) Let me remind you that the current situation results in a 509 error, which is basically the API's way of saying something bad happened and I do not know what it is. Your code must be bad, which is not the case here. It is the API code that is bad. Now that we know what causes it, we can probably live with it and safely ignore it, but personally I don't like that sort of situation. If the developers intended to use this way of disconnecting the socket, then they should have properly taken care of the error message it creates. The fact that they didn't means that what they coded was unintentional and therefore is clearly a bug. A bug needs to be fixed. However, I realise changing (adding to) the interface will make the C++ interface different than the other languages which is probably not desirable. The only way to correct this and make the existing interface the same is to create an EMutex variable which is shared by both EReader and EClientSocket (suggest using a composition pattern here). Changes to the m_isAlive variable need to be locked by the mutex as well as inside the "while(m_isAlive)" loop. This is a larger code change and needs more care to be done right but it is not that difficult and I have implemented it successfully as well. In fact using EMutex here does not slow the loop down (checking the mutex is as simple as reading a flag) since the only time it is ever locked is when we are disconnecting which means speed is not a "critical trading" issue. I agree it is good to have this thread capture this discussion for the record but I will definitely raise this problem to the coders as I still firmly believe this to be a bug. I do not wish to have to fix this myself every time there is a new API update. |
Re: C++ preventing EReader reading when socket is closed
Yeah, I see most of this as making a mountain out of a molehill. It strikes me, largely, as a misunderstanding; much like issuing a SIGKILL but expecting SIGTERM. If you are familiar with unix signal processing you know that SIGKILL is immediately forced upon the process by the OS and the process my be left in an untidy state. SIGTERM, on the other hand, gives the process an opportunity to clean up and exit gracefully. Since the API code is readily available, folks can implement their own version of EReader which suits their preference in this regard. Therefore the distinction becomes moot. There may be some chance of acceptance for a minor pull request which, e.g., swaps the calls to the thread join and socket disconnect. But, even this could be seen as a dog chasing it's own tail since the argument would merely come down to the dislike of a default. Moreover though, when you consider that the code for EReader hasn't changed in years... even a small change becomes unlikely. And, the suggestion of anything "major", like an intermediate "stop" method, becomes far fetched IMHO. It's certainly an interesting nuance but probably better addressed by documentation alone. At least we have this thread of conversation now for reference :-) |
How to estimate order execution impact on excess liquidity?
Assuming that an order execution has $cash_balance_delta?impact on cash balance and $margin_delta?on margin, is it correct to assume that the impact on?excess liquidity is
$excess_liquidity_delta =? $cash_balance_delta - $margin_delta?Is this accurate? Is there any way to have IB estimate?excess liquidity prior to the order execution instead? TIA. |
Re: C++ preventing EReader reading when socket is closed
I like evolution, so I may be wrong but here I am not sure I would flag this as a bug. |
Re: Implied Volatility of an EXPIRY
Resurrecting an old thread as I have a similar question.
I think I've convinced myself that the way the "IV of a specific chain" is calculated is the same way that the VIX is calculated as illustrated in this white paper:??There is no Black-Scholles of any sort going on with this calculation.? That means that from the API, it's possible to calculate the _current_ IV of a specific expiry; but not the _history_ of the IV that's shown in Volatility Lab. Has anyone figured out a way to do that?? (I suspect the answer is it's not possible.? If that's the case, are people using IVolatility.com, which looks like there is no longer any free component.? What about getvolatility.com?) My other question is what exactly is returned when you request historical volatility from the API?? My assumption is that it is something similar to the VIX calculation where the two expiries closet to 30 days are interpolated to that 30 day mark, although I haven't tried to do a sample calculation to confirm. |
Re: APIPending status?
Colin Beveridge
Thanks, 闯ü谤驳别苍, being less of a doofus with the contract definition seems to have helped.
?
(I had seen that documentation -- I stand by my opinion that it could be better documented; I think that "Uncommonly received" is a less helpful message than, say, "if this occurs repeatedly, check you are sending a properly-defined contract". In any case, I hope future people hitting the same problem[^0] will find this thread and find it helpful.)[^0]: Even if it's just me, I'm ok with that. |
Re: C++ preventing EReader reading when socket is closed
... I should add with the proposed code change, you can now stop the reader and disconnect the socket without actually destroying the EReader object by doing the following:
The last line here is where I wait for my? own message processing thread to end. This is now very clean and you can connect and disconnect from TWS without error and without having to destroy the EReader. |
Re: C++ preventing EReader reading when socket is closed
What makes me feel uneasy is that according to the documentation:
It makes users think that by calling eDisconnect() you can safely disconnect from TWS without causing errors but we have shown that this is not the case. You must "stop" the thread, then disconnect from the socket, in that order. It is not possible for eDisconnect() to do that without creating a mutex locking system that shares mutexes between both EClientSocket and EReader. I agree with you that adding this complexity is not the right approach, for one as it will slow down the message receiving loop. What I am opting for and will propose in the GitHub when I get the approval to create a branch, is creating an EReader::stop() function like this: then modifying the destructor to the following: Then I will also propose that the C++ documentation for the eDisconnect() function be changed to say that to disconnect safely you must call EReader::stop() before calling EClientSocket::eDisconnect(). |
Re: C++ preventing EReader reading when socket is closed
On Sun, Oct 1, 2023 at 03:15 PM, David Armour wrote:
IDK if this is what made you uneasy or what you meant, but maybe you'd prefer to see the call to eDisconnect happen in readToQueue as the penultimate action (i.e. before the final signal is issued)? In retrospect this makes a bit more sense to me. |
Re: ReqHistoricalTicks() & Futures Data Limitations, Rolling Expiring Contracts
My tool is extremely similar to yours, so no bottlenecks in code either. On Sun, Oct 1, 2023 at 8:07 PM Brendan Lydon <blydon12@...> wrote:
|
Re: ReqHistoricalTicks() & Futures Data Limitations, Rolling Expiring Contracts
I am doing this from my sim account. I should probably switch to my live account to hopefully get better times? On Sun, Oct 1, 2023 at 7:04 PM 闯ü谤驳别苍 Reinold via <TwsApiOnGroupsIo=[email protected]> wrote: Just after 15:10 US/Central this afternoon, I request Historical TickByTickLast data for Friday's NQZ3 session (20230928 17:00 through 20230929 16:00 US/Central): |
Re: ReqHistoricalTicks() & Futures Data Limitations, Rolling Expiring Contracts
Just after 15:10 US/Central this afternoon, I request Historical TickByTickLast data for Friday's NQZ3 session (20230928 17:00 through 20230929 16:00 US/Central):
toggle quoted message
Show quoted text
That means the tool makes about 9 out of 10 requests immediately (a few micro seconds) after the callback for the previous request. There is a short processing delay before every tenth request (5ms to 40ms) for the data serialization and file storage. Now, the interesting finding is the discrepancy between average and median response times. IBKR paced the responses within chunks of ~60 seconds, each time with roughly the following rhythm:
Attached a couple charts of what that looked like. I do not have data on how long they keep that 60 second chunk rhythm up in case you download a couple years worth of data. My gut tells me that you will not be able to keep up the less-than 3 second average for very long runs. 闯ü谤驳别苍 On Sun, Oct 1, 2023 at 01:39 PM, <blydon12@...> wrote: Running a script right now to get 2 years of tick data for NQ. Seems to be restricting my request limits to every 6 seconds. Are there times when this could improve? It is Sunday @ 2:30 p.m. where I am right now for reference. |
Re: APIPending status?
First of all, order status ApiPending is not an error condition. It is the state of your order(s) right after you placed them. And the section of the does provide high-level descriptions of when to expect the various order stats. They say for :
I'd review the contract definition and you should seriously think about requesting a well configured contract from IBKR via instead of initializing various fields yourselves. For example, I am not sure why you set a "strike" for am STK instrument, and initialize trading class, symbol, and local symbol will have important fields initialized with meaningful values. And then you use a Time in Force of IOT. Does the behavior change if you place the order with a simpler TIF of, say GTC or DAY? 闯ü谤驳别苍 On Sun, Oct 1, 2023 at 03:22 PM, Colin Beveridge wrote:I'm now having a seemingly identical problem using IB's python client -- I can only imagine I'm doing something boneheaded, but without documentation on the error, I'm a bit stuck. |
Re: APIPending status?
Colin Beveridge
I'm now having a seemingly identical problem using IB's python client -- I can only imagine I'm doing something boneheaded, but without documentation on the error, I'm a bit stuck.
Running on v177, I set up an order like so: ??????? con = Contract() ??????? con.conId = 76792991 ??????? con.symbol = "TSLA" ??????? con.secType = "STK" ??????? con.strike = 0. ??????? con.exchange = "SMART" ??????? con.primaryExchange = "NASDAQ" ??????? con.currency = "USD" ??????? con.tradingClass = "NMS" ??????? con.localSymbol = "TSLA" ??????? order = Order() ??????? order.action = "BUY" ??????? order.totalQuantity = 1. ??????? order.orderType = "MKT" ??????? order.tif = "IOC" ??????? order.account = "[account name]" ??????? app.placeOrder([order id], con, order) This sends: 3-[order id]-76792991-TSLA-STK--0.0---SMART-NASDAQ-USD-TSLA-NMS---BUY-1.0-MKT---IOC--[account name]--0--1-0-0-0-0-0-0-0--0-------0---1-0---0---0-0--0------0-----0-----------0---0-0---0--0-0-0-0--1.7976931348623157e+308-1.7976931348623157e+308-1.7976931348623157e+308-1.7976931348623157e+308-1.7976931348623157e+308-0----1.7976931348623157e+308-----0-0-0--2147483647-2147483647-0--- ... but a call to openOrders gives OrderStatus. Id: [order id] Status: ApiPending Filled: 0 Remaining: 1 AvgFillPrice: 0 PermId: 0 ParentId: 0 LastFillPrice: 0 ClientId: 3 WhyHeld:? MktCapPrice: 0 As I say, I imagine I'm setting something up incorrectly. If anyone can point me towards what (or even where to look), I'd be super grateful. |
Re: ReqHistoricalTicks() & Futures Data Limitations, Rolling Expiring Contracts
Running a script right now to get 2 years of tick data for NQ. Seems to be restricting my request limits to every 6 seconds. Are there times when this could improve? It is Sunday @ 2:30 p.m. where I am right now for reference.
|
Re: C++ preventing EReader reading when socket is closed
On Sun, Oct 1, 2023 at 03:15 PM, David Armour wrote:
You may see this as a wart but I, personally, won't comment with regard to how intuitive things are or any design aesthetic. I will say that consideration should be given to backward compatibility and just how much existing code would break (and therefore need to change) if the disconnect where removed from the destructor. Just some food for thought... since there's usually ripple effects, unintended consequences, and API stability is actually very important. Also, I don't think it's wise to hold off fixing some simple, obvious, and existing issue merely because there's an intention of addressing it in a more significant re-design. As they say, there is no time like the present and I appreciate small and tractable, incremental changes. However, this may come down to a judgment call. Since, I guess, people have indeed been ignoring it or working around it (or it's simply gone unnoticed). After all, it only happens late in the game when there usually isn't much network activity expected or necessarily happening.
A pull request is probably the best way to go about this: |
Re: C++ preventing EReader reading when socket is closed
I agree with everything you said although I am not entirely happy with my final solution. I do not feel that destroying the EReader object is the correct way to disconnect. It is certainly not intuitive which means I cannot be the only person finding this problem. Is everybody using C++ just ignoring this error?
Anyway, I will sleep on it one more night before submitting a bug report. Is there a special place to report API bugs or do we just raise ticket as usual? |
Re: C++ preventing EReader reading when socket is closed
On Sun, Oct 1, 2023 at 10:02 AM, David Armour wrote:
You're welcome. I think you've found an interesting oversight.
Yeah, superficially and at first blush it would seem that way. But it'd be a mistake to think so. I can understand how that initial thought may have fooled the original author into thinking the code was correct though. All this is post-mortem speculation on my part however. Nevertheless, once considered more thoughtfully, it becomes apparent that nothing prevents the destructor from being called while the processing thread's readToQueue is in the while block. The std::atomic will only insure that reading and writing m_isAlive from multiple threads is well-defined; but guarantees nothing w.r.t. the destructor and what's happening in the while loop.
"Pause", with a sleep or something? No... that's surely a game of whack-a-mole. It might work sometimes, depending on unpredictable factors, and might not. It can be fun to experiment with the timing while you investigate though. You can also try playing w/ ordering by running the code on a single core/cpu and see how that affects things.
Compiler optimizations fall somewhat into the category of "unpredictable factors" I alluded to (although they'd be deterministic given the compiler source and enough work). It's a bit surprising that a critical section wasn't implemented via mutex, but maybe the author wanted to avoid a performance penalty.
Anyway... I think you found a legitimate problem and I wouldn't worry about it too much. I like your proposed solution as well. Joining the thread and then disconnecting makes clear sense to me. And, as long as m_pClientSocket isn't being shared all over the place I don't see a reason to use more complicated locking via mutex. If I were the reviewer I could see signing off after some confirmation tests... open a ticket and see what they have to say. If you submit a patch remember to change the IB_POSIX ifdef block too :-) |
Re: C++ preventing EReader reading when socket is closed
Thanks for your comment Buddy.
I agree that the logic would seem that setting m_isAlive to false during the ~EReader() call should prevent the code trying to read from the socket. I tried playing around with that. If I pause after m_isAlive is set to false, then continue, the code works successfully without 509 error. It is as if at full speed the atomic operation is not being completed before the call to eDisconnect() happens. On Visual Studio this even happens when I turn off all Optimisations. As eDisconnect() does not use anything related to that atomic, I wonder if the compiler is parallelising the operation as all atomic operations are very slow. I also noticed that eDisconnect() sets m_fd = -1.? This should prevent the call to processNonBlockingSelect() from trying to call onReceive() which ultimately triggers receive() and recv() causing the error. Again the setting of the atomic variable is not being done in time. I am still scratching my head over this. I suspect some synchronization issue between the various threads. |
Re: C++ preventing EReader reading when socket is closed
I guess the assumption is that using
But it does not, so I take your point. |