Merge branch 'dev' of https://github.com/vnpy/vnpy into dev
This commit is contained in:
commit
69606087c5
@ -1,8 +1,7 @@
|
||||
import unittest
|
||||
|
||||
# noinspection PyUnresolvedReferences
|
||||
from tests.network.RestfulClientTest import *
|
||||
from tests.network.WebSocketClientTest import *
|
||||
from api.base import *
|
||||
|
||||
if __name__ == "__main__":
|
||||
unittest.main()
|
||||
|
@ -6,7 +6,7 @@ import unittest
|
||||
from simplejson import JSONDecodeError
|
||||
|
||||
from Promise import Promise
|
||||
from vnpy.network.RestClient import RestClient, Request
|
||||
from vnpy.api.rest.RestClient import RestClient, Request
|
||||
|
||||
|
||||
class FailedError(RuntimeError):
|
@ -1,9 +1,8 @@
|
||||
# encoding: UTF-8
|
||||
import json
|
||||
import unittest
|
||||
|
||||
from Promise import Promise
|
||||
from vnpy.network.WebSocketClient import WebsocketClient
|
||||
from vnpy.api.websocket import WebsocketClient
|
||||
|
||||
|
||||
class TestWebsocketClient(WebsocketClient):
|
@ -1,48 +1,59 @@
|
||||
# encoding: UTF-8
|
||||
from enum import Enum
|
||||
from typing import Any, Callable, List, Union
|
||||
|
||||
from vnpy.api.okexfuture.vnokexFuture import OkexFutureRestBase
|
||||
from vnpy.network.RestClient import Request
|
||||
from vnpy.api.rest import Request
|
||||
|
||||
|
||||
########################################################################
|
||||
class _OkexFutureCustomExtra(object):
|
||||
|
||||
def __init__(self, onSuccess, onFailed, extra):
|
||||
self.onFailed = onFailed
|
||||
self.onSuccess = onSuccess
|
||||
self.extra = extra
|
||||
|
||||
|
||||
########################################################################
|
||||
class OkexFutureSymbol(object):
|
||||
BTC = 'btc_usd'
|
||||
LTC = 'ltc_usd'
|
||||
ETH = 'eth_usd'
|
||||
ETC = 'etc_usd'
|
||||
BCH = 'bch_usd'
|
||||
|
||||
|
||||
class OkexFuturePriceType(Enum):
|
||||
########################################################################
|
||||
class OkexFuturePriceType(object):
|
||||
Buy = 'buy'
|
||||
Sell = 'sell'
|
||||
|
||||
|
||||
class OkexFutureContractType(Enum):
|
||||
########################################################################
|
||||
class OkexFutureContractType(object):
|
||||
ThisWeek = 'this_week'
|
||||
NextWeek = 'next_week'
|
||||
Quarter = 'quarter'
|
||||
|
||||
|
||||
class OkexFutureStatus(Enum):
|
||||
NoTraded = '0'
|
||||
PartialTraded = '1'
|
||||
AllTraded = '2'
|
||||
Canceled = '-1'
|
||||
CancelProcessing = '4'
|
||||
Canceling = '5'
|
||||
|
||||
|
||||
class OkexFutureOrderType(Enum):
|
||||
########################################################################
|
||||
class OkexFutureOrderType(object):
|
||||
OpenLong = '1'
|
||||
OpenShort = '2'
|
||||
CloseLong = '3'
|
||||
CloseShort = '4'
|
||||
|
||||
|
||||
########################################################################
|
||||
class OkexFutureOrderStatus(object):
|
||||
NotFinished = '1'
|
||||
Finished = '2'
|
||||
|
||||
|
||||
########################################################################
|
||||
class OkexFutureOrder(object):
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def __init__(self):
|
||||
self.volume = None
|
||||
self.contractName = None
|
||||
@ -59,8 +70,10 @@ class OkexFutureOrder(object):
|
||||
self.unitAmount = None
|
||||
|
||||
|
||||
########################################################################
|
||||
class OkexFutureUserInfo(object):
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def __init__(self):
|
||||
self.accountRights = None
|
||||
self.keepDeposit = None
|
||||
@ -69,15 +82,19 @@ class OkexFutureUserInfo(object):
|
||||
self.riskRate = None
|
||||
|
||||
|
||||
########################################################################
|
||||
class OkexFuturePosition(object):
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def __init__(self, ):
|
||||
self.forceLiquidatePrice = None
|
||||
self.holding = [] # type: List[OkexFuturePositionDetail]
|
||||
|
||||
|
||||
########################################################################
|
||||
class OkexFuturePositionDetail(object):
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def __init__(self, ):
|
||||
self.buyAmount = None
|
||||
self.buyAvailable = None
|
||||
@ -125,7 +142,7 @@ class OkexFutureRestClient(OkexFutureRestBase):
|
||||
def sendOrder(self, symbol, contractType, orderType, volume,
|
||||
onSuccess, onFailed=None,
|
||||
price=None, useMarketPrice=False, leverRate=None,
|
||||
extra=None): # type:(str, OkexFutureContractType, OkexFutureOrderType, float, Callable[[int, Any], Any], Callable[[Any], Any], float, bool, Union[int, None], Any)->Request
|
||||
extra=None): # type:(str, OkexFutureContractType, OkexFutureOrderType, float, Callable[[int, Any], Any], Callable[[int, Any], Any], float, bool, Union[int, None], Any)->Request
|
||||
"""
|
||||
:param symbol: str
|
||||
:param contractType: OkexFutureContractType
|
||||
@ -163,7 +180,7 @@ class OkexFutureRestClient(OkexFutureRestBase):
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def cancelOrder(self, symbol, contractType, orderId, onSuccess, onFailed=None,
|
||||
extra=None): # type: (str, OkexFutureContractType, str, Callable[[object], Any], Callable[[Any], Any], Any)->Request
|
||||
extra=None): # type: (str, OkexFutureContractType, str, Callable[[object], Any], Callable[[int, Any], Any], Any)->Request
|
||||
"""
|
||||
:param symbol: str
|
||||
:param contractType: OkexFutureContractType
|
||||
@ -186,7 +203,7 @@ class OkexFutureRestClient(OkexFutureRestBase):
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def queryOrder(self, symbol, contractType, orderId, onSuccess, onFailed=None,
|
||||
extra=None): # type: (str, OkexFutureContractType, str, Callable[[OkexFutureOrder, Any], Any], Callable[[Any], Any], Any)->Request
|
||||
extra=None): # type: (str, OkexFutureContractType, str, Callable[[OkexFutureOrder, Any], Any], Callable[[int, Any], Any], Any)->Request
|
||||
"""
|
||||
:param symbol: str
|
||||
:param contractType: OkexFutureContractType
|
||||
@ -206,10 +223,40 @@ class OkexFutureRestClient(OkexFutureRestBase):
|
||||
callback=self.onOrder,
|
||||
data=data,
|
||||
extra=_OkexFutureCustomExtra(onSuccess, onFailed, extra))
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def queryOrders(self, symbol, contractType, status,
|
||||
onSuccess, onFailed=None,
|
||||
pageIndex=None, pageLength=50,
|
||||
extra=None): # type: (str, OkexFutureContractType, OkexFutureOrderStatus, Callable[[OkexFutureOrder, Any], Any], Callable[[int, Any], Any], int, int, Any)->Request
|
||||
"""
|
||||
:param symbol: str
|
||||
:param contractType: OkexFutureContractType
|
||||
:param orderId: str
|
||||
:param onSuccess: (OkexFutureOrder, extra:Any)->Any
|
||||
:param onFailed: (extra: Any)->Any
|
||||
:param extra: Any
|
||||
:return: Request
|
||||
"""
|
||||
data = {
|
||||
'symbol': symbol,
|
||||
'contractType': contractType,
|
||||
'status': status,
|
||||
'order_id': '-1',
|
||||
'pageLength': 50
|
||||
}
|
||||
if pageIndex:
|
||||
data['page_index'] = pageIndex
|
||||
|
||||
return self.addReq('POST',
|
||||
'/future_order_info.do',
|
||||
callback=self.onOrder,
|
||||
data=data,
|
||||
extra=_OkexFutureCustomExtra(onSuccess, onFailed, extra))
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def queryUserInfo(self, onSuccess, onFailed=None,
|
||||
extra=None): # type: (Callable[[List[OkexFutureUserInfo], Any], Any], Callable[[Any], Any], Any)->Request
|
||||
extra=None): # type: (Callable[[List[OkexFutureUserInfo], Any], Any], Callable[[int, Any], Any], Any)->Request
|
||||
"""
|
||||
查询用户信息
|
||||
:param onSuccess: (userInfos: List[OkexFutureUserInfo], extra: Any)->Any
|
||||
@ -225,7 +272,7 @@ class OkexFutureRestClient(OkexFutureRestBase):
|
||||
#----------------------------------------------------------------------
|
||||
def queryPosition(self, symbol, contractType,
|
||||
onSuccess, onFailed=None,
|
||||
extra=None): # type: (str, OkexFutureContractType, Callable[[OkexFuturePosition, Any], Any], Callable[[Any], Any], Any)->Request
|
||||
extra=None): # type: (str, OkexFutureContractType, Callable[[OkexFuturePosition, Any], Any], Callable[[int, Any], Any], Any)->Request
|
||||
data = {
|
||||
'symbol': symbol,
|
||||
'contractType': contractType
|
||||
@ -248,7 +295,10 @@ class OkexFutureRestClient(OkexFutureRestBase):
|
||||
extra.onSuccess(remoteId, extra.extra)
|
||||
else:
|
||||
if extra.onFailed:
|
||||
extra.onFailed(extra.extra)
|
||||
code = 0
|
||||
if 'error_code' in data:
|
||||
code = data['error_code']
|
||||
extra.onFailed(code, extra.extra)
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
@staticmethod
|
||||
@ -262,7 +312,10 @@ class OkexFutureRestClient(OkexFutureRestBase):
|
||||
extra.onSuccess(extra.extra)
|
||||
else:
|
||||
if extra.onFailed:
|
||||
extra.onFailed(extra.extra)
|
||||
code = 0
|
||||
if 'error_code' in data:
|
||||
code = data['error_code']
|
||||
extra.onFailed(code, extra.extra)
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
@staticmethod
|
||||
@ -290,7 +343,10 @@ class OkexFutureRestClient(OkexFutureRestBase):
|
||||
extra.onSuccess(okexOrder, extra.extra)
|
||||
else:
|
||||
if extra.onFailed:
|
||||
extra.onFailed(extra.extra)
|
||||
code = 0
|
||||
if 'error_code' in data:
|
||||
code = data['error_code']
|
||||
extra.onFailed(code, extra.extra)
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
@staticmethod
|
||||
@ -311,7 +367,10 @@ class OkexFutureRestClient(OkexFutureRestBase):
|
||||
extra.onSuccess(uis, extra.extra)
|
||||
else:
|
||||
if extra.onFailed:
|
||||
extra.onFailed(extra.extra)
|
||||
code = 0
|
||||
if 'error_code' in data:
|
||||
code = data['error_code']
|
||||
extra.onFailed(code, extra.extra)
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
@staticmethod
|
||||
@ -342,4 +401,60 @@ class OkexFutureRestClient(OkexFutureRestBase):
|
||||
extra.onSuccess(pos, extra.extra)
|
||||
else:
|
||||
if extra.onFailed:
|
||||
extra.onFailed(extra.extra)
|
||||
code = 0
|
||||
if 'error_code' in data:
|
||||
code = data['error_code']
|
||||
extra.onFailed(code, extra.extra)
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
@staticmethod
|
||||
def errorCode2String(code):
|
||||
assert code in errorCodeMap
|
||||
return errorCodeMap[code]
|
||||
|
||||
|
||||
errorCodeMap = {
|
||||
0: '远程服务器并未给出错误代码',
|
||||
|
||||
20001: '用户不存在',
|
||||
20002: '用户被冻结',
|
||||
20003: '用户被爆仓冻结',
|
||||
20004: '合约账户被冻结',
|
||||
20005: '用户合约账户不存在',
|
||||
20006: '必填参数为空',
|
||||
20007: '参数错误',
|
||||
20008: '合约账户余额为空',
|
||||
20009: '虚拟合约状态错误',
|
||||
20010: '合约风险率信息不存在',
|
||||
20011: '10倍/20倍杠杆开BTC前保证金率低于90%/80%,10倍/20倍杠杆开LTC前保证金率低于80%/60%',
|
||||
20012: '10倍/20倍杠杆开BTC后保证金率低于90%/80%,10倍/20倍杠杆开LTC后保证金率低于80%/60%',
|
||||
20013: '暂无对手价',
|
||||
20014: '系统错误',
|
||||
20015: '订单信息不存在',
|
||||
20016: '平仓数量是否大于同方向可用持仓数量',
|
||||
20017: '非本人操作',
|
||||
20018: '下单价格高于前一分钟的103%或低于97%',
|
||||
20019: '该IP限制不能请求该资源',
|
||||
20020: '密钥不存在',
|
||||
20021: '指数信息不存在',
|
||||
20022: '接口调用错误(全仓模式调用全仓接口,逐仓模式调用逐仓接口)',
|
||||
20023: '逐仓用户',
|
||||
20024: 'sign签名不匹配',
|
||||
20025: '杠杆比率错误',
|
||||
20026: 'API鉴权错误',
|
||||
20027: '无交易记录',
|
||||
20028: '合约不存在',
|
||||
20029: '转出金额大于可转金额',
|
||||
20030: '账户存在借款',
|
||||
20038: '根据相关法律,您所在的国家或地区不能使用该功能。',
|
||||
20049: '用户请求接口过于频繁',
|
||||
20061: '合约相同方向只支持一个杠杆,若有10倍多单,就不能再下20倍多单',
|
||||
21005: '请求接口失败,请您重试',
|
||||
21020: '合约交割中,无法下单',
|
||||
21021: '合约清算中,无法下单',
|
||||
21023: '当前全仓方向仓位已超过最大可开张数',
|
||||
21024: '当前逐仓方向仓位已超过最大可开张数',
|
||||
21025: '下单后保证金率小于对应档位要求的最低保证金率',
|
||||
21026: '您的账户已被限制开仓操作',
|
||||
20119: '接口已下线或无法使用',
|
||||
}
|
||||
|
@ -0,0 +1,2 @@
|
||||
from .OkexFutureApi import OkexFutureSymbol, OkexFutureContractType, OkexFutureOrder, OkexFutureOrderStatus, OkexFuturePosition, \
|
||||
OkexFuturePositionDetail, OkexFuturePriceType, OkexFutureRestClient, OkexFutureUserInfo
|
@ -4,7 +4,7 @@ import urllib
|
||||
|
||||
|
||||
########################################################################
|
||||
from vnpy.network.RestClient import RestClient, Request
|
||||
from vnpy.api.rest import RestClient, Request
|
||||
|
||||
|
||||
########################################################################
|
||||
|
@ -127,6 +127,16 @@ class RestClient(object):
|
||||
:return:
|
||||
"""
|
||||
self._active = False
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def join(self):
|
||||
"""
|
||||
等待所有请求处理结束
|
||||
如果要并确保RestClient的退出,请在调用stop之后紧接着调用join。
|
||||
如果只是要确保所有的请求都处理完,直接调用join即可。
|
||||
:return:
|
||||
"""
|
||||
self._queue.join()
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def addReq(self, method, path, callback,
|
||||
@ -160,7 +170,10 @@ class RestClient(object):
|
||||
while self._active:
|
||||
try:
|
||||
req = self._queue.get(timeout=1)
|
||||
self.processReq(req, session)
|
||||
try:
|
||||
self._processReq(req, session)
|
||||
finally:
|
||||
self._queue.task_done()
|
||||
except Empty:
|
||||
pass
|
||||
|
||||
@ -202,7 +215,7 @@ class RestClient(object):
|
||||
sys.excepthook(exceptionType, exceptionValue, tb)
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def processReq(self, req, session): # type: (Request, requests.Session)->None
|
||||
def _processReq(self, req, session): # type: (Request, requests.Session)->None
|
||||
"""处理请求"""
|
||||
try:
|
||||
req = self.beforeRequest(req)
|
1
vnpy/api/rest/__init__.py
Normal file
1
vnpy/api/rest/__init__.py
Normal file
@ -0,0 +1 @@
|
||||
from .RestClient import Request, RequestStatus, RestClient, requestsSessionProvider
|
@ -9,7 +9,7 @@ import time
|
||||
from abc import abstractmethod
|
||||
from threading import Thread, Lock
|
||||
|
||||
import websocket
|
||||
import vnpy.api.websocket
|
||||
|
||||
|
||||
class WebsocketClient(object):
|
||||
@ -57,12 +57,12 @@ class WebsocketClient(object):
|
||||
#----------------------------------------------------------------------
|
||||
def sendReq(self, req): # type: (dict)->None
|
||||
"""发出请求"""
|
||||
return self._get_ws().send(json.dumps(req), opcode=websocket.ABNF.OPCODE_TEXT)
|
||||
return self._get_ws().send(json.dumps(req), opcode=vnpy.api.websocket.ABNF.OPCODE_TEXT)
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def sendText(self, text): # type: (str)->None
|
||||
"""发出请求"""
|
||||
return self._get_ws().send(text, opcode=websocket.ABNF.OPCODE_TEXT)
|
||||
return self._get_ws().send(text, opcode=vnpy.api.websocket.ABNF.OPCODE_TEXT)
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def sendData(self, data): # type: (bytes)->None
|
||||
@ -78,7 +78,7 @@ class WebsocketClient(object):
|
||||
#----------------------------------------------------------------------
|
||||
def _connect(self):
|
||||
""""""
|
||||
self._ws = websocket.create_connection(self.host, sslopt={'cert_reqs': ssl.CERT_NONE})
|
||||
self._ws = vnpy.api.websocket.create_connection(self.host, sslopt={'cert_reqs': ssl.CERT_NONE})
|
||||
self.onConnect()
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
@ -125,7 +125,7 @@ class WebsocketClient(object):
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def _ping(self):
|
||||
return self._get_ws().send('ping', websocket.ABNF.OPCODE_PING)
|
||||
return self._get_ws().send('ping', vnpy.api.websocket.ABNF.OPCODE_PING)
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
@abstractmethod
|
1
vnpy/api/websocket/__init__.py
Normal file
1
vnpy/api/websocket/__init__.py
Normal file
@ -0,0 +1 @@
|
||||
from .WebSocketClient import WebsocketClient
|
@ -5,6 +5,8 @@ from __future__ import print_function
|
||||
import json
|
||||
from abc import abstractmethod, abstractproperty
|
||||
|
||||
from typing import Dict
|
||||
|
||||
from vnpy.api.okexfuture.OkexFutureApi import *
|
||||
from vnpy.trader.vtFunction import getJsonPath
|
||||
from vnpy.trader.vtGateway import *
|
||||
@ -94,6 +96,7 @@ class _Order(object):
|
||||
self.remoteId = None
|
||||
self.vtOrder = None # type: VtOrderData
|
||||
|
||||
|
||||
########################################################################
|
||||
class OkexFutureGateway(VnpyGateway):
|
||||
"""OKEX期货交易接口"""
|
||||
@ -107,8 +110,8 @@ class OkexFutureGateway(VnpyGateway):
|
||||
self.api = OkexFutureRestClient()
|
||||
self.leverRate = 1
|
||||
self.symbols = []
|
||||
|
||||
self.orders =
|
||||
|
||||
self._orders = {} # type: Dict[str, _Order]
|
||||
#----------------------------------------------------------------------
|
||||
@property
|
||||
def gatewayName(self):
|
||||
@ -148,6 +151,15 @@ class OkexFutureGateway(VnpyGateway):
|
||||
def subscribe(self, subscribeReq):
|
||||
"""订阅行情"""
|
||||
pass
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
@staticmethod
|
||||
def _contractTypeFromSymbol(symbol):
|
||||
return symbolsForUi[symbol]
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def _getOrder(self, localId):
|
||||
return self._orders[localId]
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def sendOrder(self, vtRequest): # type: (VtOrderReq)->str
|
||||
@ -167,8 +179,8 @@ class OkexFutureGateway(VnpyGateway):
|
||||
vtOrder.direction = vtRequest.direction
|
||||
|
||||
myorder.vtOrder = vtOrder
|
||||
|
||||
symbol, contractType = symbolsForUi[vtRequest.symbol]
|
||||
|
||||
symbol, contractType = self._contractTypeFromSymbol(vtRequest.symbol)
|
||||
orderType = orderTypeMap[(vtRequest.priceType, vtRequest.offset)] # 开多、开空、平多、平空
|
||||
userMarketPrice = False
|
||||
|
||||
@ -183,14 +195,26 @@ class OkexFutureGateway(VnpyGateway):
|
||||
useMarketPrice=userMarketPrice,
|
||||
leverRate=self.leverRate,
|
||||
onSuccess=self.onOrderSent,
|
||||
extra=None)
|
||||
extra=None,
|
||||
)
|
||||
|
||||
return myorder.localId
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def cancelOrder(self, vtCancel): # type: (VtCancelOrderReq)->None
|
||||
"""撤单"""
|
||||
myorder = self._getOrder(vtCancel.orderID)
|
||||
symbol, contractType = self._contractTypeFromSymbol(vtCancel.symbol)
|
||||
self.api.cancelOrder(symbol=symbol,
|
||||
contractType=contractType,
|
||||
orderId=myorder.remoteId,
|
||||
onSuccess=self.onOrderCanceled,
|
||||
extra=myorder,
|
||||
)
|
||||
# cancelDict: 不存在的,没有localId就没有remoteId,没有remoteId何来cancel
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def cancelOrder(self, cancelOrderReq):
|
||||
"""撤单"""
|
||||
self.api.cancelOrder(cancelOrderReq)
|
||||
def queryOrder(self):
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def qryAccount(self):
|
||||
@ -207,8 +231,16 @@ class OkexFutureGateway(VnpyGateway):
|
||||
"""关闭"""
|
||||
self.api.close()
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
def onOrderSent(self, remoteId, myorder): #type: (int, _Order)->None
|
||||
myorder.remoteId = remoteId
|
||||
myorder.vtOrder.status = constant.STATUS_NOTTRADED
|
||||
self.onOrder(myorder.vtOrder)
|
||||
|
||||
|
||||
#----------------------------------------------------------------------
|
||||
@staticmethod
|
||||
def onOrderCanceled(myorder): #type: (_Order)->None
|
||||
myorder.vtOrder.status = constant.STATUS_CANCELLED
|
||||
|
||||
|
||||
|
||||
|
@ -143,10 +143,10 @@ class VtOrderData(VtBaseData):
|
||||
# 代码编号相关
|
||||
self.symbol = EMPTY_STRING # 合约代码
|
||||
self.exchange = EMPTY_STRING # 交易所代码
|
||||
self.vtSymbol = EMPTY_STRING # 合约在vt系统中的唯一代码,通常是 合约代码.交易所代码
|
||||
self.vtSymbol = EMPTY_STRING # 统一格式:f"{symbol}.{exchange}"
|
||||
|
||||
self.orderID = EMPTY_STRING # 订单编号
|
||||
self.vtOrderID = EMPTY_STRING # 订单在vt系统中的唯一编号,通常是 Gateway名.订单编号
|
||||
self.orderID = EMPTY_STRING # 订单编号 gateway内部自己生成的编号
|
||||
self.vtOrderID = EMPTY_STRING # 统一格式:f"{gatewayName}.{orderId}"
|
||||
|
||||
# 报单相关
|
||||
self.direction = EMPTY_UNICODE # 报单方向
|
||||
|
Loading…
Reference in New Issue
Block a user