简体   繁体   English

使用 Python API 下载数据时如何消除(或从控制台抑制)盈透证券错误

[英]How to eliminate (or suppress from console) Interactive Brokers error when downloading data with Python API

I wrote the code below to read information from my accounts at Interactive Brokers:我编写了下面的代码来从我在盈透证券的账户中读取信息:

# Interactive Brokers functions to import data

def read_positions(): #read all accounts positions and return DataFrame with information

    from ibapi.client import EClient 
    from ibapi.wrapper import EWrapper
    from ibapi.common import TickerId
    import pandas as pd

    class ib_class(EWrapper, EClient): 
        def __init__(self): 
            EClient.__init__(self, self)
            self.all_positions = pd.DataFrame([], columns = ['Account','Symbol', 'Quantity', 'Average Cost'])

        def position(self, account, contract, pos, avgCost):
            index = str(account)+str(contract.symbol)
            self.all_positions.loc[index]=account,contract.symbol,pos,avgCost

        def error(self, reqId:TickerId, errorCode:int, errorString:str):
            if reqId > -1:
                print("Error. Id: " , reqId, " Code: " , errorCode , " Msg: " , errorString)

        def positionEnd(self):
            super().positionEnd()
            self.disconnect()

    ib_api = ib_class() 
    ib_api.connect("127.0.0.1", 7496, 0) 
    ib_api.reqPositions()
    current_positions = ib_api.all_positions
    ib_api.run()

    return(current_positions)


def read_navs(): #read all accounts NAVs

    from ibapi.client import EClient 
    from ibapi.wrapper import EWrapper
    from ibapi.common import TickerId
    import pandas as pd

    class ib_class(EWrapper, EClient): 
        def __init__(self): 
            EClient.__init__(self, self)
            self.all_accounts = pd.DataFrame([], columns = ['reqId','Account', 'Tag', 'Value' , 'Currency'])

        def accountSummary(self, reqId, account, tag, value, currency):
            if tag == 'NetLiquidationByCurrency':
                index = str(account)
                self.all_accounts.loc[index]=reqId, account, tag, value, currency

        def error(self, reqId:TickerId, errorCode:int, errorString:str):
            if reqId > -1:
                print("Error. Id: " , reqId, " Code: " , errorCode , " Msg: " , errorString)

        def accountSummaryEnd(self, reqId:int):
                super().accountSummaryEnd(reqId)
                self.disconnect()

    ib_api = ib_class() 
    ib_api.connect("127.0.0.1", 7496, 0) 
    ib_api.reqAccountSummary(9001,"All","$LEDGER")
    current_nav = ib_api.all_accounts
    ib_api.run()

    return(current_nav)

If I call the two functions read_positions() or read_navs() I get the results I want, on DataFrame variables.如果我调用两个函数read_positions()read_navs()我会在 DataFrame 变量上得到我想要的结果。 However, I get an error message (on the console) that reads:但是,我收到一条错误消息(在控制台上),内容如下:

"OSError: [WinError 10038] An operation was attempted on something that is not a socket". “OSError: [WinError 10038] 试图对不是套接字的东西进行操作”。

Before the error message itself, I get a lot of error-related messages:在错误消息本身之前,我收到了很多与错误相关的消息:

unhandled exception in EReader thread Traceback (most recent call last): File "C:\\Users\\xxxxx\\Anaconda3\\lib\\site-packages\\ibapi-9.76.1-py3.7.egg\\ibapi\\reader.py", line 34, in run data = self.conn.recvMsg() File "C:\\Users\\xxxxx\\Anaconda3\\lib\\site-packages\\ibapi-9.76.1-py3.7.egg\\ibapi\\connection.py", line 99, in recvMsg buf = self._recvAllMsg() File "C:\\Users\\xxxxx\\Anaconda3\\lib\\site-packages\\ibapi-9.76.1-py3.7.egg\\ibapi\\connection.py", line 119, in _recvAllMsg buf = self.socket.recv(4096) EReader 线程 Traceback 中未处理的异常(最近一次调用最后一次):文件“C:\\Users\\xxxxx\\Anaconda3\\lib\\site-packages\\ibapi-9.76.1-py3.7.egg\\ibapi\\reader.py”,行34、在运行data = self.conn.recvMsg()文件“C:\\Users\\xxxxx\\Anaconda3\\lib\\site-packages\\ibapi-9.76.1-py3.7.egg\\ibapi\\connection.py”,行99、在recvMsg buf = self._recvAllMsg()文件“C:\\Users\\xxxxx\\Anaconda3\\lib\\site-packages\\ibapi-9.76.1-py3.7.egg\\ibapi\\connection.py”,第119行,在 _recvAllMsg buf = self.socket.recv(4096)

The helpdesk from IB refuses to answer my question: how do I either avoid this error message or suppress it? IB 的帮助台拒绝回答我的问题:我该如何避免或抑制此错误消息? I don't know if it is something I'm doing wrong or if this is a bug on their API.我不知道这是我做错了什么,还是他们 API 上的错误。 As long as I can avoid this junk printed on my console, I will be OK.只要我能避免在我的控制台上打印这些垃圾,我就可以了。 Any guidance is much appreciated.非常感谢任何指导。

I had a similar problem with the 9.76.01 API, so I went back to 9.74.01, which doesn't have this issue.我在 9.76.01 API 上遇到了类似的问题,所以我回到了 9.74.01,它没有这个问题。

I tried to suppress the error with try/catch blocks, but I never got that to work.我试图用 try/catch 块来抑制错误,但我从来没有让它起作用。

Matt Scarpino马特·斯卡皮诺
Algorithmic Trading with Interactive Brokers与盈透证券的算法交易

Matt's answer above is correct: it was an API bug! Matt 上面的回答是正确的:这是一个 API 错误! I'm only adding this answer to provide more clear steps on how to downgrade to the older version:我只是添加此答案以提供有关如何降级到旧版本的更清晰的步骤:

1) Download the older version from here: http://interactivebrokers.github.io/downloads/TWS%20API%20Install%20974.01.msi 1) 从这里下载旧版本: http : //interactivebrokers.github.io/downloads/TWS%20API%20Install%20974.01.msi

IB doesn't show the links for older versions but they keep the file on the Github (note the version name at the end of the link address) IB 不显示旧版本的链接,但他们将文件保存在 Github 上(注意链接地址末尾的版本名称)

2) Uninstall the current version. 2) 卸载当前版本。 From IB's own website, do the following:在 IB 自己的网站上,执行以下操作:

  • Uninstall the API from the "Add/Remove Tool" in the Windows从 Windows 中的“添加/删除工具”卸载 API
    Control Panel as usual像往常一样控制面板
  • Delete the C:\\TWS API\\ folder if any files are still remaining to prevent a version mismatch.如果仍有任何文件,请删除 C:\\TWS API\\ 文件夹以防止版本不匹配。
  • Locate the file "C:\\Windows\\SysWOW64\\TwsSocketClient.dll".找到文件“C:\\Windows\\SysWOW64\\TwsSocketClient.dll”。 Delete this file.删除此文件。 [didn't find this file] [没有找到这个文件]
  • Restart the computer before installing a different API version.在安装不同的 API 版本之前重新启动计算机。

3) Install the API using the .msi file 3) 使用 .msi 文件安装 API

4) Run the Anaconda prompt and navigate to the dir C:\\TWS API\\source\\pythonclient 4) 运行 Anaconda 提示符并导航到目录 C:\\TWS API\\source\\pythonclient

5) Run: "python setup.py install" 5)运行:“python setup.py install”

6) After python setup.py install, restart Spyder (if it was opened; I closed mine before step #5 above) 6)安装python setup.py后,重启Spyder(如果它已经打开;我在上面的步骤#5之前关闭了我的)

After I installed this older version, the error disappeared!我安装这个旧版本后,错误消失了!

So instead of downgrading, I found a quick fix to suppressing the error message.因此,我没有降级,而是找到了抑制错误消息的快速修复方法。 Go to the script where its messing up at, it should be connection.py and at line 119 at the very bottom.转到它搞砸的脚本,它应该是 connection.py 和最底部的第 119 行。 This is what I did to catch the error and it worked.这就是我为捕获错误所做的工作并且它起作用了。

while cont and self.socket is not None:
            try:
                buf = self.socket.recv(4096)
                allbuf += buf
                logger.debug("len %d raw:%s|", len(buf), buf)

                if len(buf) < 4096:
                    cont = False
            except OSError:
                pass

I was able to silence the error, however I am not sure whether this fix breaks anything else.我能够消除错误,但是我不确定此修复程序是否会破坏其他任何内容。 Maybe someone who has an in-depth understanding of the API code can tell us whether this is ok.也许对API代码有深入了解的人可以告诉我们这是否可以。

In connection.py在连接.py

    def _recvAllMsg(self):
    cont = True
    allbuf = b""

    while cont and self.socket is not None:
        try: #this line added
            buf = self.socket.recv(4096)
        except OSError: #this line added
            buf = b'' #this line added
        allbuf += buf
        logger.debug("len %d raw:%s|", len(buf), buf)

        if len(buf) < 4096:
            cont = False

    return allbuf

I finally found an answer to this issue: you can see the solution below:我终于找到了这个问题的答案:你可以看到下面的解决方案:

https://groups.io/g/twsapi/message/43333 https://groups.io/g/twsapi/message/43333

It involves making a quick change on the connection.py file and re-installing TWS API.它涉及对 connection.py 文件进行快速更改并重新安装 TWS API。 I left the answer posted here before in case someone wants to install an older version for some reason.我之前在这里留下了答案,以防有人出于某种原因想要安装旧版本。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 如何等待交互式经纪人从 tws api 下载数据? - how to wait for data to download in tws api from interactive brokers? 如何从交互式经纪人API获取历史股价数据? - How to get historical stock price data from interactive brokers API? 盈透证券交易平台,Python API - Interactive Brokers TWS, Python API 使用 Python 的 TWS 交互式经纪商 API。 通过多种方法接收时无法将实时数据放在一起 - TWS interactive brokers API with Python. Trouble putting live data together when received by several methods methods 如何使用 IB API 或 ib_insync 为 Interactive 代理设置错误处理程序? Python - How to set up an error handler for Interactive brokers using IB API or ib_insync? Python 如何使用本机Interactive Brokers Python API创建条件订单? - How to create a conditional order using the native Interactive Brokers Python API? 如何从Interactive Brokers API获取新闻合同详细信息? - How to obtain News Contract Details from the Interactive Brokers API? 如何从盈透证券 API 获取合约详情? - How to obtain Contract Details from the Interactive Brokers API? 如何始终如一地从 IBKR API(互动经纪商)返回头寸? - How to return positions from IBKR API (interactive brokers) consistently? 更新停止订单 API Interactive Brokers Python - Update stop order API Interactive Brokers Python
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM