Помогите исправить ошибку OrderModify error 1 и OrderSend error 131!

 

Всем привет!

Советник по принципу Мартингейла, вход по сигналам индикатора CCI, eurusd, M5. Результат теста не плохой! Но..

После теста советника выдает ошибку: OrderModify error 1 и OrderSend error 131. Лот используется 1.0

Для решения error 1 предлагается корректировать Отправка запроса на модификацию уровней без фактического их изменения, а для error 131проверку корректности объема.

Ничего не получается! Помогите наглядно поправить код советника или правильно вписать функцию отправки запроса на модификацию уровней и проверку корректности объема. Спасибо! 

//нннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннн
#property copyright ""
#property link      ""
#include <stderror.mqh>
#include <stdlib.mqh>
//ннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннн
extern string   MM_set = "Money Managment settings";
extern double Lot = 0.01;          // разер лота для начала торгов
extern int lotdecimal = 2;          // сколько знаков после запятой в лоте рассчитывать 0 - нормальные лоты (1), 1 - минилоты (0.1), 2 - микро (0.01)
extern double ExpoLot = 1.2;   // на сколько умножать лот при выставлении следующего колена. пример: первый лот 0.1, серия: 0.16, 0.26, 0.43 ...
bool    DynamicPips                   = true;
int     DefaultPips=0;
extern int Depth = 12;
extern int Grid = 2;
extern double slip = 2.0;           // на сколько может отличаться цена в случае если ДЦ запросит реквоты (в последний момент немного поменяет цену)
extern double TakeProfit = 10.0;    // по достижении скольких пунктов прибыли закрывать сделку
extern double Drop = 1500;
int PipStep=0;
//нннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннн
extern int MaxTrades = 10;                 // максимально количество одновременно открытых ордеров
extern bool UseEquityStop = FALSE;
extern double TotalEquityRisk = 20.0;
extern int MagicNumber = 2222;      // волшебное число (помогает советнику отличить свои ставки от чужих)
//extern bool UseTrailingStop = FALSE;
bool UseTimeOut = FALSE;            // использовать таймаут (закрывать сделки если они "висят" слишком долго)
double MaxTradeOpenHours = 48.0;    // время таймаута сделок в часах (через сколько закрывать зависшие сделки)
extern string   CCI_set = "CCI settings";
extern int CCI_Period = 21;
extern int CCI_Price = 2;
extern double CCI_Max = 300;
extern double CCI_Min = -300;
//нннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннн
double PriceTarget, StartEquity, BuyTarget, SellTarget;
double AveragePrice, SellLimit, BuyLimit;
double LastBuyPrice, LastSellPrice, Spread;
bool flag;
string EAName="CCI Martin";
int timeprev = 0, expiration;
int NumOfTrades = 0;
double iLots;
int cnt = 0, total;
double Stopper = 0.0;
bool TradeNow = FALSE, LongTrade = FALSE, ShortTrade = FALSE;
int ticket,Error;
bool  NewOrdersPlaced = FALSE, NeedModifyOrder = False;
double AccountEquityHighAmt, PrevEquity;
//нннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннн
int init() {
   Spread = MarketInfo(Symbol(), MODE_SPREAD) * Point;
   return (0);
}

int deinit() {
   return (0);
}
//нннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннн
int start()
{
  double PrevCl;
  double CurrCl;
//*защита от резкого движения*//
  if ((iCCI(NULL,30,55,0,0)>Drop && ShortTrade)||(iCCI(NULL,30,55,0,0)<(-Drop) && LongTrade))
  {
    CloseThisSymbolAll();
    Print("Closed All due to TimeOut");
  }


  if (timeprev == Time[0]) return(0);   //new bar apear check
  timeprev = Time[0];

  if (DynamicPips)  
  {
    double hival=High[iHighest(NULL,0,MODE_HIGH,Depth,1)];    // calculate highest and lowest price from last bar to 24 bars ago
    double loval=Low[iLowest(NULL,0,MODE_LOW,Depth,1)];       // chart used for symbol and time period
   PipStep=NormalizeDouble((hival-loval)/Grid/Point,0);         // calculate pips for spread between orders
      Print("PipStep = ",PipStep);

  }
  double CurrentPairProfit = CalculateProfit();  
  if (UseEquityStop)
    if (CurrentPairProfit < 0.0 && MathAbs(CurrentPairProfit) > TotalEquityRisk / 100.0 * AccountEquityHigh())
    {
      CloseThisSymbolAll();
      Print("Closed All due to Stop Out");
      NewOrdersPlaced = FALSE;
    }
  
    total = CountOfOrders();    //calculating open orders function
  
  if (total > 0 && total <= MaxTrades)  
  {
    Print("total > 0");
    for (int i = 0; i < OrdersTotal(); i++)
      if(OrderSelect( i, SELECT_BY_POS, MODE_TRADES))
        if (OrderSymbol() == Symbol() && OrderMagicNumber() == MagicNumber)
        {
          switch(OrderType())
          {
            case OP_BUY:
              LongTrade = TRUE;
              ShortTrade = FALSE;
              break;
            case OP_SELL:
              LongTrade = FALSE;
              ShortTrade = TRUE;
              break;
          }
          break;
        }
    LastBuyPrice = FindLastBuyPrice();
    LastSellPrice = FindLastSellPrice();
    if (LongTrade && LastBuyPrice - Ask >= PipStep * Point) TradeNow = TRUE;
    if (ShortTrade && Bid - LastSellPrice >= PipStep * Point) TradeNow = TRUE;
  
  }
  else
  {
    Print("total = 0");
    ShortTrade = FALSE;
    LongTrade = FALSE;
    TradeNow = TRUE;
    StartEquity = AccountEquity();
  }
  if(total > 0)
    if(TradeNow)
    {
      iLots = NormalizeDouble(Lot * MathPow(ExpoLot, total), lotdecimal);
      if (ShortTrade)
      {
        ticket = SendMarketOrder(OP_SELL, iLots, 0, 0, MagicNumber, EAName + "-" + NumOfTrades + "-" + PipStep);
      }
      if (LongTrade)
      {
        ticket = SendMarketOrder(OP_BUY, iLots, 0, 0, MagicNumber, EAName + "-" + NumOfTrades + "-" + PipStep);
      }
      if(ticket > 0)
      {
        TradeNow = FALSE;
        NewOrdersPlaced = TRUE;
        NeedModifyOrder = TRUE;
      }
      else
        return(0);
    }

  if (TradeNow && total < 1 )  {
    Print("Open first order");
    ticket = 0;
     PrevCl = iClose(Symbol(), 0, 2);
     CurrCl = iClose(Symbol(), 0, 1);
          
    if (PrevCl > CurrCl)
    {
      Print("Achieved condition SELL");
      if (iCCI(Symbol(), Period(), CCI_Period, CCI_Price, 1) <= CCI_Min)
      {
        Print("successful check");
        ticket = SendMarketOrder(OP_SELL, Lot, TakeProfit, 0, MagicNumber, EAName + "-" + total);
      }
    }
    if (PrevCl < CurrCl)
    {
      Print("Achieved condition BUY");
      if (iCCI(Symbol(), Period(), CCI_Period, CCI_Price, 1) >= CCI_Max)
      {
        Print("successful check");
        ticket = SendMarketOrder(OP_BUY, Lot, TakeProfit, 0, MagicNumber, EAName + "-" + total);
      }
    }
    if(ticket > 0)
    {
      TradeNow = FALSE;
      NewOrdersPlaced = TRUE;
      NeedModifyOrder = False;
    }
    else
      return(0);
  }
  
  AveragePrice = CalculateAveragePrice();
  
  if (NewOrdersPlaced)
  {

    if(ShortTrade)
    {
      PriceTarget = AveragePrice - TakeProfit * Point;
      NeedModifyOrder = TRUE;
    }
    if(LongTrade)
    {
      PriceTarget = AveragePrice + TakeProfit * Point;
      NeedModifyOrder = TRUE;
    }
  }
  
  if (NewOrdersPlaced)
    if (NeedModifyOrder)
    {
      Print("Modify all orders in the market");
      for (int i1 = 0; i1 < OrdersTotal(); i1++)
        if(OrderSelect(i1, SELECT_BY_POS, MODE_TRADES))
          if (OrderSymbol() == Symbol() && OrderMagicNumber() == MagicNumber)
            ModifyOrder(PriceTarget);
      NewOrdersPlaced = FALSE;
    }
  return (0);
}
//ннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннн
int CountOfOrders()
{
  int count = 0;
  for (int i = 0; i < OrdersTotal(); i++)
    if (OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
      if ((OrderSymbol() == Symbol()) && (OrderMagicNumber() == MagicNumber))
        if ((OrderType() == OP_SELL) || (OrderType() == OP_BUY))
          count++;
  return(count);
}

//нннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннн

void CloseThisSymbolAll() {
   for (int trade = OrdersTotal() - 1; trade >= 0; trade--) {
      if(!OrderSelect(trade, SELECT_BY_POS, MODE_TRADES)) Print("error!");
      if (OrderSymbol() == Symbol()) {
         if (OrderSymbol() == Symbol() && OrderMagicNumber() == MagicNumber) {
            if (OrderType() == OP_BUY) int ticket1=OrderClose(OrderTicket(), OrderLots(), Bid, slip, Blue);
            if (OrderType() == OP_SELL) ticket1=OrderClose(OrderTicket(), OrderLots(), Ask, slip, Red);
         }
         Sleep(1000);
      }
   }
}
//=========================================================================
int SendMarketOrder(int Type, double Lot1, int TP, int SL, int Magic, string Cmnt)
{
  double Price, Take, Stop;
  int Ticket, Slippage, Color, Err;
  bool Delay = False;
  Print("SendMarketOrder function");
  while(!IsStopped())
  {
    /*if(!IsExpertEnabled())
    {
      Error = ERR_TRADE_DISABLED;
      Print("EA trading is forbidden!");
      return(-1);
    }
    Print("EA trading is allowed");*/

    if(!IsConnected())
    {
      Error = ERR_NO_CONNECTION;
      Print("Communication is absent!");
      return(-1);
    }
    Print("Communication with the server is installed");
    if(IsTradeContextBusy())
    {
      Print("The trade stream is occupied!");
      Print("waiting 3 sec...");
      Sleep(3000);
      Delay = True;
      continue;
    }
    Print("The trade stream is free");
    if(Delay)
    {
      Print("updating quotes");
      RefreshRates();
      Delay = False;
    }
    else
    {
      Print("Delays weren't");
    }
    switch(Type)
    {
      case OP_BUY:
        Print("initialize parameters for BUY-order");
        Price = NormalizeDouble( Ask, Digits);
        Take = IIFd(TP == 0, 0, NormalizeDouble( Ask + TP * Point, Digits));
        Stop = IIFd(SL == 0, 0, NormalizeDouble( Ask - SL * Point, Digits));
        Color = Blue;
        break;
      case OP_SELL:
        Print("iinitialize parameters for SELL-order");
        Price = NormalizeDouble( Bid, Digits);
        Take = IIFd(TP == 0, 0, NormalizeDouble( Bid - TP * Point, Digits));
        Stop = IIFd(SL == 0, 0, NormalizeDouble( Bid + SL * Point, Digits));
        Color = Red;
        break;
      default:
        Print("order type doesn't conform to requirements.");
        return(-1);
    }
    Slippage = MarketInfo(Symbol(), MODE_SPREAD);
    Print("Slippage = ",Slippage);
    if(IsTradeAllowed())
    {
      Print("Trading is allowed, sending order...");
      Ticket = OrderSend(Symbol(), Type, Lot1, Price, Slippage, Stop, Take, Cmnt, Magic, 0, Color);
      if(Ticket < 0)
      {
        Err = GetLastError();
        if (Err == 4   || /* SERVER_BUSY */
            //Err == 130 || /* INVALID_STOPS */
            Err == 135 || /* PRICE_CHANGED */
            Err == 137 || /* BROKER_BUSY */
            Err == 138 || /* REQUOTE */
            Err == 146 || /* TRADE_CONTEXT_BUSY */
            Err == 136 )  /* OFF_QUOTES */
        {
          Print("error") ;
          Print("waitng 3 sec...");
          Sleep(3000);
          Delay = True;
          continue;
        }
        else
        {
          Print("Critical error");
          Error = Err;
          break;
        }
      }
      break;
    }
    else
    {
      Print("EA trading is forbidden or trade stream is occupied!");
      Print("waitng 3 sec...");
      Sleep(3000);
      Delay = True;
      continue;
    }
  }
  Print("The order has been sent successfully. Тicket = ",Ticket);
  return(Ticket);
}
//==================================================================
double IIFd(bool condition, double ifTrue, double ifFalse)
{
  if (condition) return(ifTrue); else return(ifFalse);
}
//нннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннн
double CalculateProfit()
{
  double Profit = 0;
  for (int i = 0; i < OrdersTotal(); i++)
    if(OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
      if ((OrderSymbol() == Symbol()) && (OrderMagicNumber() == MagicNumber))
        if ((OrderType() == OP_BUY) || (OrderType() == OP_SELL))
          Profit += OrderProfit();
  return (Profit);
}
//нннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннн

double AccountEquityHigh() {
   if (CountOfOrders() == 0) AccountEquityHighAmt = AccountEquity();
   if (AccountEquityHighAmt < PrevEquity) AccountEquityHighAmt = PrevEquity;
   else AccountEquityHighAmt = AccountEquity();
   PrevEquity = AccountEquity();
   return (AccountEquityHighAmt);
}
//нннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннн

double FindLastBuyPrice() {
   double oldorderopenprice;
   int oldticketnumber;
   double unused = 0;
   int ticketnumber = 0;
   for (cnt = OrdersTotal() - 1; cnt >= 0; cnt--) {
      if(!OrderSelect(cnt, SELECT_BY_POS, MODE_TRADES)) Print("error!");
      if (OrderSymbol() != Symbol() || OrderMagicNumber() != MagicNumber) continue;
      if (OrderSymbol() == Symbol() && OrderMagicNumber() == MagicNumber && OrderType() == OP_BUY) {
         oldticketnumber = OrderTicket();
         if (oldticketnumber > ticketnumber) {
            oldorderopenprice = OrderOpenPrice();
            unused = oldorderopenprice;
            ticketnumber = oldticketnumber;
         }
      }
   }
   return (oldorderopenprice);
}

double FindLastSellPrice() {
   double oldorderopenprice;
   int oldticketnumber;
   double unused = 0;
   int ticketnumber = 0;
   for (cnt = OrdersTotal() - 1; cnt >= 0; cnt--) {
      if(!OrderSelect(cnt, SELECT_BY_POS, MODE_TRADES)) Print("error");
      if (OrderSymbol() != Symbol() || OrderMagicNumber() != MagicNumber) continue;
      if (OrderSymbol() == Symbol() && OrderMagicNumber() == MagicNumber && OrderType() == OP_SELL) {
         oldticketnumber = OrderTicket();
         if (oldticketnumber > ticketnumber) {
            oldorderopenprice = OrderOpenPrice();
            unused = oldorderopenprice;
            ticketnumber = oldticketnumber;
         }
      }
   }
   return (oldorderopenprice);
}
//ннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннннн
double CalculateAveragePrice()
{
  AveragePrice = 0;
  double Count = 0;
  for (int i = 0; i < OrdersTotal(); i++)
    if(OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
      if (OrderSymbol() == Symbol() && OrderMagicNumber() == MagicNumber)
        if (OrderType() == OP_BUY || OrderType() == OP_SELL)
        {
           AveragePrice += OrderOpenPrice() * OrderLots();
           Count += OrderLots();
        }
  if(AveragePrice > 0 && Count > 0)
    return( NormalizeDouble(AveragePrice / Count, Digits));
  else
    return(0);
}


bool ModifyOrder( double takeprofit)
{
  while(!IsStopped())
  {
    Print("ModifyOrder function");
    if(IsTradeContextBusy())
    {
      Print("The trade stream is occupied!");
      Sleep(3000);
      continue;
    }
    Print("The trade stream is free");
    if(!IsTradeAllowed())
    {
      Print("EA trading is forbidden or trade stream is occupied!");
      Sleep(3000);
      continue;
    }
    Print("EA trading is allowed, order modify #",OrderTicket());
    if(!OrderModify(OrderTicket(), OrderOpenPrice(), 0, NormalizeDouble(takeprofit,Digits), 0, Yellow))
    {
      Print("Unable to modify order");
      int Err = GetLastError();
      Print("error");
      break;
      //Sleep(1000);
      //continue;
    }
    else
    {
      Print("Order modification completed successfully");
      break;
    }
  }
  return(True);
}
Коды возврата торгового сервера - Коды ошибок и предупреждений - Стандартные константы, перечисления и структуры - Справочник MQL4
Коды возврата торгового сервера - Коды ошибок и предупреждений - Стандартные константы, перечисления и структуры - Справочник MQL4
  • docs.mql4.com
Коды возврата торгового сервера - Коды ошибок и предупреждений - Стандартные константы, перечисления и структуры - Справочник MQL4
Файлы:
CCI-Martin.mq4  33 kb
 
Roman Rymar:

Всем привет!

Советник по принципу Мартингейла, вход по сигналам индикатора CCI, eurusd, M5. Результат теста не плохой! Но..

После теста советника выдает ошибку: OrderModify error 1! Для решения предлагается корректировать Отправка запроса на модификацию уровней без фактического их изменения.

Ничего не получается! Помогите поправить код советника или правильно вписать функцию отправки запроса на модификацию уровней. Спасибо!

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

Иными словами: если хотите, например, подтянуть стоп ордера Buy, то: если стоп ордера Buy меньше нового значения стопа, то OrderMofify()

 
Artyom Trishkin:

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

Иными словами: если хотите, например, подтянуть стоп ордера Buy, то: если стоп ордера Buy меньше нового значения стопа, то OrderMofify()

Нет стопов. 
 
Roman Rymar:
Нет стопов. 

А вы видели в моём предложении ",например" ? А то, что перед второй частью, где есть "например", написано, вы уже не читаете? Значит так хотите помощь получить.

Какая разница что вы модифицируете?

 

А для понимания причины ошибки 131, открываем справку в редакторе, вводим в поиск "Коды ошибок" и читаем в разделе "Коды возврата торгового сервера":

131

ERR_INVALID_TRADE_VOLUME

Неправильный объем


После этого идём в функцию, в которой рассчитывается объём, и проверяем: "а чего мы там наваяли"
 
Artyom Trishkin:

А вы видели в моём предложении ",например" ? А то, что перед второй частью, где есть "например", написано, вы уже не читаете? Значит так хотите помощь получить.

Какая разница что вы модифицируете?

не хотел обидеть! спасибо, буду пробовать!
 
Roman Rymar:
не хотел обидеть! спасибо, буду пробовать!

Вы меня ничем не обидели.

Пожалуйста.