Проблема с открытием стопзаявки в квике. StockSharp

Author: Sumrak $6

Через вашу библиотеку стокшарп, есть настроенное подключение к квику и создана стратегия в которой открываются рыночная сделка(здесь проблем нет) и после регистрация ордера, пытаюсь открыть стопзаявку, но заявки в терминале не открываются, в логах пишет следующие ошибки см ниже. Уже много чего перепробовал, сравнивал параметры сделок открытых в терминале квик и через стратегию, но сделки так и не открываются. Может быть я не донастроил чего или может быть есть пример кода.



Connector    30.03.2021 20:36:59 +07:00    Error    OrderRegisterFailed
74173666/ HYDR@TQBR L01+00000F00 Продажа Цена=0,796652 Объем=194 Сост=Failed Бал=194 Тип=Conditional UID=f8c11f9f-c9d0-451f-946b-b18eb2487cb6 Strategy=f8c11f9f-c9d0-451f-946b-b18eb2487cb6 Condition=Quik: IsRepo=False,IsNtm=False,RepoInfo=StockSharp.Messages.RepoOrderInfo,NtmInfo=StockSharp.Messages.NtmOrderInfo,ConditionOrderId=0,ConditionOrderPartiallyMatched=True,ConditionOrderUseMatchedBalance=False,IsMarketStopLimit=False,IsMarketTakeProfit=False,LinkedOrderCancel=False,LinkedOrderPrice=0,Offset=0%,Spread=0%,StopPrice=0,806652,StopLimitPrice=0,Type=StopLimit,StopPriceCondition=LessOrEqual
System.NullReferenceException: Object reference not set to an instance of an object.
   at StockSharp.Fix.Native.Extensions.GetFixType(OrderMessage message)
   at StockSharp.Fix.Dialects.DefaultFixDialect.#=zbwl8lj7uJXmc(IFixWriter #=zwIES6Gc=, OrderRegisterMessage #=zDhJ4Gl36iHoQ)
   at StockSharp.Fix.Dialects.DefaultFixDialect.OnWrite(IFixWriter writer, Message message)
   at StockSharp.Fix.Dialects.BaseFixDialect.SendInMessage(Message message)
   at StockSharp.Fix.FixMessageAdapter.OnSendInMessage(Message message)
   at StockSharp.Messages.MessageAdapter.SendInMessage(Message message)

Quik LUA. Transactions    30.03.2021 20:36:59 +07:00    Error    System.NullReferenceException: Object reference not set to an instance of an object.
   at StockSharp.Fix.Native.Extensions.GetFixType(OrderMessage message)
   at StockSharp.Fix.Dialects.DefaultFixDialect.#=zbwl8lj7uJXmc(IFixWriter #=zwIES6Gc=, OrderRegisterMessage #=zDhJ4Gl36iHoQ)
   at StockSharp.Fix.Dialects.DefaultFixDialect.OnWrite(IFixWriter writer, Message message)
   at StockSharp.Fix.Dialects.BaseFixDialect.SendInMessage(Message message)
   at StockSharp.Fix.FixMessageAdapter.OnSendInMessage(Message message)
   at StockSharp.Messages.MessageAdapter.SendInMessage(Message message)





5 Answers
Support

Avatar
Date: 5/18/2021
Reply


можете привести пример кода, как именно вы создаете и посылаете заявку?
Thanks:

Sumrak

Avatar
Date: 5/19/2021
Reply


Пример! Я пробовал запускать пример открытия сделки из проекта SampleConnectionGitHub, файла OrdersWindow.xaml.cs. И из документации тоже пробовал примеры. В примерах ниже пробовал различные вариации параметров. Думал может неправильно указывал параметры стоплоса или тейкпрофита/счета или направление сделки, поэтому разные варианты пробовал.
Пробовал делать открытие через окно и через код. Ниже примеры различных вариаций примеров открытия сделок.
Сам коннектор использую тоже из примера, настройки подключение тоже дефолтные.

var lots = 1;
var side = Sides.Buy;
var portf = Connector.Portfolios.ToList();
// portf = L01+00000F00
// sec = "HYDR@TQBR"
//var sec = _settings.DicSecurity.ElementAt(0).Key;

var newOrder = new OrderWindow
{
Order = new Order { Security = sec },

}.Init(Connector);

if (newOrder.ShowModal(this))
Connector.RegisterOrder(newOrder.Order);

// Рыночные заявки открываются без проблем
var order = new Order
{
// устанавливается тип заявки, в данном примере лимитный
Type = OrderTypes.Market,
// устанавливается портфель для исполнения заявки
Portfolio = portf[0],
// устанавливается объём заявки
Volume = 1,
// устанавливается цена заявки
Price = 0,
// устанавливается инструмент
Security = sec,
// устанавливается направление заявки, в данном примере покупка
Direction = Sides.Buy,
};
Connector.RegisterOrder(order);

// А вот стоп заяки не хотят открываться
var order2 = new Order
{
Security = sec,
Portfolio = portf[7],
Price = sec.BestBid.GetValueOrDefault().Price - 10 * GetPriceStep(sec),
Volume = lots,
Balance = lots,
Direction = Sides.Sell,
Type = OrderTypes.Conditional,
Condition = new QuikOrderCondition()
{
Type = QuikOrderConditionTypes.StopLimit,
StopLimitPrice = sec.BestBid.GetValueOrDefault().Price + (side == Sides.Buy ? -15 : 15) * GetPriceStep(sec),
}
};
Connector.RegisterOrder(order2);

var order3 = new Order
{
Security = sec,
Portfolio = portf[2],
Price = 0,//sec.BestBid.GetValueOrDefault().Price - 10 * GetPriceStep(sec),
Volume = lots,
Balance = lots,
Direction = Sides.Sell,
Type = OrderTypes.Conditional,
Condition = new QuikOrderCondition()
{
ActiveTime = null,
ConditionOrderId = 0,
ConditionOrderPartiallyMatched = true,
ConditionOrderSide = Sides.Sell,
ConditionOrderUseMatchedBalance = true,
IsMarketStopLimit = true,
IsMarketTakeProfit = true,
IsNtm = false,
IsRepo = false,
LinkedOrderCancel = false,
LinkedOrderPrice = 0,
Spread = new Unit(0),
Offset = new Unit(0),
OtherSecurityId = sec.ToSecurityId(),
StopLimitPrice = sec.BestBid.GetValueOrDefault().Price + (side == Sides.Sell ? -150 : 150) * GetPriceStep(sec),
StopPrice = sec.BestBid.GetValueOrDefault().Price + (side == Sides.Sell ? 150 : -150) * GetPriceStep(sec),
StopPriceCondition = QuikStopPriceConditions.MoreOrEqual,
Type = QuikOrderConditionTypes.StopLimit,
}
};
Connector.RegisterOrder(order3);

var order4 = new Order
{
Security = sec,
Portfolio = portf[7],
Price = sec.BestBid.GetValueOrDefault().Price - 10 * GetPriceStep(sec),
Volume = lots,
Direction = Sides.Sell,
Type = OrderTypes.Conditional,
Condition = new QuikOrderCondition()
{
Type = QuikOrderConditionTypes.StopLimit,
StopPrice = sec.BestBid.GetValueOrDefault().Price + (side == Sides.Buy ? 15 : -15) * GetPriceStep(sec),
}
};
Connector.RegisterOrder(order4);

var order5 = new Order
{
Security = sec,
Portfolio = portf[7],
Price = sec.BestBid.GetValueOrDefault().Price - 10 * GetPriceStep(sec),
Volume = lots,
Direction = Sides.Sell,
Type = OrderTypes.Conditional,
Condition = new QuikOrderCondition()
{
Type = QuikOrderConditionTypes.StopLimit,
StopPrice = sec.BestBid.GetValueOrDefault().Price + (side == Sides.Buy ? -15 : 15) * GetPriceStep(sec),
}
};
Connector.RegisterOrder(order5);

//decimal price = Sides.Buy == side ? sec.BestBid.Price : sec.BestAsk.Price;
QuikOrderCondition condition = new QuikOrderCondition();
// Не заполнялась в позициях
condition.ConditionOrderSide = side == Sides.Buy ? Sides.Sell : Sides.Buy;
condition.IsMarketStopLimit = true; // цена по рынку сл
condition.IsMarketTakeProfit = true; // цена по рынку тп

//Unit Slippage = GetPriceStep(sec) * 100;
condition.Offset = new Unit(0, UnitTypes.Percent); // отступ от макса
condition.Spread = new Unit(0, UnitTypes.Percent); // отступ от макса
condition.StopPrice = sec.BestAsk.GetValueOrDefault().Price + (side == Sides.Buy ? -10 : 10) * GetPriceStep(sec); // sl
//StopLimitPrice
//condition.StopPrice = sec.BestAsk.GetValueOrDefault().Price + (side == Sides.Buy ? 10 : -10) * GetPriceStep(sec);

//condition.StopPriceCondition = QuikStopPriceConditions.MoreOrEqual;
//condition.Type = QuikOrderConditionTypes.TakeProfitStopLimit;
condition.Type = QuikOrderConditionTypes.StopLimit;
//condition.StopPriceCondition = QuikStopPriceConditions.MoreOrEqual;

Order OrderSLTP = new Order
{
Id = 1,
Security = sec,
Portfolio = portf[2], // mainOrder.Portfolio
Type = OrderTypes.Conditional,
Condition = condition,
ExpiryDate = null,
Volume = 1,
Price = 0,
//Price = (decimal)(condition.StopPrice + (side == Sides.Buy ? -Slippage.Value : Slippage.Value)),
Direction = Sides.Sell,
Comment = "test comment",
};

Connector.RegisterOrder(OrderSLTP);
image4180.png 55 KB (1)
Topic starter
Thanks:

Sumrak

Avatar
Date: 5/19/2021
Reply


Еще был такой вариант, пробовал заполнять все поля. Так же пробовал завадать идентичные параметры по уже открытым стопзаявкам, которые приходят после подключения из квика.

private Order GetSLTPOrder(Order mainOrder, decimal sl, decimal tp, decimal price)
{
QuikOrderCondition condition = new QuikOrderCondition();
condition.ConditionOrderId = 0;
condition.ConditionOrderPartiallyMatched = true;
condition.ConditionOrderSide = mainOrder.Direction == Sides.Buy ? Sides.Sell : Sides.Buy;
condition.ConditionOrderUseMatchedBalance = false;
condition.IsMarketStopLimit = false; // цена по рынку сл
condition.IsMarketTakeProfit = false; // цена по рынку тп
condition.LinkedOrderCancel = false;
condition.LinkedOrderPrice = 0;
//condition.ActiveTime = null; // время до снятия ордера
//condition.ConditionOrderId = mainOrder.Id;
//condition.ConditionOrderPartiallyMatched = false;
//condition.ConditionOrderUseMatchedBalance = true;
//condition.IsMarketStopLimit = true; // цена по рынку сл
//condition.IsMarketTakeProfit = true; // цена по рынку тп
//condition.LinkedOrderCancel = false;
//condition.LinkedOrderPrice = 0;

Unit Slippage = GetPriceStep(mainOrder.Security) * 100;
condition.Offset = new Unit(0, UnitTypes.Percent); // отступ от макса
condition.Spread = new Unit(0, UnitTypes.Percent); // отступ от макса
condition.StopPrice = Math.Round(price * (100 + sl) / 100, mainOrder.Security.Decimals.GetValueOrDefault()); // sl
condition.StopLimitPrice = Math.Round(price * (100 + tp) / 100, mainOrder.Security.Decimals.GetValueOrDefault());

condition.Type = QuikOrderConditionTypes.TakeProfitStopLimit;
condition.StopPriceCondition = QuikStopPriceConditions.MoreOrEqual;



Order OrderSLTP = new Order
{
Security = mainOrder.Security,
Portfolio = Portfolio, // mainOrder.Portfolio
Type = OrderTypes.Conditional,
Condition = condition,
Volume = mainOrder.Volume,
Price = 0,
Direction = mainOrder.Direction == Sides.Buy ? Sides.Sell : Sides.Buy,
Comment = mainOrder.Comment,
};

OrderSLTP.ExtensionInfo = new Dictionary<string, Object>();
foreach (var pair in mainOrder.ExtensionInfo)
{
OrderSLTP.ExtensionInfo.Add(pair.Key, pair.Value);
}

return OrderSLTP;
}
Topic starter
Thanks:

Юрий Басангов

Avatar
Date: 6/9/2021
Reply


Sumrak Go to
Еще был такой вариант, пробовал заполнять все поля. Так же пробовал завадать идентичные параметры по уже открытым стопзаявкам, которые приходят после подключения из квика.

private Order GetSLTPOrder(Order mainOrder, decimal sl, decimal tp, decimal price)
{
QuikOrderCondition condition = new QuikOrderCondition();
condition.ConditionOrderId = 0;
condition.ConditionOrderPartiallyMatched = true;
condition.ConditionOrderSide = mainOrder.Direction == Sides.Buy ? Sides.Sell : Sides.Buy;
condition.ConditionOrderUseMatchedBalance = false;
condition.IsMarketStopLimit = false; // цена по рынку сл
condition.IsMarketTakeProfit = false; // цена по рынку тп
condition.LinkedOrderCancel = false;
condition.LinkedOrderPrice = 0;
//condition.ActiveTime = null; // время до снятия ордера
//condition.ConditionOrderId = mainOrder.Id;
//condition.ConditionOrderPartiallyMatched = false;
//condition.ConditionOrderUseMatchedBalance = true;
//condition.IsMarketStopLimit = true; // цена по рынку сл
//condition.IsMarketTakeProfit = true; // цена по рынку тп
//condition.LinkedOrderCancel = false;
//condition.LinkedOrderPrice = 0;

Unit Slippage = GetPriceStep(mainOrder.Security) * 100;
condition.Offset = new Unit(0, UnitTypes.Percent); // отступ от макса
condition.Spread = new Unit(0, UnitTypes.Percent); // отступ от макса
condition.StopPrice = Math.Round(price * (100 + sl) / 100, mainOrder.Security.Decimals.GetValueOrDefault()); // sl
condition.StopLimitPrice = Math.Round(price * (100 + tp) / 100, mainOrder.Security.Decimals.GetValueOrDefault());

condition.Type = QuikOrderConditionTypes.TakeProfitStopLimit;
condition.StopPriceCondition = QuikStopPriceConditions.MoreOrEqual;



Order OrderSLTP = new Order
{
Security = mainOrder.Security,
Portfolio = Portfolio, // mainOrder.Portfolio
Type = OrderTypes.Conditional,
Condition = condition,
Volume = mainOrder.Volume,
Price = 0,
Direction = mainOrder.Direction == Sides.Buy ? Sides.Sell : Sides.Buy,
Comment = mainOrder.Comment,
};

OrderSLTP.ExtensionInfo = new Dictionary<string, Object>();
foreach (var pair in mainOrder.ExtensionInfo)
{
OrderSLTP.ExtensionInfo.Add(pair.Key, pair.Value);
}

return OrderSLTP;
}


Добрый день, в последнем релизе коннектора ошибка с выставлением стоп-заявки устранена.
Работоспособность проверена на примере Терминала в связке с Квик.
Thanks:

Sumrak

Avatar
Date: 6/9/2021
Reply


Спасибо большое, позже обновлюсь и буду пробовать
Topic starter
Thanks:


Attach files by dragging & dropping, , or pasting from the clipboard.

loading
clippy