Reputation: 90
I'm trying to place an automated order in MetaTrader 4 using an EA on a Demo account. The order does not get placed, but also returns an error code that means no error given. What am I doing wrong here? It doesn't work. No order is ever generated, yet it says that there is no error given. How do I figure out what is wrong?
I have enabled both auto trading and 1 click trading. I also run the EA by applying it to the chart window for EURUSD in MT4.
Below is the function where the problem lies, output and supporting info:
Code
void PlaceOrder(void)
{
MqlTick last_tick;
int retval = 0;
WriteLogFile(log_filehandle, "Placing Test Order", "PlaceOrder:>");
SymbolInfoTick(Symbol(), last_tick);
//##########################
//# Testing Order Commands #
//##########################
//#####################################################################
//# WriteLogFile is a function that prints slightly formatted text to #
//# a log file. Its output is shown below #
//#####################################################################
WriteLogFile(log_filehandle, "Symbol="+ Symbol(),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Low day price="+ MarketInfo(Symbol(), MODE_LOW),"PlaceOrder:>");
WriteLogFile(log_filehandle, "High day price="+ MarketInfo(Symbol(), MODE_HIGH),"PlaceOrder:>");
WriteLogFile(log_filehandle, "The last incoming tick time="+ (MarketInfo(Symbol(), MODE_TIME)),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Last incoming bid price="+ MarketInfo(Symbol(), MODE_BID),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Last incoming ask price="+ MarketInfo(Symbol(), MODE_ASK),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Point size in the quote currency="+ MarketInfo(Symbol(), MODE_POINT),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Digits after decimal point="+ MarketInfo(Symbol(), MODE_DIGITS),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Spread value in points="+ MarketInfo(Symbol(), MODE_SPREAD),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Stop level in points="+ MarketInfo(Symbol(), MODE_STOPLEVEL),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Lot size in the base currency="+ MarketInfo(Symbol(), MODE_LOTSIZE),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Tick value in the deposit currency="+ MarketInfo(Symbol(), MODE_TICKVALUE),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Tick size in points="+ MarketInfo(Symbol(), MODE_TICKSIZE),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Swap of the buy order="+ MarketInfo(Symbol(), MODE_SWAPLONG),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Swap of the sell order="+ MarketInfo(Symbol(), MODE_SWAPSHORT),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Market starting date (for futures)="+ MarketInfo(Symbol(), MODE_STARTING),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Market expiration date (for futures)="+ MarketInfo(Symbol(), MODE_EXPIRATION),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Trade is allowed for the symbol="+ MarketInfo(Symbol(), MODE_TRADEALLOWED),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Minimum permitted amount of a lot="+ MarketInfo(Symbol(), MODE_MINLOT),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Step for changing lots="+ MarketInfo(Symbol(), MODE_LOTSTEP),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Maximum permitted amount of a lot="+ MarketInfo(Symbol(), MODE_MAXLOT),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Swap calculation method="+ MarketInfo(Symbol(), MODE_SWAPTYPE),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Profit calculation mode="+ MarketInfo(Symbol(), MODE_PROFITCALCMODE),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Margin calculation mode="+ MarketInfo(Symbol(), MODE_MARGINCALCMODE),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Initial margin requirements for 1 lot="+ MarketInfo(Symbol(), MODE_MARGININIT),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Margin to maintain open orders calculated for 1 lot="+ MarketInfo(Symbol(), MODE_MARGINMAINTENANCE),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Hedged margin calculated for 1 lot="+ MarketInfo(Symbol(), MODE_MARGINHEDGED),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Free margin required to open 1 lot for buying="+ MarketInfo(Symbol(), MODE_MARGINREQUIRED),"PlaceOrder:>");
WriteLogFile(log_filehandle, "Order freeze level in points="+ MarketInfo(Symbol(), MODE_FREEZELEVEL),"PlaceOrder:>");
//--- get minimum stop level
double minstoplevel = MarketInfo(Symbol(), MODE_STOPLEVEL);
WriteLogFile(log_filehandle, "Minimum Stop Level=" + DoubleToString(minstoplevel,Digits) + " points", "PlaceOrder:>");
double price = Ask;
//--- calculated SL and TP prices must be normalized
//double stoploss = NormalizeDouble(Bid - minstoplevel * Point, Digits);
//double takeprofit = NormalizeDouble(Bid + minstoplevel * Point, Digits);
double stoploss = NormalizeDouble(Bid - 30 * Point, Digits);
double takeprofit = NormalizeDouble(Bid + 30 * Point, Digits);
retval = OrderSend(
"EURUSD", //symbol
OP_BUY, //operation
0.1, //volume
price, //price
3, //slippage
stoploss, //Stop loss
takeprofit, //Take Profit
NULL, //comment
0, //magic number
0, //pending order expiration
clrNONE //color
);
WriteLogFile(log_filehandle, "\nEURUSD,\t\t//symbol\nOP_BUY,\t\t//operation\n0.1,\t\t//volume\n" + DoubleToString(price, Digits) + ",\t//price\n3,\t\t//slippage\n" + DoubleToString(stoploss,Digits) + ",\t//stop loss\n" + DoubleToString(takeprofit, Digits) + ",\t//Take profit\nNULL,\t\t//Comment\n0,\t\t//magic number\n0,\t\t//pending order expiration\nclrNONE\t\t//color\n", "PlaceOrder:>");
WriteLogFile(log_filehandle, "retval:" + IntegerToString(retval,0,'x'), "PlaceOrder:>");
WriteLogFile(log_filehandle, "Last Error:" + IntegerToString(GetLastError(),0,'x'), "PlaceOrder:>");
}
Output Generated in Log File
PlaceOrder:> Placing Test Order
PlaceOrder:> Symbol=EURUSD
PlaceOrder:> Low day price=1.11434
PlaceOrder:> High day price=1.1153
PlaceOrder:> The last incoming tick time=1578446266
PlaceOrder:> Last incoming bid price=1.11494
PlaceOrder:> Last incoming ask price=1.11506
PlaceOrder:> Point size in the quote currency=1e-05
PlaceOrder:> Digits after decimal point=5
PlaceOrder:> Spread value in points=12
PlaceOrder:> Stop level in points=0
PlaceOrder:> Lot size in the base currency=100000
PlaceOrder:> Tick value in the deposit currency=1
PlaceOrder:> Tick size in points=1e-05
PlaceOrder:> Swap of the buy order=-15.6
PlaceOrder:> Swap of the sell order=3.36
PlaceOrder:> Market starting date (for futures)=0
PlaceOrder:> Market expiration date (for futures)=0
PlaceOrder:> Trade is allowed for the symbol=1
PlaceOrder:> Minimum permitted amount of a lot=0.01
PlaceOrder:> Step for changing lots=0.01
PlaceOrder:> Maximum permitted amount of a lot=1000
PlaceOrder:> Swap calculation method=0
PlaceOrder:> Profit calculation mode=0
PlaceOrder:> Margin calculation mode=0
PlaceOrder:> Initial margin requirements for 1 lot=0
PlaceOrder:> Margin to maintain open orders calculated for 1 lot=0
PlaceOrder:> Hedged margin calculated for 1 lot=25000
PlaceOrder:> Free margin required to open 1 lot for buying=1115.06
PlaceOrder:> Order freeze level in points=0
PlaceOrder:> Minimum Stop Level=0.00000 points
PlaceOrder:>
EURUSD, //symbol
OP_BUY, //operation
0.1, //volume
1.11506, //price
3, //slippage
1.11464, //stop loss
1.11524, //Take profit
NULL, //Comment
0, //magic number
0, //pending order expiration
clrNONE //color
PlaceOrder:> retval:-1
PlaceOrder:> Last Error:0
According to the MT4 Manual the error codes have these definitions:
0 ERR_NO_ERROR No error returned
1 ERR_NO_RESULT No error returned, but the result is unknown
2 ERR_COMMON_ERROR Common error
3 ERR_INVALID_TRADE_PARAMETERS Invalid trade parameters
4 ERR_SERVER_BUSY Trade server is busy
5 ERR_OLD_VERSION Old version of the client terminal
6 ERR_NO_CONNECTION No connection with trade server
7 ERR_NOT_ENOUGH_RIGHTS Not enough rights
8 ERR_TOO_FREQUENT_REQUESTS Too frequent requests
9 ERR_MALFUNCTIONAL_TRADE Malfunctional trade operation
64 ERR_ACCOUNT_DISABLED Account disabled
65 ERR_INVALID_ACCOUNT Invalid account
128 ERR_TRADE_TIMEOUT Trade timeout
129 ERR_INVALID_PRICE Invalid price
130 ERR_INVALID_STOPS Invalid stops
131 ERR_INVALID_TRADE_VOLUME Invalid trade volume
132 ERR_MARKET_CLOSED Market is closed
133 ERR_TRADE_DISABLED Trade is disabled
134 ERR_NOT_ENOUGH_MONEY Not enough money
135 ERR_PRICE_CHANGED Price changed
136 ERR_OFF_QUOTES Off quotes
137 ERR_BROKER_BUSY Broker is busy
138 ERR_REQUOTE Requote
139 ERR_ORDER_LOCKED Order is locked
140 ERR_LONG_POSITIONS_ONLY_ALLOWED Buy orders only allowed
141 ERR_TOO_MANY_REQUESTS Too many requests
145 ERR_TRADE_MODIFY_DENIED Modification denied because order is too close to market
146 ERR_TRADE_CONTEXT_BUSY Trade context is busy
147 ERR_TRADE_EXPIRATION_DENIED Expirations are denied by broker
148 ERR_TRADE_TOO_MANY_ORDERS The amount of open and pending orders has reached the limit set by the broker
149 ERR_TRADE_HEDGE_PROHIBITED An attempt to open an order opposite to the existing one when hedging is disabled
150 ERR_TRADE_PROHIBITED_BY_FIFO An attempt to close an order contravening the FIFO rule
Upvotes: 1
Views: 1962
Reputation: 90
At first I did not notice because I did not have the journal tab open in MT4. I instead had the Trade tab open because I was watching to see if the trade would come through.
In the Journal I saw this error:
2020.01.07 23:41:38.725 '1182115': order #127275200 buy 0.10 EURUSD at 1.11486 closed due stop-loss at price 1.11476
I am assuming that the stop-loss price is probably too close to the buy price. I'll check it out and update my answer to be more complete.
On further examination, this kind of makes sense. I don't know why the OrderSend command did not properly set the error delivery mechanism. Clearly it knew that there was a problem because it returned -1 instead of an order number, then failed to set any useful error code for the error system.
it placed a Buy order for EURUSD at a price of 1.11486. The stop loss was set to 1.11476. The order was generated. It's order number was 127275200. However because the stop loss was only 1 pip lower than the original price it was instantly closed because the stop loss was triggered.
I have and can see order #127275200 in my records in MT4. It automatically closed out at the stop loss price of 1.11476.
A. Why did OrderSend return -1 instead of order number 127275200? The order was real. It did exist for a small period of time.
B. Why did OrderSend fail to deliver any useful error message to the error delivery system?
Upvotes: 1