我正在尝试创建一个括号定单,该定单将退出目标 1 处头寸的 1/2 和目标 2 处第二半头寸。我能够生成订单,但是,两个目标的数量是整个头寸量而不是 1/2。例如,当下订单购买 200 SPY 时,获利订单的数量应为每个 100,而不是 200。但是,当我运行我的代码时,这是 TWS 中显示的订单:
我正在跑步:
Python 3.8.2 (default, May 6 2020, 09:02:42) [MSC v.1916 64 bit (AMD64)]
ib_insync 0.9.61
TWS Build 979.4t
Java Version: 1.8.0_152, OS: Windows 10 (amd64, 10.0)
关于如何解决这个问题有什么想法吗?
请运行此代码来重现该情况:
from ib_insync import *
import time
from typing import NamedTuple
class BracketOrderTwoTargets(NamedTuple):
parent: Order
takeProfit: Order
takeProfit2: Order
stopLoss: Order
#modified from this post, https://groups.io/g/insync/message/3135
def bracketStopLimitOrderTwoTargets(
action: str, quantity: float, stopPrice: float,
limitPrice: float, takeProfitPrice1: float, takeProfitPrice2: float,
stopLossPrice: float, **kwargs) -> BracketOrderTwoTargets:
"""
Create a limit order that is bracketed by 2 take-profit orders and
a stop-loss order. Submit the bracket like:
Args:
action: 'BUY' or 'SELL'.
quantity: Size of order.
stopPrice: Stop Price for stopLimit entry order
limitPrice: Limit price of entry order.
takeProfitPrice1: 1st Limit price of profit order.
takeProfitPrice2: 2nd Limit price of profit order.
stopLossPrice: Stop price of loss order.
StopLimitOrder(action, totalQuantity, lmtPrice, stopPrice, **kwargs)
"""
assert action in ('BUY', 'SELL')
reverseAction = 'BUY' if action == 'SELL' else 'SELL'
parent = StopLimitOrder(
action, quantity, limitPrice, stopPrice,
orderId=ib.client.getReqId(),
transmit=False,
outsideRth=True,
**kwargs)
takeProfit1 = LimitOrder(
action=reverseAction, totalQuantity=quantity/2, lmtPrice=takeProfitPrice1,
orderId=ib.client.getReqId(),
transmit=False,
parentId=parent.orderId,
outsideRth=True,
**kwargs)
takeProfit2 = LimitOrder(
action=reverseAction, totalQuantity=quantity/2, lmtPrice=takeProfitPrice2,
orderId=ib.client.getReqId(),
transmit=False,
parentId=parent.orderId,
outsideRth=True,
**kwargs)
stopLoss = StopOrder(
reverseAction, quantity, stopLossPrice,
orderId=ib.client.getReqId(),
transmit=True,
parentId=parent.orderId,
outsideRth = True,
**kwargs)
return BracketOrderTwoTargets(parent, takeProfit1, takeProfit2, stopLoss)
ib = IB()
client_id = int(time.time()) # gets second since epoch. No need for the milliseconds, so round to int
ib.connect('127.0.0.1', 7497, clientId=client_id, timeout=10)
contract = Stock('SPY', exchange='SMART', currency='USD')
[ticker] = ib.reqTickers(contract)
contract_price = ticker.marketPrice()
high_bracket = bracketStopLimitOrderTwoTargets(action='BUY', quantity=200, stopPrice=contract_price+18,
limitPrice=contract_price+20,
takeProfitPrice1=contract_price+30,
takeProfitPrice2=contract_price+45,
stopLossPrice=contract_price-5)
for order in high_bracket:
order_res = ib.placeOrder(contract=contract, order=order)
print(order_res)
另一种方法是使用获利者附加的比例字段。我不知道 API 是什么样的,但首先在 TWS ui 中查看一下。在 UI 中,您将看到 - 初始组件、缩放组件和缩放价格。然后,您可以将初始分量设置为 100,如果您希望后续批次不同,请在比例分量中指定该尺寸。
你不能将父级分成与数量/2相同的2个吗?我不确定 IB 的费用是如何运作的,但我想它不会花费太多。