From cbcf781d20056b5b703217d2da971c20a2c68502 Mon Sep 17 00:00:00 2001 From: chenxy123 Date: Wed, 8 Mar 2017 22:27:08 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E9=A3=8E=E6=8E=A7=E6=A8=A1?= =?UTF-8?q?=E5=9D=97=E5=85=B3=E4=BA=8E=E6=92=A4=E5=8D=95=E7=BB=9F=E8=AE=A1?= =?UTF-8?q?=E9=83=A8=E5=88=86=E4=BB=A3=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- vn.trader/riskManager/RM_setting.json | 2 +- vn.trader/riskManager/rmEngine.py | 58 ++++++++++++++------------- vn.trader/riskManager/uiRmWidget.py | 9 +++-- vn.trader/vtConstant.py | 12 ------ vn.trader/vtEngine.py | 5 +-- vn.trader/vtGateway.py | 2 - 6 files changed, 39 insertions(+), 49 deletions(-) diff --git a/vn.trader/riskManager/RM_setting.json b/vn.trader/riskManager/RM_setting.json index 70eacac5..1e452dd7 100644 --- a/vn.trader/riskManager/RM_setting.json +++ b/vn.trader/riskManager/RM_setting.json @@ -1,9 +1,9 @@ { "orderFlowClear": 1, + "orderCancelLimit": 10, "workingOrderLimit": 20, "tradeLimit": 100, "orderSizeLimit": 10, "active": true, - "orderCountLimit": 400, "orderFlowLimit": 50 } \ No newline at end of file diff --git a/vn.trader/riskManager/rmEngine.py b/vn.trader/riskManager/rmEngine.py index 50f7c1de..6f270bca 100644 --- a/vn.trader/riskManager/rmEngine.py +++ b/vn.trader/riskManager/rmEngine.py @@ -47,9 +47,9 @@ class RmEngine(object): self.tradeCount = EMPTY_INT # 当日成交合约数量统计 self.tradeLimit = EMPTY_INT # 当日成交合约数量限制 - # 单品种报撤 - self.orderCountLimit = 450 - self.orderCount = {} + # 单品种撤单统计 + self.orderCancelLimit = EMPTY_INT # 撤单总次数限制 + self.orderCancelDict = {} # 单一合约对应撤单次数的字典 # 活动合约相关 self.workingOrderLimit = EMPTY_INT # 活动合约最大限制 @@ -75,7 +75,7 @@ class RmEngine(object): self.workingOrderLimit = d['workingOrderLimit'] - self.orderCountLimit = d['orderCountLimit'] + self.orderCancelLimit = d['orderCancelLimit'] #---------------------------------------------------------------------- def saveSetting(self): @@ -95,7 +95,7 @@ class RmEngine(object): d['workingOrderLimit'] = self.workingOrderLimit - d['orderCountLimit'] = self.orderCountLimit + d['orderCancelLimit'] = self.orderCancelLimit # 写入json jsonD = json.dumps(d, indent=4) @@ -107,16 +107,19 @@ class RmEngine(object): self.eventEngine.register(EVENT_TRADE, self.updateTrade) self.eventEngine.register(EVENT_TIMER, self.updateTimer) self.eventEngine.register(EVENT_ORDER, self.updateOrder) - + + #---------------------------------------------------------------------- def updateOrder(self, event): """更新成交数据""" + # 只需要统计撤单成功的委托 order = event.dict_['data'] - if not self.orderCount.has_key(order.symbol): - self.orderCount[order.symbol] = 0 - if order.status in [STATUS_NOTTRADED, STATUS_PARTTRADED, STATUS_ALLTRADED, STATUS_UNKNOWN]: - self.orderCount[order.symbol] += 1 - elif order.status == STATUS_CANCELLED: - self.orderCount[order.symbol] += 2 + if order.status != STATUS_CANCELLED: + return + + if order.symbol not in self.orderCancelDict: + self.orderCancelDict[order.symbol] = 1 + else: + self.orderCancelDict[order.symbol] += 1 #---------------------------------------------------------------------- def updateTrade(self, event): @@ -156,42 +159,43 @@ class RmEngine(object): """检查风险""" # 如果没有启动风控检查,则直接返回成功 if not self.active: - return RISK_OK + return True # 检查委托数量 if orderReq.volume > self.orderSizeLimit: self.writeRiskLog(u'单笔委托数量%s,超过限制%s' %(orderReq.volume, self.orderSizeLimit)) - return RISK_ERROR_ORDER_SIZE + return False # 检查成交合约量 if self.tradeCount >= self.tradeLimit: self.writeRiskLog(u'今日总成交合约数量%s,超过限制%s' %(self.tradeCount, self.tradeLimit)) - return RISK_ERROR_TRADE_COUNT + return False # 检查流控 if self.orderFlowCount >= self.orderFlowLimit: self.writeRiskLog(u'委托流数量%s,超过限制每%s秒%s' %(self.orderFlowCount, self.orderFlowClear, self.orderFlowLimit)) - return RISK_ERROR_ORDER_FLOW_COUNT + return False # 检查总活动合约 workingOrderCount = len(self.mainEngine.getAllWorkingOrders()) if workingOrderCount >= self.workingOrderLimit: self.writeRiskLog(u'当前活动委托数量%s,超过限制%s' %(workingOrderCount, self.workingOrderLimit)) - return RISK_ERROR_WORKING_ORDER - - if self.orderCount.has_key(orderReq.symbol) and self.orderCount[orderReq.symbol] > self.orderCountLimit: - self.writeRiskLog(u'%s当日报撤%s,超过限制%s' - % (orderReq.symbol, self.orderCount[orderReq.symbol], self.orderCountLimit)) - return RISK_ERROR_ORDER_SEND + return False + # 检查撤单次数 + if orderReq.symbol in self.orderCancelDict and self.orderCancelDict[orderReq.symbol] >= self.orderCancelLimit: + self.writeRiskLog(u'当日%s撤单次数%s,超过限制%s' + %(orderReq.symbol, self.orderCancelDict[orderReq.symbol], self.orderCancelLimit)) + return False + # 对于通过风控的委托,增加流控计数 self.orderFlowCount += 1 - return RISK_OK + return True #---------------------------------------------------------------------- def clearOrderFlowCount(self): @@ -230,10 +234,10 @@ class RmEngine(object): """设置活动合约限制""" self.workingOrderLimit = n - #---------------------------------------------------------------------- - def setOrderCountLimit(self, n): - """设置单品种报撤次数上限""" - self.orderCountLimit = n + #---------------------------------------------------------------------- + def setOrderCancelLimit(self, n): + """设置单合约撤单次数上限""" + self.orderCancelLimit = n #---------------------------------------------------------------------- def switchEngineStatus(self): diff --git a/vn.trader/riskManager/uiRmWidget.py b/vn.trader/riskManager/uiRmWidget.py index 74eff945..bfa5101c 100644 --- a/vn.trader/riskManager/uiRmWidget.py +++ b/vn.trader/riskManager/uiRmWidget.py @@ -68,7 +68,7 @@ class RmEngineManager(QtGui.QWidget): self.spinOrderSizeLimit = RmSpinBox(self.rmEngine.orderSizeLimit) self.spinTradeLimit = RmSpinBox(self.rmEngine.tradeLimit) self.spinWorkingOrderLimit = RmSpinBox(self.rmEngine.workingOrderLimit) - self.spinOrderCountLimit = RmSpinBox(self.rmEngine.orderCountLimit) + self.spinOrderCancelLimit = RmSpinBox(self.rmEngine.orderCancelLimit) buttonClearOrderFlowCount = QtGui.QPushButton(u'清空流控计数') buttonClearTradeCount = QtGui.QPushButton(u'清空总成交计数') @@ -92,8 +92,9 @@ class RmEngineManager(QtGui.QWidget): grid.addWidget(RmLine(), 8, 0, 1, 2) grid.addWidget(Label(u'活动订单上限'), 9, 0) grid.addWidget(self.spinWorkingOrderLimit, 9, 1) - grid.addWidget(Label(u'单品种报撤次数上限'), 10, 0) - grid.addWidget(self.spinOrderCountLimit, 10, 1) + grid.addWidget(RmLine(), 10, 0, 1, 2) + grid.addWidget(Label(u'单合约撤单上限'), 11, 0) + grid.addWidget(self.spinOrderCancelLimit, 11, 1) hbox = QtGui.QHBoxLayout() hbox.addWidget(buttonClearOrderFlowCount) @@ -112,7 +113,7 @@ class RmEngineManager(QtGui.QWidget): self.spinOrderSizeLimit.valueChanged.connect(self.rmEngine.setOrderSizeLimit) self.spinTradeLimit.valueChanged.connect(self.rmEngine.setTradeLimit) self.spinWorkingOrderLimit.valueChanged.connect(self.rmEngine.setWorkingOrderLimit) - self.spinOrderCountLimit.valueChanged.connect(self.rmEngine.setOrderCountLimit) + self.spinOrderCancelLimit.valueChanged.connect(self.rmEngine.setOrderCancelLimit) self.buttonSwitchEngineStatus.clicked.connect(self.switchEngineSatus) buttonClearOrderFlowCount.clicked.connect(self.rmEngine.clearOrderFlowCount) diff --git a/vn.trader/vtConstant.py b/vn.trader/vtConstant.py index 66488ab2..fc3efce7 100644 --- a/vn.trader/vtConstant.py +++ b/vn.trader/vtConstant.py @@ -6,18 +6,6 @@ EMPTY_UNICODE = u'' EMPTY_INT = 0 EMPTY_FLOAT = 0.0 -# 风控常量 -RISK_OK = 0 # 风控正常 -RISK_ERROR_ORDER_SIZE = 1 # 单笔委托数量超限 -RISK_ERROR_TRADE_COUNT = 2 # 今日总成交合约数量超限 -RISK_ERROR_ORDER_FLOW_COUNT = 3 # 委托流数量超限 -RISK_ERROR_WORKING_ORDER = 4 # 当前活动委托数量超限 -RISK_ERROR_ORDER_SEND = 5 # 当日单品种报撤次数超限 - -RISK_MESSAGE = {RISK_ERROR_ORDER_SIZE: u'单笔委托数量超限', RISK_ERROR_TRADE_COUNT: u'今日总成交合约数量超限', - RISK_ERROR_ORDER_FLOW_COUNT: u'委托流数量超限', RISK_ERROR_WORKING_ORDER: u'当前活动委托数量超限', - RISK_ERROR_ORDER_SEND: u'当日单品种报撤次数超限'} - # 方向常量 DIRECTION_NONE = u'无方向' DIRECTION_LONG = u'多' diff --git a/vn.trader/vtEngine.py b/vn.trader/vtEngine.py index 6a517ffd..f6c011c6 100644 --- a/vn.trader/vtEngine.py +++ b/vn.trader/vtEngine.py @@ -188,9 +188,8 @@ class MainEngine(object): def sendOrder(self, orderReq, gatewayName): """对特定接口发单""" # 如果风控检查失败则不发单 - riskResult = self.rmEngine.checkRisk(orderReq) - if riskResult != RISK_OK: - return riskResult + if not self.rmEngine.checkRisk(orderReq): + return '' if gatewayName in self.gatewayDict: gateway = self.gatewayDict[gatewayName] diff --git a/vn.trader/vtGateway.py b/vn.trader/vtGateway.py index 9a350d7f..cf1c30ef 100644 --- a/vn.trader/vtGateway.py +++ b/vn.trader/vtGateway.py @@ -291,8 +291,6 @@ class VtPositionData(VtBaseData): self.frozen = EMPTY_INT # 冻结数量 self.price = EMPTY_FLOAT # 持仓均价 self.vtPositionName = EMPTY_STRING # 持仓在vt系统中的唯一代码,通常是vtSymbol.方向 - - # 20151020添加 self.ydPosition = EMPTY_INT # 昨持仓