Download MetaTrader 5

History data and error 4066

To add comments, please log in or register
duzers
22
duzers  

Hello,

Is there any safe method to check if history is current after error 4066?.

THX!!

whroeder1
16099
whroeder1  
ArrayCopySeries - MQL4 Documentation states
If data are copied from another chart with different symbol and/or timeframe, it is possible that the necessary data will lack. In this case, error ERR_HISTORY_WILL_UPDATED (4066 - requested history data under updating) will be placed into the last_error variable, and there will be necessary to retry copying after a certain period of time.
And shows an example.
So I wrote this.
/** Starts and waits for a download of chart history.
 * In Technical Indicator Functions - MQL4 Documentation][TIF3] it states:
 * > If data (symbol name and/or timeframe differ from the current ones) are
 * > requested from another chart, the situation is possible that the
 * > corresponding chart was not opened in the client terminal and the
 * > necessary data must be requested from the server. In this case, error
 * > `ERR_HISTORY_WILL_UPDATED` (4066 - the requested history data are under
 * > updating) will be placed in the last_error variable, and and there will
 * > be necessary to retry \[the operation] after a certain period of time.
 *
 * The [ArrayCopySeries][ACS] example tests array[0] against server time.
 * [ACS]: https://docs.mql4.com/array/arraycopyseries
 * [TIF3]: https://docs.mql4.com/en/indicators
 *
 * Note: you _only_ get 4066 once. Subsequent calls (\::ArrayCopyRates and
 * apparently \::ArrayCopySeries) silently succeed but the data is bogus
 * until the download completes. These calls should have been synchronous,
 * but then they couldn't be used in indicators.
 */
bool  download_history(
         ENUM_TIMEFRAMES   period=PERIOD_CURRENT,  ///< The standard timeframe.
         string            msg=__FUNSIG__          ///< Debug.
         SYMBOL            symbol=THIS_SYMBOL      /**< The symbol required.*/){
   if(symbol == THIS_SYMBOL)     symbol = _Symbol;
   if(period == PERIOD_CURRENT)  period = _Period;
   ResetLastError();
   datetime other = iTime(symbol, period, 0);
   if(_LastError == 0)  return true;
   if(_LastError != ERR_HISTORY_WILL_UPDATED){
      AssertFailure(StringFormat("%s: iTime(%s,%i) Failed: %i",
                                 msg, symbol, period, _LastError) );
      return false;
   }
   datetime today = DateOfDay();
   for(int i = 0;i < 15; i++){
      Sleep(1000);
      ResetLastError();
      other = iTime(symbol, period, 0);
      if(today == DateOfDay(other)){   RefreshRates();   return true;   }
   }
   AssertFailure(StringFormat("%s: iTime(%s,%i) Failed: %i (15 secs)",
                              msg, symbol, period, _LastError) );
   return false;
}
whroeder1
16099
whroeder1  
#define HR2400 PERIOD_D1 * 60    // 86400 = 24 * 3600
int      TimeOfDay(datetime when=0){      if(when == 0)  when = TimeCurrent();
                                          return( when % HR2400 );            }
datetime DateOfDay(datetime when=0){      if(when == 0)  when = TimeCurrent();
                                          return( when - TimeOfDay(when) );   }
//datetime Tomorrow( datetime when=0){      if(when == 0)  when = TimeCurrent();
//                                          return(DateOfDay(when) + HR2400);   }
//datetime Yesterday(datetime when=0){      if(when == 0)  when = TimeCurrent();
//   int iD1 = iBarShift(NULL, PERIOD_D1, DateOfDay(when) - 1);
//                                       return( iTime(NULL, PERIOD_D1, iD1) ); }
Alain Verleyen
Moderator
33491
Alain Verleyen  
whroeder1:
ArrayCopySeries - MQL4 Documentation states And shows an example.
So I wrote this.
Sleep() is not executed in indicators.
honest_knave
Moderator
2319
honest_knave  

I tend to use OnTimer() with a simple flag in OnTick() / OnCalculate() to be compatible with both.

Although I believe OnTimer() wasn't an option back in 2015 

Ex Ovo Omnia
3357
Ex Ovo Omnia  
honest_knave:

I tend to use OnTimer() with a simple flag in OnTick() / OnCalculate() to be compatible with both.

Although I believe OnTimer() wasn't an option back in 2015 

OnTimer was available since 2014.
honest_knave
Moderator
2319
honest_knave  
Ovo Cz:
OnTimer was available since 2014.

I stand corrected! 

I guess it was a build 600 thing.

whroeder1
16099
whroeder1  
Alain Verleyen: Sleep() is not executed in indicators.
True. In another thread I posted a variation of download_history that didn't have the internal wait, but immediately returned false. Thus the calls would be:
In indicators
int OnCalculate(...){
   if(!download_history(...) return prev_calculated;
   :
Return and wait for the next tick and retry.
In EAs
void OnTick(){
   while(!download_history(...){ Sleep(1000); RefreshRates(); }
   :
Alain Verleyen
Moderator
33491
Alain Verleyen  
whroeder1:
True. In another thread I posted a variation of download_history that didn't have the internal wait, but immediately returned false. Thus the calls would be:
In indicators
int OnCalculate(...){
   if(!download_history(...) return prev_calculated;
   :
Return and wait for the next tick and retry.
In EAs
void OnTick(){
   while(!download_history(...){ Sleep(1000); RefreshRates(); }
   :
Yes. I didn't notice it was an old post.
To add comments, please log in or register