using Microsoft.AspNetCore.Hosting; using Microsoft.Extensions.Hosting; using Microsoft.Extensions.Logging; using Newtonsoft.Json; using Quartz; using SolarPower.Models.PowerStation; using SolarPower.Repository.Interface; using SolarPower.Services.Implement; using System; using System.Collections.Generic; using System.Linq; using System.Net.Http; using System.Threading.Tasks; using Microsoft.Extensions.Configuration; namespace SolarPower.Quartz.Jobs { [DisallowConcurrentExecution] public class CalcPowerStationJobV2 : IJob { private readonly ILogger logger; private readonly IPowerStationRepository powerStationRepository; private readonly IConfiguration Configuration; public IWebHostEnvironment environment; private double carbonRate; string calcPowerStationTime = ""; public CalcPowerStationJobV2( ILogger logger, IPowerStationRepository powerStationRepository, IWebHostEnvironment environment, IConfiguration Configuration) { this.logger = logger; this.powerStationRepository = powerStationRepository; this.environment = environment; this.Configuration = Configuration; } public async Task Execute(IJobExecutionContext context) { try { var DateTimeNow = DateTime.Now; var dateTime = DateTimeNow.AddHours(-1).ToString("yyyy-MM-dd HH"); logger.LogInformation("【CalcPowerStationJobV2】【任務開始】"); #region step1. 找出所有電站 logger.LogInformation("【CalcPowerStationJobV2】【開始取得電站資料】"); var powerStations = await powerStationRepository.GetAllAsync(); logger.LogInformation("【CalcPowerStationJobV2】【取得成功電站資料】"); logger.LogInformation("【CalcPowerStationJobV2】【電站資料"); #endregion await ArchiveStation(powerStations, dateTime); await ArchiveStationForPowerStationWithWinForm(powerStations, dateTime); await ArchiveSensorWithWinForm(powerStations, dateTime); await ArchiveInverter(powerStations, dateTime); await ArchiveSensoravg(powerStations, dateTime); await ArchiveMeter(powerStations, dateTime); await ArchiveWeather(powerStations, dateTime); logger.LogInformation("【CalcPowerStationJobV2】【任務完成】"); } catch (Exception exception) { logger.LogError("【CalcPowerStationJobV2】[Exception] - {0}", exception.Message); if (exception.InnerException != null) { logger.LogError("【CalcPowerStationJobV2】[InnerException] - {0}", exception.InnerException.Message); } } } private async Task ArchiveStation(List powerStations, string dateTime) { List powerStationHistoriesHour = new List(); List calcPowerStations = new List(); foreach (var powerStation in powerStations) { try { #region step2-1. 取得該電站的當前這小時的歷史資料 var table_name = String.Format("s{1}01_station", powerStation.SiteDB, powerStation.Code); var full_table_name = String.Format("`{0}`.`{1}`", powerStation.SiteDB, table_name); var exist = await powerStationRepository.ExistTable(powerStation.SiteDB, table_name); if (string.IsNullOrEmpty(exist)) { logger.LogError($"【CalcPowerStationJobV2】【查無電站[{powerStation.Code}]的s{powerStation.Code}01_station資料表】"); } else { logger.LogInformation("【CalcPowerStationJobV2】【開始取得電站[{0}]在{1}的每小時歷史資料】", powerStation.Code, dateTime); var history = await powerStationRepository.GetPowerStationHistoryPerHour(dateTime, full_table_name); if (history == null) { logger.LogWarning("【CalcPowerStationJobV2】【查無電站[{0}]在{1}的每小時歷史資料】", powerStation.Code, dateTime); } else { logger.LogInformation("【CalcPowerStationJobV2】【取得成功電站[{0}]在{1}的每小時歷史資料】", powerStation.Code, dateTime); logger.LogInformation("【CalcPowerStationJobV2】【電站[{0}]在{1}的每小時歷史資料】 - {2}", powerStation.Code, dateTime, System.Text.Json.JsonSerializer.Serialize(history)); logger.LogInformation("【CalcPowerStationJobV2】【開始計算電站[{0}]在{1}的每小時歷史資料】", powerStation.Code, dateTime); history.PowerStationId = powerStation.Id; history.Timestamp = Convert.ToDateTime(history.Timestamp + ":00:00").ToString("yyyy-MM-dd HH:mm:ss"); #region 計算單一電站每小時發電量、發電金額等資料 for history #region 發電金額 history.MONEY = history.KWH * powerStation.PowerRate; history.TODAYMONEY = history.TodayKWh * powerStation.PowerRate; history.TOTALMONEY = history.TotalKWH * powerStation.PowerRate; #endregion #region 減碳量 carbonRate = Convert.ToDouble(await powerStationRepository.GetOneVariableByName("CarbonRate")); history.CARBON = history.KWH * carbonRate; history.TODAYCARBON = history.TodayKWh * carbonRate; history.TOTALCARBON = history.TotalKWH * carbonRate; #endregion #endregion powerStationHistoriesHour.Add(history); logger.LogInformation("【CalcPowerStationJobV2】【計算完成電站[{0}]在{1}的每小時歷史資料】", powerStation.Code, dateTime); } } #endregion } catch (Exception exception) { logger.LogError("【CalcPowerStationJobV2】【ArchiveStation】[Exception] - {0}", exception.Message); if (exception.InnerException != null) { logger.LogError("【CalcPowerStationJobV2】【ArchiveStation】[InnerException] - {0}", exception.InnerException.Message); } } } if (!environment.IsDevelopment()) { #region step3. 將historiers INSERT 到 power_station_history_hour 資料表 List history_properties = new List() { "PowerStationId", "TIMESTAMP", "SITEID", "SITETYPE", "KWH", "TODAYKWH", "TOTALKWH", "KWHKWP", "PR", "MP", "SolarHour", "MONEY", "CARBON", "TODAYMONEY", "TOTALMONEY", "TODAYCARBON", "TOTALCARBON" }; logger.LogInformation("【Insert PowerStationHistoryHour】【ArchiveStation】【開始寫入 PowerStationHistoryHour 資料】- {0}", dateTime); await powerStationRepository.AddPowerStationHistory(powerStationHistoriesHour, history_properties); logger.LogInformation("【Insert PowerStationHistoryHour】【ArchiveStation】【完成寫入 PowerStationHistoryHour 資料】- {0}", dateTime); #endregion } } private async Task ArchiveStationForPowerStation(List powerStations, string dateTime) { List powerStationHistoriesHour = new List(); List calcPowerStations = new List(); foreach (var powerStation in powerStations) { try { var calcPowerStation = new PowerStation(); calcPowerStation.Id = powerStation.Id; #region step2-1. 取得該電站的當前這小時的歷史資料 var table_name = String.Format("s{1}01_station", powerStation.SiteDB, powerStation.Code); var full_table_name = String.Format("`{0}`.`{1}`", powerStation.SiteDB, table_name); var exist = await powerStationRepository.ExistTable(powerStation.SiteDB, table_name); if (string.IsNullOrEmpty(exist)) { logger.LogError($"【CalcPowerStationJobV2】【查無電站[{powerStation.Code}]的s{powerStation.Code}01_station資料表】"); } else { #region 計算單一電站每小時發電量、發電金額等資料 for calcPowerStation var dateTimeforPowerStation = DateTime.Now.AddHours(-1).ToString("yyyy-MM-dd");//取當天 logger.LogInformation("【CalcPowerStationJobV2】【開始取得電站[{0}]在{1}的每小時歷史資料 for calcPowerStation】", powerStation.Code, dateTimeforPowerStation); var history_for_powerStation = await powerStationRepository.GetPowerStationHistoryPerHourForPowerStation(dateTimeforPowerStation, full_table_name); if (history_for_powerStation == null) { logger.LogWarning("【CalcPowerStationJobV2】【查無電站[{0}]在{1}的每小時歷史資料 for calcPowerStation;發電量、發電金額等資料設定為0】", powerStation.Code, dateTimeforPowerStation); calcPowerStation.kwh = 0; calcPowerStation.Today_kWh = 0; calcPowerStation.Total_kWh = 0; calcPowerStation.Today_Money = 0; calcPowerStation.Total_Money = 0; calcPowerStation.Today_kwhkwp = 0; calcPowerStation.Today_PR = 0; calcPowerStation.Today_Carbon = 0; calcPowerStation.Total_Carbon = 0; calcPowerStation.SolarHour = 0; } else { logger.LogInformation("【CalcPowerStationJobV2】【開始計算電站[{0}]在{1}的每小時歷史資料 for calcPowerStation】", powerStation.Code, dateTimeforPowerStation); #region 發電量 //每小時發電量(直接填寫 calcPowerStation.kwh = history_for_powerStation.KWH; //今日發電量(直接填寫 calcPowerStation.Today_kWh = history_for_powerStation.TodayKWh; //總發電量(直接填寫 calcPowerStation.Total_kWh = history_for_powerStation.TotalKWH; #endregion #region 發電金額 history_for_powerStation.MONEY = history_for_powerStation.KWH * powerStation.PowerRate; history_for_powerStation.TODAYMONEY = history_for_powerStation.TodayKWh * powerStation.PowerRate; history_for_powerStation.TOTALMONEY = history_for_powerStation.TotalKWH * powerStation.PowerRate; //即時發電金額 switch (powerStation.SolarType) { case (int)SolarTypeEnum.SelfSold: //自建躉售 //今日發電金額 計算方式:todaykWh * 授電費率 calcPowerStation.Today_Money = history_for_powerStation.TodayKWh * powerStation.PowerRate; ////總發電金額 計算方式:totalkWh * 授電費率 calcPowerStation.Total_Money = history_for_powerStation.TotalKWH * powerStation.PowerRate; break; case (int)SolarTypeEnum.HireSold: //租建躉售 //找出該電站的所有土地房屋資訊 var landBuildings = await powerStationRepository.GetAllLandBuildingInfoByPowerStationId(powerStation.Id, powerStation.SiteDB); var sumLeaseRate = 0.00; var avgLeaseRate = 0.00; foreach (var landBuilding in landBuildings) { sumLeaseRate += landBuilding.LeaseRate; } calcPowerStation.Today_Money = history_for_powerStation.TodayKWh * powerStation.PowerRate * sumLeaseRate / 100; calcPowerStation.Total_Money = history_for_powerStation.TotalKWH * powerStation.PowerRate * sumLeaseRate / 100; break; case (int)SolarTypeEnum.SelfUse: //自建自用 //今日發電金額 計算方式:todaykWh * 授電費率 calcPowerStation.Today_Money = history_for_powerStation.TodayKWh * powerStation.PowerRate; //總發電金額 計算方式:totalkWh * 授電費率 calcPowerStation.Total_Money = history_for_powerStation.TotalKWH * powerStation.PowerRate; break; } #endregion #region kWh/kWp ////直接填寫 calcPowerStation.Today_kwhkwp = history_for_powerStation.KWHKWP; #endregion #region PR //直接填寫 calcPowerStation.Today_PR = history_for_powerStation.PR; #endregion #region 減碳量 carbonRate = Convert.ToDouble(await powerStationRepository.GetOneVariableByName("CarbonRate")); history_for_powerStation.CARBON = history_for_powerStation.KWH * carbonRate; history_for_powerStation.TODAYCARBON = history_for_powerStation.TodayKWh * carbonRate; history_for_powerStation.TOTALCARBON = history_for_powerStation.TotalKWH * carbonRate; //今日減碳量( 今日發電量 * (0.554/1000)[抓資料庫值] calcPowerStation.Today_Carbon = history_for_powerStation.TodayKWh * carbonRate; //總減碳量(總發電量 * (0.554/1000)[抓資料庫值] calcPowerStation.Total_Carbon = history_for_powerStation.TotalKWH * carbonRate; #endregion #region 發電時間 calcPowerStation.SolarHour = history_for_powerStation.SolarHour; #endregion #region 取拿到資料的時間 calcPowerStationTime = history_for_powerStation.Timestamp; #endregion } #endregion string dateTimeForCalc; if (calcPowerStationTime != "") { dateTimeForCalc = calcPowerStationTime; } else { dateTimeForCalc = dateTime; } logger.LogInformation("【CalcPowerStationJobV2】【開始取得電站[{0}]在{1}的日照計設備資訊】", powerStation.Code, dateTime); var deviceInfos = await powerStationRepository.GetListPyrheliometerByPowerStationId(powerStation.Id, powerStation.SiteDB); logger.LogInformation("【CalcPowerStationJobV2】【取得成功電站[{0}]在{1}的日照計設備資訊】", powerStation.Code, dateTime); logger.LogInformation("【CalcPowerStationJobV2】【電站[{0}]在{1}的日照計設備資訊】 - {2}", powerStation.Code, dateTime, System.Text.Json.JsonSerializer.Serialize(deviceInfos)); if (deviceInfos != null && deviceInfos.Count() > 0) { var pyrheliometerHistory_for_calcPowerStation = await powerStationRepository.CalcSensorHistoryPerHour(dateTimeForCalc, deviceInfos, Convert.ToInt32(SensorTypeEnum.PYR)); if (pyrheliometerHistory_for_calcPowerStation != null) { calcPowerStation.Today_irradiance = pyrheliometerHistory_for_calcPowerStation.Irradiance; logger.LogInformation("【CalcPowerStationJobV2】【計算完成電站[{0}]在{1}的日照計的平均值】", powerStation.Code, dateTime); } else { logger.LogWarning("【CalcPowerStationJobV2】【查無結果電站[{0}]在{1}的日照計的平均值】", powerStation.Code, dateTime); } } calcPowerStations.Add(calcPowerStation); logger.LogInformation("【CalcPowerStationJobV2】【計算完成電站[{0}]在{1}的每小時歷史資料】", powerStation.Code, dateTime); } #endregion } catch (Exception exception) { logger.LogError("【CalcPowerStationJobV2】【ArchiveStation】[Exception] - {0}", exception.Message); if (exception.InnerException != null) { logger.LogError("【CalcPowerStationJobV2】【ArchiveStation】[InnerException] - {0}", exception.InnerException.Message); } } } if (!environment.IsDevelopment()) { #region step5. calcPowerStations UPDATE 到 power_station 資料表 List power_station_properties = new List() { "Id", "kwh", "Today_kwh", "Total_kwh", "today_kwhkwp", "today_money", "total_money", "today_PR", "today_carbon", "total_carbon", "today_irradiance", "SolarHour", "WeathersStationId", "TodayWeatherTemp", "TodayWeather", "RateOfRain" }; logger.LogInformation("【update Power_Station】【ArchiveStation】【開始更新 Power_Station 資料】- {0}", dateTime); await powerStationRepository.UpdateList(calcPowerStations, power_station_properties); logger.LogInformation("【update Power_Station】【ArchiveStation】【完成更新 Power_Station 資料】- {0}", dateTime); #endregion } } private async Task ArchiveStationForPowerStationWithWinForm(List powerStations, string dateTime) { logger.LogInformation("【CalcPowerStationJobV2】【開始計算全電站在{0}的發電量等資訊】", dateTime); #region step2-2. 取得該電站的當前這小時的發電量等歷史資料 //使用winform function var Connection_string = Configuration.GetValue("mySql"); SensorHourlyService sensorHourlyService = new SensorHourlyService(Connection_string); await sensorHourlyService.ArchiveStationHourly(); logger.LogInformation("【CalcPowerStationJobV2】【更新完成全電站在{0}的發電量等資訊】", dateTime); #endregion } private async Task ArchiveSensorWithWinForm(List powerStations, string dateTime) { foreach (var powerStation in powerStations) { try { var sensoravg_table_name = String.Format("s{1}01_sensoravg", powerStation.SiteDB, powerStation.Code); var full_sensoravg_table_name = String.Format("`{0}`.`{1}`", powerStation.SiteDB, sensoravg_table_name); var sensoravg_table_exist = await powerStationRepository.ExistTable(powerStation.SiteDB, sensoravg_table_name); if (string.IsNullOrEmpty(sensoravg_table_exist)) { logger.LogError($"【CalcPowerStationJobV2】【查無電站[{powerStation.Code}]的s{powerStation.Code}01_sensoravg資料表】"); } else { logger.LogInformation("【CalcPowerStationJobV2】【開始計算電站[{0}]在{1}的設備資訊】", powerStation.Code, dateTime); #region step2-2. 取得該電站的當前這小時的設備歷史資料 //使用winform function var Connection_string = Configuration.GetValue("mySql"); SensorHourlyService sensorHourlyService = new SensorHourlyService(Connection_string); sensorHourlyService.ArchiveSensorHourly(powerStation.Code, dateTime); logger.LogInformation("【CalcPowerStationJobV2】【更新完成電站[{0}]在{1}的設備資訊】", powerStation.Code, dateTime); #endregion } } catch (Exception exception) { logger.LogError("【CalcPowerStationJobV2】【ArchiveSensor】[Exception] - {0}", exception.Message); if (exception.InnerException != null) { logger.LogError("【CalcPowerStationJobV2】【ArchiveSensor】[InnerException] - {0}", exception.InnerException.Message); } } } } private async Task ArchiveInverter(List powerStations, string dateTime) { List inverterHistoriesHour = new List(); foreach (var powerStation in powerStations) { #region step2-3. 計算該電站所有逆變器每小時值 var inverter_table_name = String.Format("s{0}01_inv", powerStation.Code); var full_inverter_table_name = String.Format("`{0}`.`{1}`", powerStation.SiteDB, inverter_table_name); var inverter_exist = await powerStationRepository.ExistTable(powerStation.SiteDB, inverter_table_name); if (string.IsNullOrEmpty(inverter_exist)) { logger.LogError("【CalcPowerStationJobV2】【查無電站[0]的s{0}01_inv資料表】", powerStation.Code); } else { try { logger.LogInformation("【CalcPowerStationJobV2】【開始取得電站[{0}]在{1}的逆變器設備資訊】", powerStation.Code, dateTime); var controllers = await powerStationRepository.GetAllDeviceControllerId(powerStation.Id, powerStation.SiteDB); var inverters = await powerStationRepository.InverterTable(controllers, powerStation.SiteDB); var inverterIds = inverters.Where(x => x.Enabled == 1 && x.Status != 0).Select(x => x.InverterId).ToList(); logger.LogInformation("【CalcPowerStationJobV2】【取得成功電站[{0}]在{1}的逆變器設備資訊】", powerStation.Code, dateTime); logger.LogInformation("【CalcPowerStationJobV2】【電站[{0}]在{1}的逆變器設備資訊】 - {2}", powerStation.Code, dateTime, System.Text.Json.JsonSerializer.Serialize(inverterIds)); if (inverterIds != null && inverterIds.Count() > 0) { logger.LogInformation("【CalcPowerStationJobV2】【開始計算電站[{0}]在{1}的逆變器的資訊】", powerStation.Code, dateTime); var inverterHistories = await powerStationRepository.CalcInverterHisyortHourData(dateTime, powerStation.SiteDB, full_inverter_table_name, inverterIds); //取得日照計要找的欄位資訊 var pyrheliometer = await powerStationRepository.GetFirstPyrheliometerInfo(powerStation.Id, powerStation.SiteDB); var pyrheliometerValue = await powerStationRepository.GetFirstPyrheliometerValue(dateTime, pyrheliometer.DBName, pyrheliometer.TableName, pyrheliometer.ColName); foreach (var inverterHistory in inverterHistories) { inverterHistory.Irradiance = pyrheliometerValue; inverterHistory.DC1KW = inverterHistory.DC1W / 1000; inverterHistory.DC2KW = inverterHistory.DC2W / 1000; inverterHistory.DC3KW = inverterHistory.DC3W / 1000; inverterHistory.DC4KW = inverterHistory.DC4W / 1000; inverterHistory.DC5KW = inverterHistory.DC5W / 1000; inverterHistory.DCKW = (inverterHistory.DC1W + inverterHistory.DC2W + inverterHistory.DC3W + inverterHistory.DC4W + inverterHistory.DC5W) / 1000; inverterHistory.ACKW = (inverterHistory.AC1W + inverterHistory.AC2W + inverterHistory.AC3W) / 1000; inverterHistory.TIMESTAMP = Convert.ToDateTime(inverterHistory.TIMESTAMP + ":00:00").ToString("yyyy-MM-dd HH:mm:ss"); inverterHistory.PowerStationId = powerStation.Id; inverterHistoriesHour.Add(inverterHistory); } logger.LogInformation("【CalcPowerStationJobV2】【計算完成電站[{0}]在{1}的逆變器的資訊】", powerStation.Code, dateTime); } } catch (Exception ex) { logger.LogError("【CalcPowerStationJobV2】【ArchiveInverter】【計算失敗電站[{0}]在{1}的逆變器的資訊】", powerStation.Code, dateTime); logger.LogError("【CalcPowerStationJobV2】【ArchiveInverter】【失敗原因】- {0}", ex.Message); } } #endregion } if (!environment.IsDevelopment()) { #region step6. 將 inverter INSERT 到 inverter_history_hour 資料表 List inverter_history_properties = new List() { "PowerStationId", "INVERTERID", "TIMESTAMP", "Irradiance", "AC1V", "AC1A", "AC1W", "AC1F", "AC1WH", "AC2V", "AC2A", "AC2W", "AC2F", "AC2WH", "AC3V", "AC3A", "AC3W", "AC3F", "AC3WH", "DC1V", "DC1A", "DC1W", "DC1KW", "DC1WH", "DC2V", "DC2A", "DC2W", "DC2KW", "DC2WH", "DC3V", "DC3A", "DC3W", "DC3KW", "DC3WH", "DC4V", "DC4A", "DC4W", "DC4KW", "DC4WH", "DC5V", "DC5A", "DC5W", "DC5KW", "DC5WH", "PR", "RA1", "RA2", "RA3", "RA4", "RA5", "DCKW", "ACKW", "KWH", "TODAYKWH", "TOTALKWH", "KWHKWP", }; logger.LogInformation("【Insert InverterHistoryHour】【ArchiveInverter】【開始寫入 inverter_history_hour 資料】- {0}", dateTime); await powerStationRepository.AddInverterHistory(inverterHistoriesHour, inverter_history_properties); logger.LogInformation("【Insert InverterHistoryHour】【ArchiveInverter】【完成寫入 inverter_history_hour 資料】- {0}", dateTime); #endregion } } private async Task ArchiveSensoravg(List powerStations, string dateTime) { List sensorAvgHistoryHour = new List(); foreach (var powerStation in powerStations) { try { var sensoravg_table_name = String.Format("s{1}01_sensoravg", powerStation.SiteDB, powerStation.Code); var full_sensoravg_table_name = String.Format("`{0}`.`{1}`", powerStation.SiteDB, sensoravg_table_name); var sensoravg_table_exist = await powerStationRepository.ExistTable(powerStation.SiteDB, sensoravg_table_name); #region step2-4. 計算該電站所有sensoravg try { if (!string.IsNullOrEmpty(sensoravg_table_exist)) { logger.LogInformation("【CalcPowerStationJobV2】【開始計算電站[{0}]在{1}的sensor avg的資訊】", powerStation.Code, dateTime); var sensorAvgHistory = await powerStationRepository.CalcSensorAvgHistory(dateTime, full_sensoravg_table_name); logger.LogInformation("【CalcPowerStationJobV2】【計算完成電站[{0}]在{1}的sensor avg的資訊】", powerStation.Code, dateTime); if (sensorAvgHistory != null) { sensorAvgHistory.PowerStationId = powerStation.Id; sensorAvgHistory.TIMESTAMP = Convert.ToDateTime(sensorAvgHistory.TIMESTAMP + ":00:00").ToString("yyyy-MM-dd HH:mm:ss"); sensorAvgHistoryHour.Add(sensorAvgHistory); } } } catch (Exception ex) { logger.LogError("【CalcPowerStationJobV2】【ArchiveSensoravg】【計算失敗電站[{0}]在{1}的sensor avg的資訊】", powerStation.Code, dateTime); logger.LogError("【CalcPowerStationJobV2】【ArchiveSensoravg】【失敗原因】- {0}", ex.Message); } #endregion } catch (Exception exception) { logger.LogError("【CalcPowerStationJobV2】【ArchiveSensoravg】[Exception] - {0}", exception.Message); if (exception.InnerException != null) { logger.LogError("【CalcPowerStationJobV2】【ArchiveSensoravg】[InnerException] - {0}", exception.InnerException.Message); } } } if (!environment.IsDevelopment()) { #region step7. 將 sensoravg INSERT 到 sensoravg_history_hour 資料表 List sensoravg_history_properties = new List() { "PowerStationId", "TIMESTAMP", "SENSORAVG01", "SENSORAVG02", "SENSORAVG03", "SENSORAVG04", "SENSORAVG05", "SENSORAVG06", "SENSORAVG07", "SENSORAVG08", "SENSORAVG09", "SENSORAVG10", "SENSORAVG11", "SENSORAVG12", "SENSORAVG13", "SENSORAVG14", "SENSORAVG15", "SENSORAVG16", "SENSORAVG17", "SENSORAVG18", "SENSORAVG19", "SENSORAVG20", "SENSORAVG21", "SENSORAVG22", "SENSORAVG23", "SENSORAVG24", "SENSORAVG25", "SENSORAVG26", "SENSORAVG27", "SENSORAVG28", "SENSORAVG29", "SENSORAVG30", "SENSORAVG31", "SENSORAVG32", "SENSORAVG33", "SENSORAVG34", "SENSORAVG35", "SENSORAVG36", "SENSORAVG37", "SENSORAVG38", "SENSORAVG39", "SENSORAVG40", "SENSORAVG41", "SENSORAVG42", "SENSORAVG43", "SENSORAVG44", "SENSORAVG45", "SENSORAVG46", "SENSORAVG47", "SENSORAVG48", "SENSORAVG49", "SENSORAVG50", }; logger.LogInformation("【Insert SensoravgHistoryHour】【ArchiveSensoravg】【開始寫入 sensoravg_history_hour 資料】- {0}", dateTime); await powerStationRepository.AddSensorAvgHistory(sensorAvgHistoryHour, sensoravg_history_properties); logger.LogInformation("【Insert SensoravgHistoryHour】【ArchiveSensoravg】【完成寫入 sensoravg_history_hour 資料】- {0}", dateTime); #endregion } } private async Task ArchiveMeter(List powerStations, string dateTime) { List meterHistoriesHour = new List(); foreach (var powerStation in powerStations) { try { var meter_table_name = String.Format("s{0}01_meter", powerStation.Code); var full_meter_table_name = String.Format("`{0}`.`{1}`", powerStation.SiteDB, meter_table_name); var exist_meter_table = await powerStationRepository.ExistTable(powerStation.SiteDB, meter_table_name); #region step2-5. 計算該電站meter try { if (string.IsNullOrEmpty(exist_meter_table)) { logger.LogError($"【CalcPowerStationJobV2】【查無電站[{powerStation.Code}]的s{powerStation.Code}01_meter資料表】"); } else { logger.LogInformation("【CalcPowerStationJobV2】【開始計算電站[{0}]在{1}的meter的資訊】", powerStation.Code, dateTime); var meterHistory = await powerStationRepository.CalcMeterHistory(dateTime, full_meter_table_name); logger.LogInformation("【CalcPowerStationJobV2】【計算完成電站[{0}]在{1}的meter的資訊】", powerStation.Code, dateTime); if (meterHistory != null) { meterHistory.PowerStationId = powerStation.Id; meterHistory.TIMESTAMP = Convert.ToDateTime(meterHistory.TIMESTAMP + ":00:00").ToString("yyyy-MM-dd HH:mm:ss"); meterHistoriesHour.Add(meterHistory); } } } catch (Exception ex) { logger.LogError("【CalcPowerStationJobV2】【ArchiveMeter】【計算失敗電站[{0}]在{1}的meter的資訊】", powerStation.Code, dateTime); logger.LogError("【CalcPowerStationJobV2】【ArchiveMeter】【失敗原因】- {0}", ex.Message); } #endregion } catch (Exception exception) { logger.LogError("【CalcPowerStationJobV2】【ArchiveMeter】[Exception] - {0}", exception.Message); if (exception.InnerException != null) { logger.LogError("【CalcPowerStationJobV2】【ArchiveMeter】[InnerException] - {0}", exception.InnerException.Message); } } } if (!environment.IsDevelopment()) { #region step8. 將 meter INSERT 到 meter_history_hour 資料表 List memter_history_properties = new List() { "PowerStationId", "TIMESTAMP", "METERID", "V_AB", "V_BC", "V_CA", "I_A", "I_B", "I_C", "I_C", "P", "F", "INPUT_KWH", "OUTPUT_KWH" }; logger.LogInformation("【Insert MeterHistoryHour】【ArchiveMeter】【開始寫入 meter_history_hour 資料】- {0}", dateTime); await powerStationRepository.AddMeterHistory(meterHistoriesHour, memter_history_properties); logger.LogInformation("【Insert MeterHistoryHour】【ArchiveMeter】【完成寫入 meter_history_hour 資料】- {0}", dateTime); #endregion } } private async Task ArchiveWeather(List powerStations, string dateTime) { Root2 observation = null; List weatherObservations = new List(); #region 氣象觀測(取資料) try { logger.LogInformation("【CalcPowerStationJobV2】【開始取得氣象觀測】"); var client = new HttpClient(); var UVUri = "https://opendata.cwb.gov.tw/api/v1/rest/datastore/O-A0003-001?Authorization=CWB-EA24220B-DDCC-4188-84E5-AD37A0E03F80&elementName=TIME,TEMP"; HttpResponseMessage response = client.GetAsync(UVUri).Result; String jsonUVs = response.Content.ReadAsStringAsync().Result.ToString(); observation = JsonConvert.DeserializeObject(jsonUVs); logger.LogInformation("【CalcPowerStationJobV2】【取得成功氣象觀測】"); } catch (Exception ex) { logger.LogError("【CalcPowerStationJobV2】【取得失敗氣象觀測】"); logger.LogError("【{0}】{1}", "CalcPowerStationJobV2", ex.Message); observation = null; } #endregion foreach (var powerStation in powerStations) { try { var calcPowerStation = new PowerStation(); calcPowerStation.Id = powerStation.Id; #region 確認是否有觀測站(沒有則新增) try { if (powerStation.WeathersStationId == null) { var weatherStationId = ""; double shortLocation = 9999; foreach (var Location in observation.Records.Location) { if (powerStation.Coordinate != null) { var powerLocation = powerStation.Coordinate.Split(','); double p1 = Convert.ToDouble(powerLocation[0].Replace("°", string.Empty)); double p2 = Convert.ToDouble(powerLocation[1].Replace("°", string.Empty)); double dLat = Convert.ToDouble(Location.Lat); double dLon = Convert.ToDouble(Location.Lon); double x = Math.Pow(p1 - dLat, 2); double y = Math.Pow(p2 - dLon, 2); var nowLocation = Math.Sqrt(x + y); if (nowLocation < shortLocation) { shortLocation = nowLocation; weatherStationId = Location.StationId; calcPowerStation.TodayWeatherTemp = Convert.ToDouble(Location.WeatherElement[0].ElementValue); } } } calcPowerStation.WeathersStationId = weatherStationId; } WeatherObservation weatherObservation = new WeatherObservation(); if (powerStation.WeathersStationId != null && observation != null) { foreach (var Location in observation.Records.Location) { if (Location.StationId == powerStation.WeathersStationId) { calcPowerStation.TodayWeatherTemp = Convert.ToDouble(Location.WeatherElement[0].ElementValue); weatherObservation.PowerStationId = powerStation.Id; weatherObservation.Temp = Convert.ToDouble(Location.WeatherElement[0].ElementValue); weatherObservation.ObsTime = !string.IsNullOrEmpty(Location.Time.ObsTime) ? Convert.ToInt32(Location.Time.ObsTime.Substring(0, 4)) >= 1971 ? Location.Time.ObsTime : DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss") : DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"); calcPowerStation.WeathersStationId = powerStation.WeathersStationId; break; } } weatherObservations.Add(weatherObservation); } logger.LogInformation("【CalcPowerStationJobV2】【開始取得電站[{0}]在{1}的天氣預報的資訊】", powerStation.Code, dateTime); var weather = await powerStationRepository.SelectNowWeather(powerStation.CityId); logger.LogInformation("【CalcPowerStationJobV2】【取得成功電站[{0}]在{1}的天氣預報的資訊】", powerStation.Code, dateTime); if (weather != null) { calcPowerStation.TodayWeather = weather.WeatherKey; calcPowerStation.RateOfRain = weather.PoP; } } catch (Exception ex) { logger.LogError("【CalcPowerStationJobV2】【ArchiveWeather】【取得失敗電站[{0}]在{1}的天氣預報的資訊】", powerStation.Code, dateTime); logger.LogError("【CalcPowerStationJobV2】【ArchiveWeather】【失敗原因】- {0}", ex.Message); } #endregion } catch (Exception exception) { //logger.LogError("【CalcPowerStationJobV2】[Exception] - {0}", exception.Message); if (exception.InnerException != null) { //logger.LogError("【CalcPowerStationJobV2】[InnerException] - {0}", exception.InnerException.Message); } } } if (!environment.IsDevelopment()) { #region step9. 新增天氣資訊 List weather_observation_properties = new List() { "PowerStationId", "ObsTime", "Temp" }; logger.LogInformation("【Insert WeatherObservation】【ArchiveWeather】【開始寫入 weather_observation 資料】- {0}", dateTime); await powerStationRepository.AddWeatherObservation(weatherObservations, weather_observation_properties); logger.LogInformation("【Insert WeatherObservation】【ArchiveWeather】【完成寫入 weather_observation 資料】- {0}", dateTime); #endregion } } } }