/// <summary> /// Fetches the data for pre-configured languages and merges it to internally used dictionaries. First time the method is invoked it fetches the data only for missing languages. /// On subsequent calls data for all configured languages is fetched and dictionary are cleared before fetched data is added / merged /// </summary> /// <param name="sender">A <see cref="ITimer"/> invoking the method</param> /// <param name="e">The <see cref="EventArgs"/> providing additional information about the event which invoked the method</param> private async void OnTimerElapsed(object sender, EventArgs e) { if (!await _semaphore.WaitAsyncSafe().ConfigureAwait(false)) { return; } IList <CultureInfo> cultureInfos = new List <CultureInfo>(); try { var missingLanguages = _wasDataAutoFetched ? _requiredCultures : _requiredCultures.Where(c => !FetchedCultures.Any()).ToList(); cultureInfos = missingLanguages as IList <CultureInfo> ?? missingLanguages.ToList(); if (cultureInfos.Any()) { await FetchAndMergeAll(cultureInfos, _wasDataAutoFetched).ConfigureAwait(false); ExecutionLog.Info($"Sport data for languages [{string.Join(",", cultureInfos)}] successfully fetched and merged."); _wasDataAutoFetched = true; } } catch (FeedSdkException ex) { ExecutionLog.Warn($"An exception occurred while attempting to fetch sport data for: {string.Join(",", cultureInfos)}. Exception was: {ex}"); } catch (ObjectDisposedException) { ExecutionLog.Warn($"An exception occurred while attempting to fetch sport data for: {string.Join(",", cultureInfos)}. DataProvider was already disposed."); } catch (TaskCanceledException) { ExecutionLog.Warn($"An exception occurred while attempting to fetch sport data for: {string.Join(",", cultureInfos)}. Task canceled. DataProvider was already disposed."); } catch (Exception ex) { ExecutionLog.Warn($"An exception occurred while attempting to fetch sport data for: {string.Join(",", cultureInfos)}. Exception: {ex}"); } finally { _semaphore.ReleaseSafe(); } }