/// <summary> /// Get a table of events for the day from the cache or from the server /// </summary> /// <remarks>The returned table after loading is not changed by an instance of this class, /// thus, reading its data is thread safe. /// The method always returns a non-null object.</remarks> public EventTableLight GetEventTable(DateTime date) { try { // getting event table from cache date = date.Date; var utcNowDT = DateTime.UtcNow; var cacheItem = EventTableCache.GetOrCreateItem(date, utcNowDT); // blocking access to only one event table lock (cacheItem) { var table = cacheItem.Value; // table to get var tableAge = cacheItem.ValueAge; // table file change time bool tableIsNotValid = utcNowDT - cacheItem.ValueRefrDT > DataValidSpan; // the table might be out of date // getting event table from server if (table == null || tableIsNotValid) { string tableName = EventAdapter.BuildEvTableName(date); var newTableAge = serverComm.ReceiveFileAge(ServerComm.Dirs.Events, tableName); if (newTableAge == DateTime.MinValue) { // the table file does not exist or there is no connection to the server table = null; // do not clog the log //log.WriteError($"Unable to receive modification time of the event table {tableName}"); } else if (newTableAge != tableAge) // table file changed { table = new EventTableLight(); if (serverComm.ReceiveEventTable(tableName, table)) { table.FileModTime = newTableAge; table.LastFillTime = utcNowDT; } else { throw new ScadaException("Unable to receive event table."); } } if (table == null) { table = new EventTableLight(); } // update table in cache EventTableCache.UpdateItem(cacheItem, table, newTableAge, utcNowDT); } return(table); } } catch (Exception ex) { log.WriteException(ex, "Error getting event table for {0} from the cache or from the server", date.ToLocalizedDateString()); return(new EventTableLight()); } }
/// <summary> /// Получить таблицу событий за сутки из кэша или от сервера /// </summary> /// <remarks>Возвращаемая таблица после загрузки не изменяется экземпляром данного класса, /// таким образом, чтение её данных является потокобезопасным. /// Метод всегда возвращает объект, не равный null</remarks> public EventTableLight GetEventTable(DateTime date) { try { // получение таблицы событий из кэша date = date.Date; DateTime utcNowDT = DateTime.UtcNow; Cache <DateTime, EventTableLight> .CacheItem cacheItem = EventTableCache.GetOrCreateItem(date, utcNowDT); // блокировка доступа только к одной таблице событий lock (cacheItem) { EventTableLight table = cacheItem.Value; // таблица, которую необходимо получить DateTime tableAge = cacheItem.ValueAge; // время изменения файла таблицы bool tableIsNotValid = utcNowDT - cacheItem.ValueRefrDT > DataValidSpan; // таблица могла устареть // получение таблицы событий от сервера if (table == null || tableIsNotValid) { string tableName = EventAdapter.BuildEvTableName(date); DateTime newTableAge = serverComm.ReceiveFileAge(ServerComm.Dirs.Events, tableName); if (newTableAge == DateTime.MinValue) // файл таблицы не существует или нет связи с сервером { table = null; // не засорять лог /*log.WriteError(string.Format(Localization.UseRussian ? * "Не удалось принять время изменения таблицы событий {0}" : * "Unable to receive modification time of the event table {0}", tableName));*/ } else if (newTableAge != tableAge) // файл таблицы изменён { table = new EventTableLight(); if (serverComm.ReceiveEventTable(tableName, table)) { table.FileModTime = newTableAge; table.LastFillTime = utcNowDT; } else { throw new ScadaException(Localization.UseRussian ? "Не удалось принять таблицу событий." : "Unable to receive event table."); } } if (table == null) { table = new EventTableLight(); } // обновление таблицы в кэше EventTableCache.UpdateItem(cacheItem, table, newTableAge, utcNowDT); } return(table); } } catch (Exception ex) { log.WriteException(ex, Localization.UseRussian ? "Ошибка при получении таблицы событий за {0} из кэша или от сервера" : "Error getting event table for {0} from the cache or from the server", date.ToLocalizedDateString()); return(new EventTableLight()); } }