| | |
| | | package com.xcong.excoin.modules.gateApi; |
| | | package com.xcong.excoin.modules.gateApi; |
| | | |
| | | import cn.hutool.core.collection.CollUtil; |
| | | import cn.hutool.core.util.StrUtil; |
| | |
| | | return; |
| | | } |
| | | |
| | | // [Gate-需求1] 多仓止盈触发:清空止盈状态 + 取消最远多仓止损 + 检查是否最后一个止盈 |
| | | // [Gate-需求1] 多仓止盈触发:清空止盈状态 + 取消最近多仓止损 |
| | | GridElement longTpElem = GridElement.findByLongTakeProfitOrderId(orderId); |
| | | if (longTpElem != null && StrUtil.isNotEmpty(tradeId) && !tradeId.equals("0")) { |
| | | longTakeProfitTraderIdParam(longTpElem, null, false); |
| | | log.info("[Gate] 多仓止盈触发 gridId:{}, orderId:{}", longTpElem.getId(), orderId); |
| | | cancelFarthestLongStopLoss(); |
| | | // checkLastTakeProfitAndRestart(); |
| | | cancelNearestLongStopLoss(); |
| | | return; |
| | | } |
| | | // [Gate-需求1] 空仓止盈触发:清空止盈状态 + 取消最远空仓止损 + 检查是否最后一个止盈 |
| | | // [Gate-需求1] 空仓止盈触发:清空止盈状态 + 取消最近空仓止损 |
| | | GridElement shortTpElem = GridElement.findByShortTakeProfitOrderId(orderId); |
| | | if (shortTpElem != null && StrUtil.isNotEmpty(tradeId) && !tradeId.equals("0")) { |
| | | shortTakeProfitTraderIdParam(shortTpElem, null, false); |
| | | log.info("[Gate] 空仓止盈触发 gridId:{}, orderId:{}", shortTpElem.getId(), orderId); |
| | | cancelFarthestShortStopLoss(); |
| | | cancelNearestShortStopLoss(); |
| | | // checkLastTakeProfitAndRestart(); |
| | | return; |
| | | } |
| | |
| | | // // 找多仓第一个(最近的)止损位置 |
| | | // int firstLongSlId = 0; |
| | | // for (GridElement e : config.getGridElements()) { |
| | | // if (e.getLongStopLossOrderId() != null) { |
| | | // if (e.hasLongStopLossOrders()) { |
| | | // if (firstLongSlId == 0 || e.getId() > firstLongSlId) { |
| | | // firstLongSlId = e.getId(); |
| | | // } |
| | |
| | | // // 找空仓第一个(最近的)止损位置 |
| | | // int firstShortSlId = 0; |
| | | // for (GridElement e : config.getGridElements()) { |
| | | // if (e.getShortStopLossOrderId() != null) { |
| | | // if (e.hasShortStopLossOrders()) { |
| | | // if (firstShortSlId == 0 || e.getId() < firstShortSlId) { |
| | | // firstShortSlId = e.getId(); |
| | | // } |
| | |
| | | // ORDER_TYPE_CLOSE_SHORT, |
| | | // size, |
| | | // profitId -> { |
| | | // elemShort.setShortStopLossOrderId(profitId); |
| | | // elemShort.addShortStopLossOrderId(profitId); |
| | | // GridElement.refreshIndices(); |
| | | // log.info("[Gate] 空仓止损已挂, gridId:{}, 触发价:{}, stopLossId:{}", shortTime, triggerPrice, profitId); |
| | | // } |
| | |
| | | // ORDER_TYPE_CLOSE_LONG, |
| | | // negate(size), |
| | | // profitId -> { |
| | | // elemLong.setLongStopLossOrderId(profitId); |
| | | // elemLong.addLongStopLossOrderId(profitId); |
| | | // GridElement.refreshIndices(); |
| | | // log.info("[Gate] 多仓止损已挂, gridId:{}, 触发价:{}, stopLossId:{}", longTime, triggerPrice, profitId); |
| | | // } |
| | |
| | | ORDER_TYPE_CLOSE_SHORT, |
| | | size, |
| | | profitId -> { |
| | | elem.setShortStopLossOrderId(profitId); |
| | | elem.addShortStopLossOrderId(profitId); |
| | | GridElement.refreshIndices(); |
| | | log.info("[Gate] 空仓止损已挂, gridId:{}, 触发价:{}, stopLossId:{}", finalId, triggerPrice, profitId); |
| | | } |
| | |
| | | ORDER_TYPE_CLOSE_LONG, |
| | | negate(size), |
| | | profitId -> { |
| | | elem.setLongStopLossOrderId(profitId); |
| | | elem.addLongStopLossOrderId(profitId); |
| | | GridElement.refreshIndices(); |
| | | log.info("[Gate] 多仓止损已挂, gridId:{}, 触发价:{}, stopLossId:{}", finalId, triggerPrice, profitId); |
| | | } |
| | |
| | | } |
| | | |
| | | private void handleLongStopLossTriggered(GridElement gridElement) { |
| | | gridElement.setLongStopLossOrderId(null); |
| | | gridElement.clearLongStopLossOrderIds(); |
| | | |
| | | accumulatedLongLossCount++; |
| | | int gridId = gridElement.getId(); |
| | |
| | | } |
| | | |
| | | private void handleShortStopLossTriggered(GridElement gridElement) { |
| | | gridElement.setShortStopLossOrderId(null); |
| | | gridElement.clearShortStopLossOrderIds(); |
| | | |
| | | accumulatedShortLossCount++; |
| | | int gridId = gridElement.getId(); |
| | |
| | | } |
| | | |
| | | /** |
| | | * 取消最远的多仓止损订单。 |
| | | * 多仓止损在 gridId 负方向,最远 = id 最小。 |
| | | * 取消最近的多仓止损订单(A 位置,gridId 最大即最接近 0)。 |
| | | * 多仓止损在 gridId 负方向,A = gridId-2,是三个位置中 ID 最大(最接近 0)的那个。 |
| | | */ |
| | | private void cancelFarthestLongStopLoss() { |
| | | GridElement farthest = null; |
| | | private void cancelNearestLongStopLoss() { |
| | | GridElement nearest = null; |
| | | for (GridElement e : config.getGridElements()) { |
| | | if (e.getLongStopLossOrderId() != null) { |
| | | if (farthest == null || e.getId() < farthest.getId()) { |
| | | farthest = e; |
| | | if (e.hasLongStopLossOrders()) { |
| | | if (nearest == null || e.getId() > nearest.getId()) { |
| | | nearest = e; |
| | | } |
| | | } |
| | | } |
| | | if (farthest != null) { |
| | | String slId = farthest.getLongStopLossOrderId(); |
| | | farthest.setLongStopLossOrderId(null); |
| | | if (nearest != null && nearest.hasLongStopLossOrders()) { |
| | | List<String> ids = nearest.getLongStopLossOrderIds(); |
| | | String slId = ids.get(0); // 取第一个(最早加入的 = A 位置第一单) |
| | | nearest.removeLongStopLossOrderId(slId); |
| | | GridElement.refreshIndices(); |
| | | GridElement finalFarthest = farthest; |
| | | GridElement finalNearest = nearest; |
| | | executor.cancelConditionalOrder(slId, oid -> |
| | | log.info("[Gate] 止盈触发, 取消最远多仓止损 gridId:{}, orderId:{}", finalFarthest.getId(), slId)); |
| | | log.info("[Gate] 止盈触发, 取消最近多仓止损 gridId:{}, orderId:{}", finalNearest.getId(), slId)); |
| | | } |
| | | } |
| | | |
| | | /** |
| | | * 取消最远的空仓止损订单。 |
| | | * 空仓止损在 gridId 正方向,最远 = id 最大。 |
| | | * 取消最近的空仓止损订单(A 位置,gridId 最小即最接近 0)。 |
| | | * 空仓止损在 gridId 正方向,A = gridId+2,是三个位置中 ID 最小(最接近 0)的那个。 |
| | | */ |
| | | private void cancelFarthestShortStopLoss() { |
| | | GridElement farthest = null; |
| | | private void cancelNearestShortStopLoss() { |
| | | GridElement nearest = null; |
| | | for (GridElement e : config.getGridElements()) { |
| | | if (e.getShortStopLossOrderId() != null) { |
| | | if (farthest == null || e.getId() > farthest.getId()) { |
| | | farthest = e; |
| | | if (e.hasShortStopLossOrders()) { |
| | | if (nearest == null || e.getId() < nearest.getId()) { |
| | | nearest = e; |
| | | } |
| | | } |
| | | } |
| | | if (farthest != null) { |
| | | String slId = farthest.getShortStopLossOrderId(); |
| | | farthest.setShortStopLossOrderId(null); |
| | | if (nearest != null && nearest.hasShortStopLossOrders()) { |
| | | List<String> ids = nearest.getShortStopLossOrderIds(); |
| | | String slId = ids.get(0); // 取第一个(最早加入的 = A 位置第一单) |
| | | nearest.removeShortStopLossOrderId(slId); |
| | | GridElement.refreshIndices(); |
| | | GridElement finalFarthest = farthest; |
| | | GridElement finalNearest = nearest; |
| | | executor.cancelConditionalOrder(slId, oid -> |
| | | log.info("[Gate] 止盈触发, 取消最远空仓止损 gridId:{}, orderId:{}", finalFarthest.getId(), slId)); |
| | | log.info("[Gate] 止盈触发, 取消最近空仓止损 gridId:{}, orderId:{}", finalNearest.getId(), slId)); |
| | | } |
| | | } |
| | | |
| | |
| | | e.setLongTakeProfitOrderId(null); |
| | | executor.cancelConditionalOrder(tpId, oid -> {}); |
| | | } |
| | | String slId = e.getLongStopLossOrderId(); |
| | | if (slId != null) { |
| | | e.setLongStopLossOrderId(null); |
| | | for (String slId : new ArrayList<>(e.getLongStopLossOrderIds())) { |
| | | executor.cancelConditionalOrder(slId, oid -> {}); |
| | | } |
| | | e.clearLongStopLossOrderIds(); |
| | | } |
| | | GridElement.refreshIndices(); |
| | | log.info("[Gate] 已提交取消所有多仓止盈+止损"); |
| | |
| | | e.setShortTakeProfitOrderId(null); |
| | | executor.cancelConditionalOrder(tpId, oid -> {}); |
| | | } |
| | | String slId = e.getShortStopLossOrderId(); |
| | | if (slId != null) { |
| | | e.setShortStopLossOrderId(null); |
| | | for (String slId : new ArrayList<>(e.getShortStopLossOrderIds())) { |
| | | executor.cancelConditionalOrder(slId, oid -> {}); |
| | | } |
| | | e.clearShortStopLossOrderIds(); |
| | | } |
| | | GridElement.refreshIndices(); |
| | | log.info("[Gate] 已提交取消所有空仓止盈+止损"); |
| | |
| | | log.info("[Gate] 首次成交,取消所有初始化止盈单"); |
| | | } |
| | | |
| | | // ========== 止损追单 ========== |
| | | // ========== 止损追单(新逻辑:3 个固定位置,每个位置挂多个 1 张止损单) ========== |
| | | |
| | | /** |
| | | * 多仓止损追单 — 3 个固定位置,从近到远分配合约。 |
| | | * A(gridId-2): (filledQty/qty - 2) 个独立止损单,每个 qty 张 |
| | | * B(gridId-3): 1 个止损单,qty 张 |
| | | * C(gridId-4): 1 个止损单,qty 张 |
| | | * 注意:多仓止损在 gridId 负方向,触发价 ≤ 网格价。 |
| | | */ |
| | | private void extendLongStopLoss(int filledQty,int gridId) { |
| | | int furthestSlId = 0; |
| | | for (GridElement e : config.getGridElements()) { |
| | | if (e.getLongStopLossOrderId() != null && e.getId() < furthestSlId) { |
| | | furthestSlId = e.getId(); |
| | | } |
| | | int qty = Integer.parseInt(config.getQuantity()); |
| | | int aCount = Math.max(0, filledQty / qty - 2); |
| | | log.info("[Gate] 多仓追挂止损, 成交{}张, gridId:{}, A({})x{} B({})x1 C({})x1", |
| | | filledQty, gridId, gridId - 2, aCount, gridId - 3, gridId - 4); |
| | | |
| | | // A 位置:挂 aCount 个独立止损单 |
| | | placeStopLossOrders(gridId - 2, aCount, qty, FuturesPriceTrigger.RuleEnum.NUMBER_2, |
| | | ORDER_TYPE_CLOSE_LONG, true); |
| | | // B 位置:挂 1 个 |
| | | placeStopLossOrders(gridId - 3, 1, qty, FuturesPriceTrigger.RuleEnum.NUMBER_2, |
| | | ORDER_TYPE_CLOSE_LONG, true); |
| | | // C 位置:挂 1 个 |
| | | placeStopLossOrders(gridId - 4, 1, qty, FuturesPriceTrigger.RuleEnum.NUMBER_2, |
| | | ORDER_TYPE_CLOSE_LONG, true); |
| | | } |
| | | |
| | | // int interval = 1; |
| | | // if (furthestSlId == 0) { |
| | | // furthestSlId = gridId; |
| | | // interval = 2; |
| | | // } |
| | | // int stopLossCount = filledQty / Integer.parseInt(config.getQuantity()); |
| | | // log.info("[Gate] 多仓追挂止损, 当前最远止损gridId:{}, 成交{}张, 追加{}个止损单", furthestSlId, filledQty, stopLossCount); |
| | | // for (int i = 0; i < stopLossCount; i++) { |
| | | // int newSlId = furthestSlId - i - interval; |
| | | // GridElement elem = GridElement.findById(newSlId); |
| | | // if (elem == null) { |
| | | // continue; |
| | | // } |
| | | // BigDecimal triggerPrice = elem.getGridPrice(); |
| | | // int finalSlId = newSlId; |
| | | // executor.placeTakeProfit( |
| | | // triggerPrice, |
| | | // FuturesPriceTrigger.RuleEnum.NUMBER_2, |
| | | // ORDER_TYPE_CLOSE_LONG, |
| | | // negate(config.getQuantity()), |
| | | // profitId -> { |
| | | // elem.setLongStopLossOrderId(profitId); |
| | | // GridElement.refreshIndices(); |
| | | // log.info("[Gate] 多仓止损追加, gridId:{}, 触发价:{}, stopLossId:{}", finalSlId, triggerPrice, profitId); |
| | | // } |
| | | // ); |
| | | // } |
| | | |
| | | int parseInt = Integer.parseInt(config.getQuantity()); |
| | | int total = filledQty - parseInt; |
| | | if (total > parseInt) { |
| | | String firstNum = String.valueOf(total); |
| | | log.info("[Gate] 多仓追挂止损, 当前最远止损gridId:{}, 成交{}张, 追加{}个止损单", furthestSlId, filledQty, 2); |
| | | int newSlId = gridId - 2; |
| | | GridElement elem = GridElement.findById(newSlId); |
| | | if (elem != null) { |
| | | BigDecimal triggerPrice = elem.getGridPrice(); |
| | | int finalSlId = newSlId; |
| | | executor.placeTakeProfit( |
| | | triggerPrice, |
| | | FuturesPriceTrigger.RuleEnum.NUMBER_2, |
| | | ORDER_TYPE_CLOSE_LONG, |
| | | negate(firstNum), |
| | | profitId -> { |
| | | elem.setLongStopLossOrderId(profitId); |
| | | GridElement.refreshIndices(); |
| | | log.info("[Gate] 多仓止损追加, gridId:{}, 触发价:{}, 数量:{}, stopLossId:{}", finalSlId, triggerPrice, firstNum, profitId); |
| | | } |
| | | ); |
| | | } |
| | | int newSecendSlId = gridId - 3; |
| | | GridElement elemSecend = GridElement.findById(newSecendSlId); |
| | | if (elemSecend != null) { |
| | | BigDecimal triggerPrice = elemSecend.getGridPrice(); |
| | | int finalSlId = newSecendSlId; |
| | | executor.placeTakeProfit( |
| | | triggerPrice, |
| | | FuturesPriceTrigger.RuleEnum.NUMBER_2, |
| | | ORDER_TYPE_CLOSE_LONG, |
| | | negate(config.getQuantity()), |
| | | profitId -> { |
| | | elemSecend.setLongStopLossOrderId(profitId); |
| | | GridElement.refreshIndices(); |
| | | log.info("[Gate] 多仓止损追加, gridId:{}, 触发价:{}, 数量:{}, stopLossId:{}", finalSlId, triggerPrice, config.getQuantity(), profitId); |
| | | } |
| | | ); |
| | | } |
| | | } |
| | | if (total == parseInt){ |
| | | String firstNum = config.getQuantity(); |
| | | log.info("[Gate] 多仓追挂止损, 当前最远止损gridId:{}, 成交{}张, 追加{}个止损单", furthestSlId, filledQty, 1); |
| | | int newSlId = gridId - 2; |
| | | GridElement elem = GridElement.findById(newSlId); |
| | | if (elem != null) { |
| | | BigDecimal triggerPrice = elem.getGridPrice(); |
| | | int finalSlId = newSlId; |
| | | executor.placeTakeProfit( |
| | | triggerPrice, |
| | | FuturesPriceTrigger.RuleEnum.NUMBER_2, |
| | | ORDER_TYPE_CLOSE_LONG, |
| | | negate(firstNum), |
| | | profitId -> { |
| | | elem.setLongStopLossOrderId(profitId); |
| | | GridElement.refreshIndices(); |
| | | log.info("[Gate] 多仓止损追加, gridId:{}, 触发价:{}, 数量:{}, stopLossId:{}", finalSlId, triggerPrice, firstNum, profitId); |
| | | } |
| | | ); |
| | | } |
| | | } |
| | | |
| | | } |
| | | |
| | | /** |
| | | * 空仓止损追单 — 3 个固定位置,从近到远分配合约。 |
| | | * A(gridId+2): (filledQty/qty - 2) 个独立止损单,每个 qty 张 |
| | | * B(gridId+3): 1 个止损单,qty 张 |
| | | * C(gridId+4): 1 个止损单,qty 张 |
| | | * 注意:空仓止损在 gridId 正方向,触发价 ≥ 网格价。 |
| | | */ |
| | | private void extendShortStopLoss(int filledQty, int gridId) { |
| | | int furthestSlId = 0; |
| | | for (GridElement e : config.getGridElements()) { |
| | | if (e.getShortStopLossOrderId() != null && e.getId() > furthestSlId) { |
| | | furthestSlId = e.getId(); |
| | | } |
| | | int qty = Integer.parseInt(config.getQuantity()); |
| | | int aCount = Math.max(0, filledQty / qty - 2); |
| | | log.info("[Gate] 空仓追挂止损, 成交{}张, gridId:{}, A({})x{} B({})x1 C({})x1", |
| | | filledQty, gridId, gridId + 2, aCount, gridId + 3, gridId + 4); |
| | | |
| | | // A 位置:挂 aCount 个独立止损单 |
| | | placeStopLossOrders(gridId + 2, aCount, qty, FuturesPriceTrigger.RuleEnum.NUMBER_1, |
| | | ORDER_TYPE_CLOSE_SHORT, false); |
| | | // B 位置:挂 1 个 |
| | | placeStopLossOrders(gridId + 3, 1, qty, FuturesPriceTrigger.RuleEnum.NUMBER_1, |
| | | ORDER_TYPE_CLOSE_SHORT, false); |
| | | // C 位置:挂 1 个 |
| | | placeStopLossOrders(gridId + 4, 1, qty, FuturesPriceTrigger.RuleEnum.NUMBER_1, |
| | | ORDER_TYPE_CLOSE_SHORT, false); |
| | | } |
| | | |
| | | // int interval = 1; |
| | | // if (furthestSlId == 0) { |
| | | // furthestSlId = gridId; |
| | | // interval = 2; |
| | | // } |
| | | // int stopLossCount = filledQty / Integer.parseInt(config.getQuantity()); |
| | | // log.info("[Gate] 空仓追挂止损, 当前最远止损gridId:{}, 成交{}张, 追加{}个止损单", furthestSlId, filledQty, stopLossCount); |
| | | // for (int i = 0; i < stopLossCount; i++) { |
| | | // int newSlId = furthestSlId + i + interval; |
| | | // GridElement elem = GridElement.findById(newSlId); |
| | | // if (elem == null) { |
| | | // continue; |
| | | // } |
| | | // BigDecimal triggerPrice = elem.getGridPrice(); |
| | | // int finalSlId = newSlId; |
| | | // executor.placeTakeProfit( |
| | | // triggerPrice, |
| | | // FuturesPriceTrigger.RuleEnum.NUMBER_1, |
| | | // ORDER_TYPE_CLOSE_SHORT, |
| | | // config.getQuantity(), |
| | | // profitId -> { |
| | | // elem.setShortStopLossOrderId(profitId); |
| | | // GridElement.refreshIndices(); |
| | | // log.info("[Gate] 空仓止损追加, gridId:{}, 触发价:{}, stopLossId:{}", finalSlId, triggerPrice, profitId); |
| | | // } |
| | | // ); |
| | | // } |
| | | |
| | | int parseInt = Integer.parseInt(config.getQuantity()); |
| | | int total = filledQty - parseInt; |
| | | if (total > parseInt) { |
| | | String firstNum = String.valueOf(total); |
| | | log.info("[Gate] 空仓追挂止损, 当前最远止损gridId:{}, 成交{}张, 追加{}个止损单", furthestSlId, filledQty, 2); |
| | | int newSlId = gridId + 2; |
| | | GridElement elem = GridElement.findById(newSlId); |
| | | if (elem != null) { |
| | | /** |
| | | * 在指定网格位置挂 count 个独立止损单,每个 size 张。 |
| | | */ |
| | | private void placeStopLossOrders(int gridId, int count, int qty, |
| | | FuturesPriceTrigger.RuleEnum rule, |
| | | String orderType, boolean isLong) { |
| | | if (count <= 0) { |
| | | return; |
| | | } |
| | | GridElement elem = GridElement.findById(gridId); |
| | | if (elem == null) { |
| | | log.warn("[Gate] 止损挂单位置不存在, gridId:{}", gridId); |
| | | return; |
| | | } |
| | | BigDecimal triggerPrice = elem.getGridPrice(); |
| | | int finalSlId = newSlId; |
| | | for (int i = 0; i < count; i++) { |
| | | String size = isLong ? negate(String.valueOf(qty)) : String.valueOf(qty); |
| | | int finalGridId = gridId; |
| | | int finalI = i; |
| | | executor.placeTakeProfit( |
| | | triggerPrice, |
| | | FuturesPriceTrigger.RuleEnum.NUMBER_1, |
| | | ORDER_TYPE_CLOSE_SHORT, |
| | | firstNum, |
| | | triggerPrice, rule, orderType, size, |
| | | profitId -> { |
| | | elem.setShortStopLossOrderId(profitId); |
| | | if (isLong) { |
| | | elem.addLongStopLossOrderId(profitId); |
| | | } else { |
| | | elem.addShortStopLossOrderId(profitId); |
| | | } |
| | | GridElement.refreshIndices(); |
| | | log.info("[Gate] 空仓止损追加, gridId:{}, 触发价:{}, 数量:{}, stopLossId:{}", finalSlId, triggerPrice, firstNum, profitId); |
| | | log.info("[Gate] {}止损追加, gridId:{}, 触发价:{}, 第{}单, stopLossId:{}", |
| | | isLong ? "多仓" : "空仓", finalGridId, triggerPrice, finalI + 1, profitId); |
| | | } |
| | | ); |
| | | } |
| | | int newSecendSlId = gridId + 2; |
| | | GridElement elemSecend = GridElement.findById(newSecendSlId); |
| | | if (elemSecend != null) { |
| | | BigDecimal triggerPrice = elemSecend.getGridPrice(); |
| | | int finalSlId = newSecendSlId; |
| | | executor.placeTakeProfit( |
| | | triggerPrice, |
| | | FuturesPriceTrigger.RuleEnum.NUMBER_1, |
| | | ORDER_TYPE_CLOSE_SHORT, |
| | | config.getQuantity(), |
| | | profitId -> { |
| | | elemSecend.setShortStopLossOrderId(profitId); |
| | | GridElement.refreshIndices(); |
| | | log.info("[Gate] 空仓止损追加, gridId:{}, 触发价:{}, 数量:{}, stopLossId:{}", finalSlId, triggerPrice, config.getQuantity(), profitId); |
| | | } |
| | | ); |
| | | } |
| | | } |
| | | if (total == parseInt) { |
| | | String firstNum = config.getQuantity(); |
| | | log.info("[Gate] 空仓追挂止损, 当前最远止损gridId:{}, 成交{}张, 追加{}个止损单", furthestSlId, filledQty, 1); |
| | | int newSlId = gridId + 2; |
| | | GridElement elem = GridElement.findById(newSlId); |
| | | if (elem != null) { |
| | | BigDecimal triggerPrice = elem.getGridPrice(); |
| | | int finalSlId = newSlId; |
| | | executor.placeTakeProfit( |
| | | triggerPrice, |
| | | FuturesPriceTrigger.RuleEnum.NUMBER_1, |
| | | ORDER_TYPE_CLOSE_SHORT, |
| | | firstNum, |
| | | profitId -> { |
| | | elem.setShortStopLossOrderId(profitId); |
| | | GridElement.refreshIndices(); |
| | | log.info("[Gate] 空仓止损追加, gridId:{}, 触发价:{}, 数量:{}, stopLossId:{}", finalSlId, triggerPrice, firstNum, profitId); |
| | | } |
| | | ); |
| | | } |
| | | } |
| | | |
| | | } |
| | | |
| | | // ---- 工具 ---- |