def get_message(self): """ 亲测可用 用来抓信息的 """ time.sleep(2) while not self.msg_queue.empty(): text = self.msg_queue.get(block=True, timeout=0.2) # print("貌似下面会接着自动调用nextValidId函数") # print(f"报文:{text}") fields = comm.read_fields(text) self.decoder.interpret(fields)
def test_readFields(self): text1 = "ABCD" text2 = "123" msg = comm.make_msg(comm.make_field(text1) + comm.make_field(text2)) (size, text, rest) = comm.read_msg(msg) fields = comm.read_fields(text) self.assertEqual(len(fields), 2, "incorrect number of fields") self.assertEqual(fields[0].decode(), text1) self.assertEqual(fields[1].decode(), text2)
def checkQueue(self): try: print("*********Checking Queue***************") text = self.msg_queue.get(block=True, timeout=0.2) except queue.Empty: print("-------------Queue is empty---------------") logging.debug("queue.get: empty") else: print("+++++++++++Reading Data++++++++++++++++++") fields = comm.read_fields(text) logging.debug("fields %s", fields) #print(datetime.now(), 'CALLING INTERPRETER TOO') self.decoder.interpret(fields)
def run(self): if not self.done and self.isConnected(): try: text = self.msg_queue.get(block=True, timeout=0.2) if len(text) > MAX_MSG_LEN: errorMsg = "%s:%d:%s" % (BAD_LENGTH.msg(), len(text), text) self.wrapper.error(NO_VALID_ID, BAD_LENGTH.code(), errorMsg) self.disconnect() # break fields = comm.read_fields(text) self.decoder.interpret(fields) except Empty: pass
def run(self): """ This is the function that has the message loop. Extended copy of the EClient run() + onLoopIteration() hook + onIdle() hook """ try: while not self.done and (self.isConnected() or not self.msg_queue.empty()): try: try: # Hook to process messages/events from other sources. self.onLoopIteration() text = self.msg_queue.get(block=True, timeout=0.2) if len(text) > MAX_MSG_LEN: self.wrapper.error( NO_VALID_ID, BAD_LENGTH.code(), "%s:%d:%s" % (BAD_LENGTH.msg(), len(text), text)) self.disconnect() break except queue.Empty: # Hook to process something while no messages are # comming from the TWS. # self.onIdle() logging.debug("queue.get: empty") else: fields = comm.read_fields(text) logging.debug("fields %s", fields) self.decoder.interpret(fields) except (KeyboardInterrupt, SystemExit): logging.info("detected KeyboardInterrupt, SystemExit") self.keyboardInterrupt() self.keyboardInterruptHard() except BadMessage: logging.info("BadMessage") self.conn.disconnect() except Exception: logging.error(traceback.format_exc()) logging.debug("conn:%d queue.sz:%d", self.isConnected(), self.msg_queue.qsize()) finally: self.disconnect()
def run(self): """ Reimplement the original run message loop of eclient. Remove all unnecessary try...catch... and allow exceptions to interrupt loop. """ while not self.done and self.isConnected(): try: text = self.msg_queue.get(block=True, timeout=0.2) if len(text) > MAX_MSG_LEN: errorMsg = "%s:%d:%s" % (BAD_LENGTH.msg(), len(text), text) self.wrapper.error(NO_VALID_ID, BAD_LENGTH.code(), errorMsg) self.disconnect() break fields = comm.read_fields(text) self.decoder.interpret(fields) except Empty: pass
def run(self): """ Reimplement the original run message loop of eclient. Remove all unnecessary try...catch... and allow exceptions to interrupt loop. """ while not self.done and self.isConnected(): try: text = self.msg_queue.get(block=True, timeout=0.2) if len(text) > MAX_MSG_LEN: errorMsg = "%s:%d:%s" % (BAD_LENGTH.msg(), len(text), text) self.wrapper.error( NO_VALID_ID, BAD_LENGTH.code(), errorMsg ) self.disconnect() break fields = comm.read_fields(text) self.decoder.interpret(fields) except Empty: pass
def runnable(self, func): """This is the function that has the message loop.""" try: while not self.done and (self.conn.isConnected() or not self.msg_queue.empty()): try: try: text = self.msg_queue.get(block=True, timeout=0.2) if len(text) > MAX_MSG_LEN: self.wrapper.error( NO_VALID_ID, BAD_LENGTH.code(), "%s:%d:%s" % (BAD_LENGTH.msg(), len(text), text)) self.disconnect() break except queue.Empty: if datetime.datetime.utcnow( ) - self.lastStamp > datetime.timedelta(seconds=30): func() self.lastStamp = datetime.datetime.utcnow() logging.debug("queue.get: empty") else: fields = comm.read_fields(text) logging.debug("fields %s", fields) self.decoder.interpret(fields) except (KeyboardInterrupt, SystemExit): logging.info("detected KeyboardInterrupt, SystemExit") self.keyboardInterrupt() self.keyboardInterruptHard() except BadMessage: logging.info("BadMessage") self.conn.disconnect() logging.debug("conn:%d queue.sz:%d", self.conn.isConnected(), self.msg_queue.qsize()) finally: self.disconnect()
def send_msg(self, msg): """Mock send to ib by interpreting and placing on receive queue. Args: msg: message to be sent (i.e., interpreted and queued) """ logger.debug('entered with message %s', msg) (size, msg2, buf) = read_msg(msg) logger.debug('size, msg, buf: %d, %s, %s ', size, msg2, buf) fields = read_fields(msg2) logger.debug('fields: %s', fields) recv_msg = b'' ####################################################################### # get version and connect time (special case - not decode able) ####################################################################### if msg == b'API\x00\x00\x00\x00\tv100..157': current_dt = datetime.now( tz=timezone(offset=timedelta(hours=5))).\ strftime('%Y%m%d %H:%M:%S') # recv_msg = b'\x00\x00\x00\x1a157\x0020210301 23:43:23 EST\x00' recv_msg = b'\x00\x00\x00\x1a157\x00' \ + current_dt.encode('utf-8') + b' EST\x00' ####################################################################### # reqId (get next valid requestID) # b'\x00\x00\x00\x0871\x002\x000\x00\x00' ####################################################################### elif int(fields[0]) == OUT.START_API: logger.info('startAPI detected') # recv_msg = b'\x00\x00\x00\x069\x001\x001\x00' if self.reqId_timeout: # if testing timeout case recv_msg = make_msg('0') # simulate timeout else: # build the normal next valid id message recv_msg = make_msg( make_field(IN.NEXT_VALID_ID) + make_field('1') + make_field('1')) logger.debug('recv_msg: %s', recv_msg) ####################################################################### # Handle special test cases for request disconnect and timeout ####################################################################### elif self.simulate_request_disconnect: # if testing timeout case time.sleep(2) # allow some time for request to get into wait loop recv_msg = b'' # simulate disconnect elif self.simulate_request_timeout: recv_msg = make_msg('0') # simulate timeout ####################################################################### # reqMatchingSymbols ####################################################################### elif int(fields[0]) == OUT.REQ_MATCHING_SYMBOLS: logger.info('reqMatchingSymbols detected') reqId = int(fields[1]) pattern = fields[2].decode(errors='backslashreplace') logger.debug('pattern: %s', pattern) # construct start of receive message for wrapper build_msg = make_field(IN.SYMBOL_SAMPLES) + make_field(reqId) # find pattern matches in mock contract descriptions symbol_starts_with_pattern = \ self.contract_descriptions['symbol'].map( lambda symbol: symbol.startswith(pattern)) match_descs = \ self.contract_descriptions[symbol_starts_with_pattern] # match_descs = self.contract_descriptions.loc[ # self.contract_descriptions['symbol'].str. # startswith(pattern)] # limit the number found as ib does num_found = min(self.MAX_CONTRACT_DESCS_RETURNED, match_descs.shape[0]) # add the number of descriptions to the receive message build_msg = build_msg + make_field(num_found) for i in range(num_found): build_msg = build_msg \ + make_field(match_descs.iloc[i].conId) \ + make_field(match_descs.iloc[i].symbol) \ + make_field(match_descs.iloc[i].secType) \ + make_field(match_descs.iloc[i].primaryExchange) \ + make_field(match_descs.iloc[i].currency) \ + make_field(len(match_descs.iloc[i].derivativeSecTypes)) for dvt in match_descs.iloc[i].derivativeSecTypes: build_msg = build_msg + make_field(dvt) recv_msg = make_msg(build_msg) ####################################################################### # reqContractDetails ####################################################################### elif int(fields[0]) == OUT.REQ_CONTRACT_DATA: logger.info('reqContractDetails detected') version = int(fields[1]) reqId = int(fields[2]) conId = int(fields[3]) # construct start of receive message for wrapper start_msg = make_field(IN.CONTRACT_DATA) \ + make_field(version) \ + make_field(reqId) # find pattern matches in mock contract descriptions # fow now, just conId match_descs = self.contract_descriptions.loc[ self.contract_descriptions['conId'] == conId] for i in range(len(match_descs)): build_msg = start_msg \ + make_field(match_descs.iloc[i].symbol) \ + make_field(match_descs.iloc[i].secType) \ + make_field(match_descs.iloc[i]. lastTradeDateOrContractMonth) \ + make_field(match_descs.iloc[i].strike) \ + make_field(match_descs.iloc[i].right) \ + make_field(match_descs.iloc[i].exchange) \ + make_field(match_descs.iloc[i].currency) \ + make_field(match_descs.iloc[i].localSymbol) \ + make_field(match_descs.iloc[i].marketName) \ + make_field(match_descs.iloc[i].tradingClass) \ + make_field(match_descs.iloc[i].conId) \ + make_field(match_descs.iloc[i].minTick) \ + make_field(match_descs.iloc[i].mdSizeMultiplier) \ + make_field(match_descs.iloc[i].multiplier) \ + make_field(match_descs.iloc[i].orderTypes) \ + make_field(match_descs.iloc[i].validExchanges) \ + make_field(match_descs.iloc[i].priceMagnifier) \ + make_field(match_descs.iloc[i].underConId) \ + make_field(match_descs.iloc[i].longName) \ + make_field(match_descs.iloc[i].primaryExchange) \ + make_field(match_descs.iloc[i].contractMonth) \ + make_field(match_descs.iloc[i].industry) \ + make_field(match_descs.iloc[i].category) \ + make_field(match_descs.iloc[i].subcategory) \ + make_field(match_descs.iloc[i].timeZoneId) \ + make_field(match_descs.iloc[i].tradingHours) \ + make_field(match_descs.iloc[i].liquidHours) \ + make_field(match_descs.iloc[i].evRule) \ + make_field(match_descs.iloc[i].evMultiplier) \ + make_field(match_descs.iloc[i].secIdListCount) for tv in match_descs.iloc[i].secIdList: build_msg += make_field(tv) build_msg += make_field(match_descs.iloc[i].aggGroup) \ + make_field(match_descs.iloc[i].underSymbol) \ + make_field(match_descs.iloc[i].underSecType) \ + make_field(match_descs.iloc[i].marketRuleIds) \ + make_field(match_descs.iloc[i].realExpirationDate) \ + make_field(match_descs.iloc[i].stockType) recv_msg = make_msg(build_msg) self.msg_rcv_q.put(recv_msg, timeout=5) build_msg = make_field(IN.CONTRACT_DATA_END) \ + make_field(version) \ + make_field(reqId) recv_msg = make_msg(build_msg) ####################################################################### # queue the message to be received ####################################################################### self.msg_rcv_q.put(recv_msg, timeout=5)
def getMessage(self, wait=3): time.sleep(wait) while not self.msg_queue.empty(): text = self.msg_queue.get(block=True, timeout=0.2) fields = comm.read_fields(text) self.decoder.interpret(fields)