def _update_order(self, order_info): """ Order update. Args: order_info: Order information. Returns: None. """ order_no = str(order_info["order_id"]) state = order_info["state"] remain = float(order_info["size"]) - float(order_info["filled_size"]) ctime = tools.utctime_str_to_mts(order_info["ctime"]) utime = tools.utctime_str_to_mts(order_info["utime"]) if state == "-2": status = ORDER_STATUS_FAILED elif state == "-1": status = ORDER_STATUS_CANCELED elif state == "0": status = ORDER_STATUS_SUBMITTED elif state == "1": status = ORDER_STATUS_PARTIAL_FILLED elif state == "2": status = ORDER_STATUS_FILLED else: logger.error("status error! order_info:", order_info, caller=self) return None order = self._orders.get(order_no) if order: order.remain = remain order.status = status order.price = order_info["price"] else: info = { "platform": self._platform, "account": self._account, "strategy": self._strategy, "order_no": order_no, "action": ORDER_ACTION_BUY if order_info["side"] == "buy" else ORDER_ACTION_SELL, "symbol": self._symbol, "price": order_info["price"], "quantity": order_info["size"], "remain": remain, "status": status, "avg_price": order_info["price"] } order = Order(**info) self._orders[order_no] = order order.ctime = ctime order.utime = utime SingleTask.run(self._order_update_callback, copy.copy(order)) if status in [ ORDER_STATUS_FAILED, ORDER_STATUS_CANCELED, ORDER_STATUS_FILLED ]: self._orders.pop(order_no)
async def process(self, msg): """ 处理websocket上接收到的消息 """ logger.debug("msg:", msg, caller=self) if not isinstance(msg, dict): return table = msg.get("table") if table == "orderBook10": # 订单薄数据 for item in msg["data"]: symbol = item.get("symbol") orderbook = { "platform": self._platform, "symbol": symbol, "asks": item.get("asks"), "bids": item.get("bids"), "timestamp": tools.utctime_str_to_mts(item["timestamp"]) } EventOrderbook(**orderbook).publish() logger.info("symbol:", symbol, "orderbook:", orderbook, caller=self) elif table == "trade": # 成交数据 for item in msg["data"]: symbol = item["symbol"] trade = { "platform": self._platform, "symbol": symbol, "action": ORDER_ACTION_BUY if item["side"] else ORDER_ACTION_SELL, "price": "%.1f" % item["price"], "quantity": str(item["size"]), "timestamp": tools.utctime_str_to_mts(item["timestamp"]) } EventTrade(**trade).publish() logger.info("symbol:", symbol, "trade:", trade, caller=self) elif table == "tradeBin1m": # 1分钟K线数据 for item in msg["data"]: symbol = item["symbol"] kline = { "platform": self._platform, "symbol": symbol, "open": "%.1f" % item["open"], # 开盘价 "high": "%.1f" % item["high"], # 最高价 "low": "%.1f" % item["low"], # 最低价 "close": "%.1f" % item["close"], # 收盘价 "volume": str(item["volume"]), # 交易量 "timestamp": tools.utctime_str_to_mts(item["timestamp"]), # 时间戳 "kline_type": MARKET_TYPE_KLINE } EventKline(**kline).publish() logger.info("symbol:", symbol, "kline:", kline, caller=self)
def _convert_order_format(self, order_info): order_no = str(order_info["order_id"]) symbol = order_info["instrument_id"] ctime = tools.utctime_str_to_mts(order_info["created_at"]) utime = tools.utctime_str_to_mts(order_info["timestamp"]) state = order_info["state"] if state == "-2": status = ORDER_STATUS_FAILED elif state == "-1": status = ORDER_STATUS_CANCELED elif state == "0": status = ORDER_STATUS_SUBMITTED elif state == "1": status = ORDER_STATUS_PARTIAL_FILLED elif state == "2": status = ORDER_STATUS_FILLED else: status = ORDER_STATUS_NONE if order_info["type"] == "market": order_type = ORDER_TYPE_MARKET else: if order_info["order_type"] == "3": order_type = ORDER_TYPE_IOC else: order_type = ORDER_TYPE_LIMIT action = ORDER_ACTION_BUY if order_info[ "side"] == "buy" else ORDER_ACTION_SELL if order_type == ORDER_TYPE_MARKET and action == ORDER_ACTION_BUY: quantity = float(order_info["notional"]) #市价买单传入的是金额,输出的也要是金额 remain = quantity - float( order_info["filled_notional"]) #市价买单传入的是金额,输出的也要是金额 else: quantity = float(order_info["size"]) remain = quantity - float(order_info["filled_size"]) price_str = order_info["price"] if not price_str: price_str = "0" info = { "platform": self._platform, "account": self._account, "strategy": self._strategy, "order_no": order_no, "action": action, "symbol": symbol, "price": float(price_str), "quantity": quantity, "remain": remain, "order_type": order_type, "status": status, "ctime": ctime, "utime": utime #"avg_price": order_info["price_avg"] filled_notional/filled_size??? } return Order(**info)
def _update_position(self, position_info): """ Position update. Args: position_info: Position information. Returns: None. """ self._position.leverage = position_info["leverage"] self._position.long_quantity = int(position_info["long_qty"]) self._position.long_avg_price = position_info["long_avg_cost"] self._position.long_pnl_ratio = position_info["long_pnl_ratio"] self._position.long_pnl_unreal = position_info["long_unrealised_pnl"] self._position.long_pnl = position_info["long_settled_pnl"] self._position.short_quantity = int(position_info["short_qty"]) self._position.short_avg_price = position_info["short_avg_cost"] self._position.short_pnl_ratio = position_info["short_pnl_ratio"] self._position.short_pnl_unreal = position_info["short_unrealised_pnl"] self._position.short_pnl = position_info["short_settled_pnl"] self._position.liquid_price = position_info["liquidation_price"] self._position.utime = tools.utctime_str_to_mts(position_info["updated_at"]) self._position.long_pos_margin = position_info["long_margin"] self._position.short_pos_margin = position_info['short_margin'] SingleTask.run(self._position_update_callback, copy.copy(self.position)) # publish order EventPosition(**self.position.__dict__).publish() logger.info("position:", self.position, caller=self)
async def deal_kline_update(self, data): """ 处理K线数据 1分钟 """ symbol = data["instrument_id"].replace("-", "/") if symbol not in self._symbols: return timestamp = tools.utctime_str_to_mts(data["candle"][0]) _open = "%.8f" % float(data["candle"][1]) high = "%.8f" % float(data["candle"][2]) low = "%.8f" % float(data["candle"][3]) close = "%.8f" % float(data["candle"][4]) volume = "%.8f" % float(data["candle"][5]) # 推送trade数据 kline = { "platform": self._platform, "symbol": symbol, "open": _open, "high": high, "low": low, "close": close, "volume": volume, "timestamp": timestamp, "kline_type": const.MARKET_TYPE_KLINE } EventKline(**kline).publish() logger.info("symbol:", symbol, "kline:", kline, caller=self)
async def process_orderbook_update(self, data): """Deal with orderbook update message.""" symbol = data.get("instrument_id") asks = data.get("asks") bids = data.get("bids") timestamp = tools.utctime_str_to_mts(data.get("timestamp")) if symbol not in self._orderbooks: return self._orderbooks[symbol]["timestamp"] = timestamp for ask in asks: price = float(ask[0]) quantity = int(ask[1]) if quantity == 0 and price in self._orderbooks[symbol]["asks"]: self._orderbooks[symbol]["asks"].pop(price) else: self._orderbooks[symbol]["asks"][price] = quantity for bid in bids: price = float(bid[0]) quantity = int(bid[1]) if quantity == 0 and price in self._orderbooks[symbol]["bids"]: self._orderbooks[symbol]["bids"].pop(price) else: self._orderbooks[symbol]["bids"][price] = quantity await self.publish_orderbook(symbol)
async def process_ticker(self, data): """ { "table":"spot/ticker", "data":[ { "instrument_id":"ETH-USDT", "last":"146.24", "last_qty":"0.082483", "best_bid":"146.24", "best_bid_size":"0.006822", "best_ask":"146.25", "best_ask_size":"80.541709", "open_24h":"147.17", "high_24h":"147.48", "low_24h":"143.88", "base_volume_24h":"117387.58", "quote_volume_24h":"17159427.21", "timestamp":"2019-12-11T02:31:40.436Z" } ] } """ info = { "platform": self._platform, "symbol": data["instrument_id"], "ask": float(data["best_ask"]), "bid": float(data["best_bid"]), "last": float(data["last"]), "timestamp": tools.utctime_str_to_mts(data["timestamp"]) } ticker = Ticker(**info) SingleTask.run(self.cb.on_ticker_update_callback, ticker)
async def process_kline(self, data): """ Deal with 1min kline data, and publish kline message to EventCenter via KlineEvent. Args: data: Newest kline data. """ symbol = data["instrument_id"] if symbol not in self._symbols: return timestamp = tools.utctime_str_to_mts(data["candle"][0]) _open = "%.5f" % float(data["candle"][1]) high = "%.5f" % float(data["candle"][2]) low = "%.5f" % float(data["candle"][3]) close = "%.5f" % float(data["candle"][4]) volume = str(data["candle"][5]) # Publish EventKline kline = { "platform": self._platform, "symbol": symbol, "open": _open, "high": high, "low": low, "close": close, "volume": volume, "timestamp": timestamp, "kline_type": const.MARKET_TYPE_KLINE } EventKline(**kline).publish() logger.debug("symbol:", symbol, "kline:", kline, caller=self)
def _update_position(self, position_info): """ 更新持仓信息 @param position_info 持仓信息 """ current_qty = position_info.get("currentQty") if current_qty > 0: self._position.long_quantity = abs(int(current_qty)) self._position.short_quantity = 0 if position_info.get("avgEntryPrice"): self._position.long_avg_price = position_info.get( "avgEntryPrice") elif current_qty < 0: self._position.long_quantity = 0 self._position.short_quantity = abs(int(current_qty)) if position_info.get("avgEntryPrice"): self._position.short_avg_price = position_info.get( "avgEntryPrice") else: self._position.short_quantity = 0 self._position.long_avg_price = 0 self._position.long_quantity = 0 self._position.short_avg_price = 0 if position_info.get("liquidationPrice"): self._position.liquid_price = position_info.get("liquidationPrice") if position_info.get("timestamp"): self._position.utime = tools.utctime_str_to_mts( position_info.get("timestamp"))
def _update_position(self, position_info): """ Position update. Args: position_info: Position information. Returns: None. """ if len( position_info["holding"] ) == 0: # When the length of `holding` is 0, specific all the position is closed self._position.update(0, 0, 0, 0, 0) return for item in position_info["holding"]: if item["side"] == "long": self._position.liquid_price = item["liquidation_price"] self._position.long_quantity = int(item["position"]) self._position.long_avg_price = item["avg_cost"] elif item["side"] == "short": self._position.short_quantity = int(item["position"]) self._position.short_avg_price = item["avg_cost"] else: continue self._position.utime = tools.utctime_str_to_mts(item["timestamp"])
async def process_orderbook_update(self, msg): """ Deal with orderbook message that updated. Args: msg: Orderbook update message. """ symbol = msg["product_id"].replace("-", "/") if symbol not in self._symbols: return self._orderbooks[symbol]["timestamp"] = tools.utctime_str_to_mts( msg["time"][:23] + "Z") for item in msg["changes"]: side = item[0] price = float(item[1]) quantity = float(item[2]) if side == "sell": if quantity == 0: if price in self._orderbooks[symbol]["asks"]: self._orderbooks[symbol]["asks"].pop(price) else: self._orderbooks[symbol]["asks"][price] = quantity elif side == "buy": if quantity == 0: if price in self._orderbooks[symbol]["bids"]: self._orderbooks[symbol]["bids"].pop(price) else: self._orderbooks[symbol]["bids"][price] = quantity await self.publish_orderbook_event(symbol)
async def process_trade(self, msg): """Process trade data and publish TradeEvent.""" symbol = msg["product_id"].replace("-", "/") if symbol not in self._symbols: return if not msg.get( "trade_id" ): # The first ticker message received from Websocket maybe no this field, dropped. return action = ORDER_ACTION_BUY if msg.get( "side") == "buy" else ORDER_ACTION_SELL price = "%.8f" % float(msg["price"]) quantity = "%.8f" % float(msg["last_size"]) timestamp = tools.utctime_str_to_mts(msg["time"][:23] + "Z") trade = { "platform": self._platform, "symbol": symbol, "action": action, "price": price, "quantity": quantity, "timestamp": timestamp } EventTrade(**trade).publish() logger.info("symbol:", symbol, "trade:", trade, caller=self)
async def deal_orderbook_update(self, data): """ 处理orderbook增量数据 """ symbol = data.get("instrument_id").replace("-", "/") asks = data.get("asks") bids = data.get("bids") timestamp = tools.utctime_str_to_mts(data.get("timestamp")) if symbol not in self._orderbooks: return self._orderbooks[symbol]["timestamp"] = timestamp for ask in asks: price = float(ask[0]) quantity = float(ask[1]) if quantity == 0 and price in self._orderbooks[symbol]["asks"]: self._orderbooks[symbol]["asks"].pop(price) else: self._orderbooks[symbol]["asks"][price] = quantity for bid in bids: price = float(bid[0]) quantity = float(bid[1]) if quantity == 0 and price in self._orderbooks[symbol]["bids"]: self._orderbooks[symbol]["bids"].pop(price) else: self._orderbooks[symbol]["bids"][price] = quantity await self.publish_orderbook()
def _update_kline(self, kline_info, symbol): """ kline update. Args: kline_info: kline information. Returns: None. """ info = { "platform": self._platform, "symbol": symbol, "open": kline_info["open"], "high": kline_info["high"], "low": kline_info["low"], "close": kline_info["close"], "volume": kline_info["volume"], "timestamp": tools.utctime_str_to_mts(kline_info["startTime"], "%Y-%m-%dT%H:%M:%S+00:00"), "kline_type": MARKET_TYPE_KLINE } kline = Kline(**info) SingleTask.run(self.cb.on_kline_update_callback, kline)
async def process_trade(self, data): """Deal with trade data, and publish trade message to EventCenter via TradeEvent.""" symbol = data["instrument_id"] if symbol not in self._symbols: return action = ORDER_ACTION_BUY if data[ "side"] == "buy" else ORDER_ACTION_SELL price = "%.5f" % float(data["price"]) if self._platform == const.OKEX_FUTURE: quantity = str(data["qty"]) else: quantity = str(data["size"]) timestamp = tools.utctime_str_to_mts(data["timestamp"]) # Publish EventTrade. trade = { "platform": self._platform, "symbol": symbol, "action": action, "price": price, "quantity": quantity, "timestamp": timestamp } EventTrade(**trade).publish() logger.debug("symbol:", symbol, "trade:", trade, caller=self)
def _update_order(self, order_info): """ Order update. Args: order_info: Order information. Returns: Return order object if or None. """ order_no = str(order_info["order_id"]) state = order_info["state"] remain = int(order_info["size"]) - int(order_info["filled_qty"]) ctime = tools.utctime_str_to_mts(order_info["timestamp"]) if state == "-2": status = ORDER_STATUS_FAILED elif state == "-1": status = ORDER_STATUS_CANCELED elif state == "0": status = ORDER_STATUS_SUBMITTED elif state == "1": status = ORDER_STATUS_PARTIAL_FILLED elif state == "2": status = ORDER_STATUS_FILLED else: return None order = self._orders.get(order_no) if not order: info = { "platform": self._platform, "account": self._account, "strategy": self._strategy, "order_no": order_no, "action": ORDER_ACTION_BUY if order_info["type"] in ["1", "4"] else ORDER_ACTION_SELL, "symbol": self._symbol, "price": order_info["price"], "quantity": order_info["size"], "trade_type": int(order_info["type"]) } order = Order(**info) order.remain = remain order.status = status order.avg_price = order_info["price_avg"] order.ctime = ctime order.utime = ctime self._orders[order_no] = order if state in ["-1", "2"]: self._orders.pop(order_no) return order
def _update_position(self, position_info): """ 更新持仓信息 @param position_info 持仓信息 """ self._position.long_quantity = int(position_info["long_qty"]) self._position.long_avg_price = position_info["long_avg_cost"] self._position.short_quantity = int(position_info["short_qty"]) self._position.short_avg_price = position_info["short_avg_cost"] self._position.liquid_price = position_info["liquidation_price"] self._position.utime = tools.utctime_str_to_mts(position_info["updated_at"])
def _update_order(self, order_info): """ Order update. Args: order_info: Order information. Returns: None. """ order_no = str(order_info["order_id"]) state = order_info["state"] remain = int(order_info["size"]) - int(order_info["filled_qty"]) ctime = tools.utctime_str_to_mts(order_info["timestamp"]) if state == "-2": status = ORDER_STATUS_FAILED elif state == "-1": status = ORDER_STATUS_CANCELED elif state == "0": status = ORDER_STATUS_SUBMITTED elif state == "1": status = ORDER_STATUS_PARTIAL_FILLED elif state == "2": status = ORDER_STATUS_FILLED else: return None order = self._orders.get(order_no) if not order: info = { "platform": self._platform, "account": self._account, "strategy": self._strategy, "order_no": order_no, "action": ORDER_ACTION_BUY if order_info["type"] in ["1", "4"] else ORDER_ACTION_SELL, "symbol": self._symbol, "price": order_info["price"], "quantity": order_info["size"], "trade_type": int(order_info["type"]) } order = Order(**info) order.remain = remain order.status = status order.avg_price = order_info["price_avg"] order.ctime = ctime order.utime = ctime self._orders[order_no] = order SingleTask.run(self._order_update_callback, copy.copy(order)) if status in [ORDER_STATUS_FAILED, ORDER_STATUS_CANCELED, ORDER_STATUS_FILLED]: self._orders.pop(order_no) # publish order EventOrder(**order.__dict__).publish() logger.info("symbol:", order.symbol, "order:", order, caller=self)
def _update_position(self, position_info): """ Position update. Args: position_info: Position information. Returns: None. """ if len(position_info["holding"]) == 0: # When the length of `holding` is 0, specific all the position is closed self._position.update(0, 0, 0, 0, 0) return for item in position_info["holding"]: usd_value_volume = 100 if self._symbol.startswith("BTC") else 10 if item["side"] == "long": self._position.liquid_price = item["liquidation_price"] self._position.leverage = item["leverage"] self._position.maint_margin_ratio = item["maint_margin_ratio"] self._position.long_quantity = int(item["avail_position"]) self._position.long_avg_price = item["avg_cost"] if float(item["settlement_price"]) and float(item["last"]): self._position.long_pnl_unreal = round((usd_value_volume/float(item["settlement_price"]) - usd_value_volume/float(item["last"])) * int(item["avail_position"]), 8) else: self._position.long_pnl_unreal = 0 self._position.long_pnl = item["settled_pnl"] self._position.long_pos_margin = item["margin"] if float(item["margin"]): self._position.long_pnl_ratio = round((float(item["settled_pnl"]) + float(self._position.long_pnl_unreal))/float(item["margin"]), 5) else: self._position.long_pnl_ratio = 0 elif item["side"] == "short": self._position.liquid_price = item["liquidation_price"] self._position.leverage = item["leverage"] self._position.maint_margin_ratio = item["maint_margin_ratio"] self._position.short_quantity = int(item["avail_position"]) self._position.short_avg_price = item["avg_cost"] if float(item["settlement_price"]) and float(item["last"]): self._position.short_pnl_unreal = -round((usd_value_volume/float(item["settlement_price"]) - usd_value_volume/float(item["last"])) * int(item["avail_position"]), 8) else: self._position.short_pnl_unreal = 0 self._position.short_pnl = item["settled_pnl"] self._position.short_pos_margin = item["margin"] if float(item["margin"]): self._position.short_pnl_ratio = round((float(item["settled_pnl"]) + float(self._position.short_pnl_unreal))/float(item["margin"]), 5) else: self._position.short_pnl_ratio = 0 else: continue self._position.utime = tools.utctime_str_to_mts(item["timestamp"]) SingleTask.run(self._position_update_callback, copy.copy(self._position)) logger.info("position:", self._position, caller=self)
async def process_orderbook(self, data): """Process orderbook data and publish OrderbookEvent.""" for item in data: symbol = item.get("symbol") orderbook = { "platform": self._platform, "symbol": symbol, "asks": item.get("asks"), "bids": item.get("bids"), "timestamp": tools.utctime_str_to_mts(item["timestamp"]) } EventOrderbook(**orderbook).publish() logger.debug("symbol:", symbol, "orderbook:", orderbook, caller=self)
async def process_trade(self, data): """Process trade data and publish TradeEvent.""" for item in data: symbol = item["symbol"] trade = { "platform": self._platform, "symbol": symbol, "action": ORDER_ACTION_BUY if item["side"] == "Buy" else ORDER_ACTION_SELL, "price": "%.8f" % item["price"], "quantity": str(item["size"]), "timestamp": tools.utctime_str_to_mts(item["timestamp"]) } EventTrade(**trade).publish() logger.debug("symbol:", symbol, "trade:", trade, caller=self)
async def process_kline(self, data): symbol = data["instrument_id"] if symbol not in self._symbols: return cur_kline = data["candle"] if self._prev_kline_map[symbol]: #如果存在前一根k线 prev_kline = self._prev_kline_map[symbol] prev_timestamp = tools.utctime_str_to_mts(prev_kline[0]) cur_timestamp = tools.utctime_str_to_mts(cur_kline[0]) if prev_timestamp != cur_timestamp: #前一根k线的开始时间与当前k线开始时间不同,意味着前一根k线已经统计完毕,通知上层策略 info = { "platform": self._platform, "symbol": symbol, "open": float(prev_kline[1]), "high": float(prev_kline[2]), "low": float(prev_kline[3]), "close": float(prev_kline[4]), "volume": float(prev_kline[5]), "timestamp": prev_timestamp, "kline_type": MARKET_TYPE_KLINE } kline = Kline(**info) SingleTask.run(self.cb.on_kline_update_callback, kline) self._prev_kline_map[symbol] = cur_kline
def _update_position(self, position_info): """ Position update. Args: position_info: Position information. Returns: None. """ self._position.long_quantity = int(position_info["long_qty"]) self._position.long_avg_price = position_info["long_avg_cost"] self._position.short_quantity = int(position_info["short_qty"]) self._position.short_avg_price = position_info["short_avg_cost"] self._position.liquid_price = position_info["liquidation_price"] self._position.utime = tools.utctime_str_to_mts(position_info["updated_at"]) SingleTask.run(self._position_update_callback, copy.copy(self.position))
async def process_kline(self, data): """Process kline data and publish KlineEvent.""" for item in data: symbol = item["symbol"] kline = { "platform": self._platform, "symbol": symbol, "open": "%.1f" % item["open"], "high": "%.1f" % item["high"], "low": "%.1f" % item["low"], "close": "%.1f" % item["close"], "volume": str(item["volume"]), "timestamp": tools.utctime_str_to_mts(item["timestamp"]), "kline_type": MARKET_TYPE_KLINE } EventKline(**kline).publish() logger.info("symbol:", symbol, "kline:", kline, caller=self)
async def process_orderbook_partial(self, data): """Process orderbook partical data.""" symbol = data.get("instrument_id").replace("-", "/") if symbol not in self._symbols: return asks = data.get("asks") bids = data.get("bids") self._orderbooks[symbol] = {"asks": {}, "bids": {}, "timestamp": 0} for ask in asks: price = float(ask[0]) quantity = float(ask[1]) self._orderbooks[symbol]["asks"][price] = quantity for bid in bids: price = float(bid[0]) quantity = float(bid[1]) self._orderbooks[symbol]["bids"][price] = quantity timestamp = tools.utctime_str_to_mts(data.get("timestamp")) self._orderbooks[symbol]["timestamp"] = timestamp
async def deal_orderbook_partial(self, data): """ Deal with orderbook partial message. """ symbol = data.get("instrument_id") if symbol not in self._symbols: return asks = data.get("asks") bids = data.get("bids") self._orderbooks[symbol] = {"asks": {}, "bids": {}, "timestamp": 0} for ask in asks: price = float(ask[0]) quantity = int(ask[1]) self._orderbooks[symbol]["asks"][price] = quantity for bid in bids: price = float(bid[0]) quantity = int(bid[1]) self._orderbooks[symbol]["bids"][price] = quantity timestamp = tools.utctime_str_to_mts(data.get("timestamp")) self._orderbooks[symbol]["timestamp"] = timestamp
async def process_trade(self, data): symbol = data.get("instrument_id") if symbol not in self._symbols: return action = ORDER_ACTION_BUY if data[ "side"] == "buy" else ORDER_ACTION_SELL price = float(data["price"]) quantity = float(data["size"]) timestamp = tools.utctime_str_to_mts(data["timestamp"]) info = { "platform": self._platform, "symbol": symbol, "action": action, "price": price, "quantity": quantity, "timestamp": timestamp } trade = Trade(**info) SingleTask.run(self.cb.on_trade_update_callback, trade)
async def process_trade(self, data): """Process trade data and publish TradeEvent.""" symbol = data.get("instrument_id").replace("-", "/") if symbol not in self._symbols: return action = ORDER_ACTION_BUY if data["side"] == "buy" else ORDER_ACTION_SELL price = "%.8f" % float(data["price"]) quantity = "%.8f" % float(data["size"]) timestamp = tools.utctime_str_to_mts(data["timestamp"]) trade = { "platform": self._platform, "symbol": symbol, "action": action, "price": price, "quantity": quantity, "timestamp": timestamp } EventTrade(**trade).publish() logger.debug("symbol:", symbol, "trade:", trade, caller=self)
def _update_fill(self, fill_info): """ Fill update. Args: fill_info: Fill information. Returns: None. """ #{"channel": "orders", "type": "update", "data": {"id": 751733812, "clientId": null, "market": "ETH-PERP", "type": "limit", "side": "buy", "price": 187.93, "size": 0.001, "status": "closed", "filledSize": 0.001, "remainingSize": 0.0, "reduceOnly": false, "avgFillPrice": 184.25, "postOnly": false, "ioc": false}} #{"channel": "fills", "type": "update", "data": {"id": 5741311, "market": "ETH-PERP", "future": "ETH-PERP", "baseCurrency": null, "quoteCurrency": null, "type": "order", "side": "buy", "price": 184.25, "size": 0.001, "orderId": 751733812, "time": "2019-11-08T09:52:27.366467+00:00", "feeRate": 0.0007, "fee": 0.000128975, "liquidity": "taker"}} data = fill_info["data"] fill_no = str(data["id"]) order_no = str(data["orderId"]) price = float(data["price"]) size = float(data["size"]) fee = float(data["fee"]) ts = tools.utctime_str_to_mts(data["time"], "%Y-%m-%dT%H:%M:%S.%f+00:00") liquidity = LIQUIDITY_TYPE_TAKER if data[ "liquidity"] == "taker" else LIQUIDITY_TYPE_MAKER info = { "platform": self._platform, "account": self._account, "strategy": self._strategy, "fill_no": fill_no, "order_no": order_no, "side": ORDER_ACTION_BUY if data["side"] == "buy" else ORDER_ACTION_SELL, "symbol": data["market"], "price": price, "quantity": size, "liquidity": liquidity, "fee": fee, "ctime": ts } fill = Fill(**info) SingleTask.run(self.cb.on_fill_update_callback, fill)
def _update_order(self, order_info): """ Order update. Args: order_info: Order information. Returns: None. """ if order_info.get("margin_trading") and order_info[ "margin_trading"] != "1": # 1.币币交易订单 2.杠杆交易订单 return order = self._convert_order_format(order_info) if self.cb.on_order_update_callback: SingleTask.run(self.cb.on_order_update_callback, order) #===================================================================================== #如果存在成交部分,就处理成交回调 if (order.status == ORDER_STATUS_PARTIAL_FILLED or order.status == ORDER_STATUS_FILLED) and \ order_info.get("last_fill_px") and order_info.get("last_fill_qty"): #liquidity = LIQUIDITY_TYPE_TAKER if order_info["role"]=="taker" else LIQUIDITY_TYPE_MAKER #原始数据中没有 #fee = float(order_info["fees"]) #原始数据中没有,可以考虑自己计算 f = { "platform": self._platform, "account": self._account, "strategy": self._strategy, "fill_no": order_info["last_fill_id"], "order_no": str(order_info["order_id"]), "side": ORDER_ACTION_BUY if order_info["side"] == "buy" else ORDER_ACTION_SELL, #成交方向,买还是卖 "symbol": order_info["instrument_id"], "price": float(order_info["last_fill_px"]), #成交价格 "quantity": float(order_info["last_fill_qty"]), #成交数量 #"liquidity": liquidity, #maker成交还是taker成交 #"fee": fee, "ctime": tools.utctime_str_to_mts(order_info["last_fill_time"]) } fill = Fill(**f) if self.cb.on_fill_update_callback: SingleTask.run(self.cb.on_fill_update_callback, fill)