diff --git a/CumulusMX/Alarm.cs b/CumulusMX/Alarm.cs index 4a4ac537..4abfc13f 100644 --- a/CumulusMX/Alarm.cs +++ b/CumulusMX/Alarm.cs @@ -49,7 +49,7 @@ public bool Triggered public double LatchHours { get; set; } public string EmailMsg { get; set; } public string Units { get; set; } - public string LastError { get; set; } + public string LastMessage { get; set; } public int TriggerThreshold { get; set; } AlarmTypes type; @@ -72,6 +72,12 @@ public void CheckAlarm(double value) } } + public void ClearAlarm() + { + if (Latch && triggered && DateTime.Now > triggeredTime.AddHours(LatchHours)) + doTriggered(false); + } + private void doTriggered(bool value) { if (value) @@ -91,9 +97,9 @@ private void doTriggered(bool value) { // Construct the message - preamble, plus values var msg = cumulus.Trans.AlarmEmailPreamble + "\r\n" + string.Format(EmailMsg, Value, Units); - if (!string.IsNullOrEmpty(LastError)) + if (!string.IsNullOrEmpty(LastMessage)) { - msg += "\r\nLast error: " + LastError; + msg += "\r\nLast message: " + LastMessage; } _ = Task.Run(async () => { @@ -105,7 +111,7 @@ private void doTriggered(bool value) cumulus.LogMessage($"Alarm ({Name}): Sending email - attempt {i + 1}"); - if (await cumulus.emailer.SendEmail(cumulus.AlarmDestEmail, cumulus.AlarmFromEmail, cumulus.Trans.AlarmEmailSubject, msg, cumulus.AlarmEmailHtml)) + if (await cumulus.emailer.SendEmail(cumulus.AlarmDestEmail, cumulus.AlarmFromEmail, cumulus.Trans.AlarmEmailSubject, msg, cumulus.AlarmEmailHtml, cumulus.AlarmEmailUseBcc)) { break; } @@ -239,6 +245,15 @@ public bool DownTriggered } } + public new void ClearAlarm() + { + if (Latch && upTriggered && DateTime.Now > UpTriggeredTime.AddHours(LatchHours)) + doUpTriggered(false); + + if (Latch && downTriggered && DateTime.Now > DownTriggeredTime.AddHours(LatchHours)) + doDownTriggered(false); + } + private void doUpTriggered(bool value) { if (value) @@ -262,7 +277,7 @@ private void doUpTriggered(bool value) cumulus.LogMessage($"Alarm ({Name}): Sending email - attempt {i + 1}"); - if (await cumulus.emailer.SendEmail(cumulus.AlarmDestEmail, cumulus.AlarmFromEmail, cumulus.Trans.AlarmEmailSubject, msg, cumulus.AlarmEmailHtml)) + if (await cumulus.emailer.SendEmail(cumulus.AlarmDestEmail, cumulus.AlarmFromEmail, cumulus.Trans.AlarmEmailSubject, msg, cumulus.AlarmEmailHtml, cumulus.AlarmEmailUseBcc)) { break; } @@ -336,7 +351,7 @@ private void doDownTriggered(bool value) cumulus.LogMessage($"Alarm ({Name}): Sending email - attempt {i + 1}"); - if (await cumulus.emailer.SendEmail(cumulus.AlarmDestEmail, cumulus.AlarmFromEmail, cumulus.Trans.AlarmEmailSubject, msg, cumulus.AlarmEmailHtml)) + if (await cumulus.emailer.SendEmail(cumulus.AlarmDestEmail, cumulus.AlarmFromEmail, cumulus.Trans.AlarmEmailSubject, msg, cumulus.AlarmEmailHtml, cumulus.AlarmEmailUseBcc)) { break; } diff --git a/CumulusMX/AlarmSettings.cs b/CumulusMX/AlarmSettings.cs index 07df7d6d..6749c9df 100644 --- a/CumulusMX/AlarmSettings.cs +++ b/CumulusMX/AlarmSettings.cs @@ -185,6 +185,19 @@ public string GetAlarmSettings() Action = cumulus.SensorAlarm.Action, ActionParams = cumulus.SensorAlarm.ActionParams }, + newRecord = new JsonAlarmValues() + { + Enabled = cumulus.NewRecordAlarm.Enabled, + SoundEnabled = cumulus.NewRecordAlarm.Sound, + Sound = cumulus.NewRecordAlarm.SoundFile, + Notify = cumulus.NewRecordAlarm.Notify, + Email = cumulus.NewRecordAlarm.Email, + Latches = cumulus.NewRecordAlarm.Latch, + LatchHrs = cumulus.NewRecordAlarm.LatchHours, + Threshold = cumulus.NewRecordAlarm.TriggerThreshold, + Action = cumulus.NewRecordAlarm.Action, + ActionParams = cumulus.NewRecordAlarm.ActionParams + }, dataStopped = new JsonAlarmValues() { Enabled = cumulus.DataStoppedAlarm.Enabled, @@ -238,16 +251,16 @@ public string GetAlarmSettings() }, httpUpload = new JsonAlarmValues() { - Enabled = cumulus.HttpUploadAlarm.Enabled, - SoundEnabled = cumulus.HttpUploadAlarm.Sound, - Sound = cumulus.HttpUploadAlarm.SoundFile, - Notify = cumulus.HttpUploadAlarm.Notify, - Email = cumulus.HttpUploadAlarm.Email, - Latches = cumulus.HttpUploadAlarm.Latch, - LatchHrs = cumulus.HttpUploadAlarm.LatchHours, - Threshold = cumulus.HttpUploadAlarm.TriggerThreshold, - Action = cumulus.HttpUploadAlarm.Action, - ActionParams = cumulus.HttpUploadAlarm.ActionParams + Enabled = cumulus.ThirdPartyAlarm.Enabled, + SoundEnabled = cumulus.ThirdPartyAlarm.Sound, + Sound = cumulus.ThirdPartyAlarm.SoundFile, + Notify = cumulus.ThirdPartyAlarm.Notify, + Email = cumulus.ThirdPartyAlarm.Email, + Latches = cumulus.ThirdPartyAlarm.Latch, + LatchHrs = cumulus.ThirdPartyAlarm.LatchHours, + Threshold = cumulus.ThirdPartyAlarm.TriggerThreshold, + Action = cumulus.ThirdPartyAlarm.Action, + ActionParams = cumulus.ThirdPartyAlarm.ActionParams }, mySqlUpload = new JsonAlarmValues() { @@ -261,6 +274,19 @@ public string GetAlarmSettings() Threshold = cumulus.MySqlUploadAlarm.TriggerThreshold, Action = cumulus.MySqlUploadAlarm.Action, ActionParams = cumulus.MySqlUploadAlarm.ActionParams + }, + ftpUpload = new JsonAlarmValues() + { + Enabled = cumulus.FtpAlarm.Enabled, + SoundEnabled = cumulus.FtpAlarm.Sound, + Sound = cumulus.FtpAlarm.SoundFile, + Notify = cumulus.FtpAlarm.Notify, + Email = cumulus.FtpAlarm.Email, + Latches = cumulus.FtpAlarm.Latch, + LatchHrs = cumulus.FtpAlarm.LatchHours, + Threshold = cumulus.FtpAlarm.TriggerThreshold, + Action = cumulus.FtpAlarm.Action, + ActionParams = cumulus.FtpAlarm.ActionParams } }; @@ -268,7 +294,8 @@ public string GetAlarmSettings() { fromEmail = cumulus.AlarmFromEmail, destEmail = cumulus.AlarmDestEmail.Join(";"), - useHtml = cumulus.AlarmEmailHtml + useHtml = cumulus.AlarmEmailHtml, + useBcc = cumulus.AlarmEmailUseBcc }; var retObject = new JsonAlarmSettings() @@ -448,6 +475,18 @@ public string UpdateAlarmSettings(IHttpContext context) cumulus.HighWindAlarm.Action = settings.windAbove.Action.Trim(); cumulus.HighWindAlarm.ActionParams = settings.windAbove.ActionParams.Trim(); + cumulus.NewRecordAlarm.Enabled = settings.newRecord.Enabled; + cumulus.NewRecordAlarm.Sound = settings.newRecord.SoundEnabled; + cumulus.NewRecordAlarm.SoundFile = settings.newRecord.Sound.Trim(); + cumulus.NewRecordAlarm.Notify = settings.newRecord.Notify; + cumulus.NewRecordAlarm.Email = settings.newRecord.Email; + cumulus.NewRecordAlarm.Latch = settings.newRecord.Latches; + cumulus.NewRecordAlarm.LatchHours = settings.newRecord.LatchHrs; + cumulus.NewRecordAlarm.TriggerThreshold = settings.newRecord.Threshold; + emailRequired = emailRequired || (cumulus.NewRecordAlarm.Email && cumulus.NewRecordAlarm.Enabled); + cumulus.NewRecordAlarm.Action = settings.newRecord.Action.Trim(); + cumulus.NewRecordAlarm.ActionParams = settings.newRecord.ActionParams.Trim(); + cumulus.SensorAlarm.Enabled = settings.contactLost.Enabled; cumulus.SensorAlarm.Sound = settings.contactLost.SoundEnabled; cumulus.SensorAlarm.SoundFile = settings.contactLost.Sound.Trim(); @@ -507,17 +546,17 @@ public string UpdateAlarmSettings(IHttpContext context) cumulus.UpgradeAlarm.Action = settings.upgrade.Action.Trim(); cumulus.UpgradeAlarm.ActionParams = settings.upgrade.ActionParams.Trim(); - cumulus.HttpUploadAlarm.Enabled = settings.httpUpload.Enabled; - cumulus.HttpUploadAlarm.Sound = settings.httpUpload.SoundEnabled; - cumulus.HttpUploadAlarm.SoundFile = settings.httpUpload.Sound.Trim(); - cumulus.HttpUploadAlarm.Notify = settings.httpUpload.Notify; - cumulus.HttpUploadAlarm.Email = settings.httpUpload.Email; - cumulus.HttpUploadAlarm.Latch = settings.httpUpload.Latches; - cumulus.HttpUploadAlarm.LatchHours = settings.httpUpload.LatchHrs; - cumulus.HttpUploadAlarm.TriggerThreshold = settings.httpUpload.Threshold; - emailRequired = emailRequired || (cumulus.HttpUploadAlarm.Email && cumulus.HttpUploadAlarm.Enabled); - cumulus.HttpUploadAlarm.Action = settings.httpUpload.Action.Trim(); - cumulus.HttpUploadAlarm.ActionParams = settings.httpUpload.ActionParams.Trim(); + cumulus.ThirdPartyAlarm.Enabled = settings.httpUpload.Enabled; + cumulus.ThirdPartyAlarm.Sound = settings.httpUpload.SoundEnabled; + cumulus.ThirdPartyAlarm.SoundFile = settings.httpUpload.Sound.Trim(); + cumulus.ThirdPartyAlarm.Notify = settings.httpUpload.Notify; + cumulus.ThirdPartyAlarm.Email = settings.httpUpload.Email; + cumulus.ThirdPartyAlarm.Latch = settings.httpUpload.Latches; + cumulus.ThirdPartyAlarm.LatchHours = settings.httpUpload.LatchHrs; + cumulus.ThirdPartyAlarm.TriggerThreshold = settings.httpUpload.Threshold; + emailRequired = emailRequired || (cumulus.ThirdPartyAlarm.Email && cumulus.ThirdPartyAlarm.Enabled); + cumulus.ThirdPartyAlarm.Action = settings.httpUpload.Action.Trim(); + cumulus.ThirdPartyAlarm.ActionParams = settings.httpUpload.ActionParams.Trim(); cumulus.MySqlUploadAlarm.Enabled = settings.mySqlUpload.Enabled; cumulus.MySqlUploadAlarm.Sound = settings.mySqlUpload.SoundEnabled; @@ -531,6 +570,18 @@ public string UpdateAlarmSettings(IHttpContext context) cumulus.MySqlUploadAlarm.Action = settings.mySqlUpload.Action.Trim(); cumulus.MySqlUploadAlarm.ActionParams = settings.mySqlUpload.ActionParams.Trim(); + cumulus.FtpAlarm.Enabled = settings.ftpUpload.Enabled; + cumulus.FtpAlarm.Sound = settings.ftpUpload.SoundEnabled; + cumulus.FtpAlarm.SoundFile = settings.ftpUpload.Sound.Trim(); + cumulus.FtpAlarm.Notify = settings.ftpUpload.Notify; + cumulus.FtpAlarm.Email = settings.ftpUpload.Email; + cumulus.FtpAlarm.Latch = settings.ftpUpload.Latches; + cumulus.FtpAlarm.LatchHours = settings.ftpUpload.LatchHrs; + cumulus.FtpAlarm.TriggerThreshold = settings.ftpUpload.Threshold; + emailRequired = emailRequired || (cumulus.FtpAlarm.Email && cumulus.FtpAlarm.Enabled); + cumulus.FtpAlarm.Action = settings.ftpUpload.Action.Trim(); + cumulus.FtpAlarm.ActionParams = settings.ftpUpload.ActionParams.Trim(); + // validate the from email if (emailRequired && !EmailSender.CheckEmailAddress(result.email.fromEmail.Trim())) { @@ -559,6 +610,7 @@ public string UpdateAlarmSettings(IHttpContext context) } cumulus.AlarmDestEmail = emails; cumulus.AlarmEmailHtml = result.email.useHtml; + cumulus.AlarmEmailUseBcc = result.email.useBcc; // Save the settings cumulus.WriteIniFile(); @@ -648,6 +700,7 @@ public class JsonAlarmSettingsData public JsonAlarmValues rainRateAbove { get; set; } public JsonAlarmValues gustAbove { get; set; } public JsonAlarmValues windAbove { get; set; } + public JsonAlarmValues newRecord { get; set; } public JsonAlarmValues contactLost { get; set; } public JsonAlarmValues dataStopped { get; set; } public JsonAlarmValues batteryLow { get; set; } @@ -656,6 +709,7 @@ public class JsonAlarmSettingsData public JsonAlarmValues httpUpload { get; set; } public JsonAlarmValues mySqlUpload { get; set; } public JsonAlarmValues isRaining { get; set; } + public JsonAlarmValues ftpUpload { get; set; } } public class JsonAlarmValues @@ -678,6 +732,7 @@ public class JsonAlarmEmail public string fromEmail { get; set; } public string destEmail { get; set; } public bool useHtml { get; set; } + public bool useBcc { get; set; } } public class JsonAlarmUnits diff --git a/CumulusMX/AstroLib.cs b/CumulusMX/AstroLib.cs index cde6eb68..688e689f 100644 --- a/CumulusMX/AstroLib.cs +++ b/CumulusMX/AstroLib.cs @@ -4,7 +4,7 @@ namespace CumulusMX { internal class AstroLib { - public static double BrasSolar(double el, double erv, double nfac) + public static int BrasSolar(double el, double erv, double nfac) { // el solar elevation deg from horizon // erv distance from earth to sun in AU @@ -25,10 +25,10 @@ public static double BrasSolar(double el, double erv, double nfac) double al = 0.128 - (0.054 * Math.Log(m) / Math.Log(10)); // clear-sky solar radiation at earth surface on horizontal surface (W/m^2) - return i0 * Math.Exp(-nfac * al * m); + return (int) Math.Round(i0 * Math.Exp(-nfac * al * m)); } - public static double RyanStolzSolar(double el, double erv, double atc, double z) + public static int RyanStolzSolar(double el, double erv, double atc, double z) { // el solar elevation deg from horizon // erv distance from earth to sun in AU @@ -47,7 +47,7 @@ public static double RyanStolzSolar(double el, double erv, double atc, double z) double rsToa = 1360 * sinal / (erv * erv); // RS on the top of atmosphere - return rsToa * Math.Pow(atc, rm); //RS on the ground + return (int) Math.Round(rsToa * Math.Pow(atc, rm)); //RS on the ground } private static double DegToRad(double angle) @@ -60,8 +60,8 @@ private static double RadToDeg(double angle) return angle * (180.0 / Math.PI); } - public static double SolarMax(DateTime timestamp, double longitude, double latitude, double altitude, - out double solarelevation, SolarOptions options) + public static int SolarMax(DateTime timestamp, double longitude, double latitude, double altitude, + out double solarelevation, SolarOptions options) { double factor = 0; if (options.SolarCalc == 0) @@ -76,7 +76,7 @@ public static double SolarMax(DateTime timestamp, double longitude, double latit } - private static double SolarMax(DateTime timestamp, double longitude, double latitude, double altitude, + private static int SolarMax(DateTime timestamp, double longitude, double latitude, double altitude, out double solarelevation, double factor, int method) { DateTime utctime = timestamp.ToUniversalTime(); @@ -504,7 +504,7 @@ private static double calcObliquityCorrection(double t) double e0 = calcMeanObliquityOfEcliptic(t); double omega = 125.04 - 1934.136 * t; - + return e0 + 0.00256 * Math.Cos(DegToRad(omega)); } @@ -543,7 +543,7 @@ private static void CalculateSunPosition(DateTime dateTime, double latitude, dou //var solarNoonLst = (720.0 - 4 * longitude - eqOfTime + zone * 60.0) / 1440.0; //var sunriseTimeLst = solarNoonLst - haSunRise * 4 / 1440.0; //var sunsetTimeLst = solarNoonLst + haSunRise * 4 / 1440.0; - //var sunlightDurationMins = 8 * haSunRise; + //var sunlightDurationMins = 8 * haSunRise; var trueSolarTime = PutInRange(dateTime.TimeOfDay.TotalMinutes + eqOfTime + 4 * longitude - 60 * zone, 1440); var hourAngle = trueSolarTime / 4.0 < 0 ? trueSolarTime / 4.0 + 180 : trueSolarTime / 4.0 - 180; var solarZenithAngle = RadToDeg(Math.Acos(Math.Sin(DegToRad(latitude)) * Math.Sin(DegToRad(sunDec)) + Math.Cos(DegToRad(latitude)) * Math.Cos(DegToRad(sunDec)) * Math.Cos(DegToRad(hourAngle)))); @@ -636,7 +636,7 @@ public static void CalculateSunPosition(DateTime dateTime, double latitude, doub Math.Sin(latitude * Deg2Rad) * Math.Sin(declination) + Math.Cos(latitude * Deg2Rad) * - Math.Cos(declination) * + Math.Cos(declination) * Math.Cos(hourAngle) ); diff --git a/CumulusMX/Cumulus.cs b/CumulusMX/Cumulus.cs index 8cbe9786..491f1ab6 100644 --- a/CumulusMX/Cumulus.cs +++ b/CumulusMX/Cumulus.cs @@ -445,6 +445,7 @@ public struct TExtraFiles public string AlarmFromEmail; public string[] AlarmDestEmail; public bool AlarmEmailHtml; + public bool AlarmEmailUseBcc; public bool RealtimeIntervalEnabled; // The timer is to be started private int realtimeFTPRetries; // Count of failed realtime FTP attempts @@ -476,6 +477,7 @@ public struct TExtraFiles // OpenWeatherMap settings public WebUploadService OpenWeatherMap = new WebUploadService(); + public string WxnowComment = string.Empty; // MQTT settings public struct MqttSettings @@ -528,9 +530,11 @@ public struct MqttSettings public Alarm HighTempAlarm = new Alarm("High Temperature", AlarmTypes.Above); public Alarm LowTempAlarm = new Alarm("Low Temperature", AlarmTypes.Below); public Alarm UpgradeAlarm = new Alarm("Upgrade Available", AlarmTypes.Trigger); - public Alarm HttpUploadAlarm = new Alarm("HTTP Uploads", AlarmTypes.Trigger); + public Alarm ThirdPartyAlarm = new Alarm("HTTP Uploads", AlarmTypes.Trigger); public Alarm MySqlUploadAlarm = new Alarm("MySQL Uploads", AlarmTypes.Trigger); public Alarm IsRainingAlarm = new Alarm("IsRaining", AlarmTypes.Trigger); + public Alarm NewRecordAlarm = new Alarm("New Record", AlarmTypes.Trigger); + public Alarm FtpAlarm = new Alarm("Web Upload", AlarmTypes.Trigger); private const double DEFAULTFCLOWPRESS = 950.0; @@ -680,11 +684,6 @@ public Cumulus(int HTTPport, bool DebugEnabled, string startParms) Trace.Listeners.Add(myTextListener); Trace.AutoFlush = true; - if (FtpOptions.Logging) - { - CreateFtpLogFile(ftpLogfile); - } - // Read the configuration file LogMessage(" ========================== Cumulus MX starting =========================="); @@ -705,7 +704,7 @@ public Cumulus(int HTTPport, bool DebugEnabled, string startParms) MethodInfo displayName = type.GetMethod("GetDisplayName", BindingFlags.NonPublic | BindingFlags.Static); if (displayName != null) - LogMessage("Mono version: " + displayName.Invoke(null, null)); + LogMessage("Mono version : " + displayName.Invoke(null, null)); } // restrict the threadpool size - for Mono which does not seem to have very good pool management! @@ -715,9 +714,16 @@ public Cumulus(int HTTPport, bool DebugEnabled, string startParms) Platform = IsOSX ? "Mac OS X" : Environment.OSVersion.Platform.ToString(); - LogMessage("Platform: " + Platform); + LogMessage("Platform : " + Platform); - LogMessage("OS version: " + Environment.OSVersion); + try + { + LogMessage("OS Description : " + RuntimeInformation.OSDescription); + } + catch + { + LogMessage("OS Version : " + Environment.OSVersion + " (possibly not accurate)"); + } LogMessage($"Current culture: {CultureInfo.CurrentCulture.DisplayName} [{CultureInfo.CurrentCulture.Name}]"); @@ -1040,9 +1046,16 @@ public Cumulus(int HTTPport, bool DebugEnabled, string startParms) CheckForSingleInstance(boolWindows); if (FtpOptions.FtpMode == FtpProtocols.PHP) + { LogMessage("Maximum concurrent PHP Uploads = " + FtpOptions.MaxConcurrentUploads); + } uploadCountLimitSemaphoreSlim = new SemaphoreSlim(FtpOptions.MaxConcurrentUploads); + if (FtpOptions.Logging) + { + CreateFtpLogFile(ftpLogfile); + } + ListSeparator = CultureInfo.CurrentCulture.TextInfo.ListSeparator; DecimalSeparator = CultureInfo.CurrentCulture.NumberFormat.NumberDecimalSeparator; @@ -1371,9 +1384,11 @@ public Cumulus(int HTTPport, bool DebugEnabled, string startParms) LowTempAlarm.cumulus = this; LowTempAlarm.Units = Units.TempText; UpgradeAlarm.cumulus = this; - HttpUploadAlarm.cumulus = this; + ThirdPartyAlarm.cumulus = this; MySqlUploadAlarm.cumulus = this; IsRainingAlarm.cumulus = this; + NewRecordAlarm.cumulus = this; + FtpAlarm.cumulus = this; GetLatestVersion(); @@ -1631,6 +1646,12 @@ public Cumulus(int HTTPport, bool DebugEnabled, string startParms) InitialiseRG11(); + // Do the start-up MySQL commands before the station is started + if (MySqlSettings.CustomStartUp.Enabled) + { + CustomMySqlStartUp(); + } + if (station.timerStartNeeded) { StartTimersAndSensors(); @@ -1719,7 +1740,7 @@ internal async void TestPhpUploadCompression() } catch (Exception ex) { - LogMessage("TestPhpUploadCompression: Error - " + ex.Message); + LogExceptionMessage(ex, "TestPhpUploadCompression: Error - "); } } } @@ -2134,14 +2155,6 @@ private void RG11StateChange(object sender, SerialPinChangedEventArgs e) } } - private void APRSTimerTick(object sender, ElapsedEventArgs e) - { - if (!string.IsNullOrEmpty(APRS.ID)) - { - station.UpdateAPRS(); - } - } - private void WebTimerTick(object sender, ElapsedEventArgs e) { if (station.DataStopped) @@ -2243,14 +2256,14 @@ internal async void UpdateWunderground(DateTime timestamp) if (!Wund.RapidFireEnabled || Wund.ErrorFlagCount >= 12) { LogMessage("Wunderground: Response = " + response.StatusCode + ": " + responseBodyAsText); - HttpUploadAlarm.LastError = "Wunderground: HTTP response - " + response.StatusCode; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "Wunderground: HTTP response - " + response.StatusCode; + ThirdPartyAlarm.Triggered = true; Wund.ErrorFlagCount = 0; } } else { - HttpUploadAlarm.Triggered = false; + ThirdPartyAlarm.Triggered = false; Wund.ErrorFlagCount = 0; } } @@ -2258,8 +2271,8 @@ internal async void UpdateWunderground(DateTime timestamp) catch (Exception ex) { LogMessage("Wunderground: ERROR - " + ex.Message); - HttpUploadAlarm.LastError = "Wunderground: " + ex.Message; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "Wunderground: " + ex.Message; + ThirdPartyAlarm.Triggered = true; } finally { @@ -2292,20 +2305,20 @@ internal async void UpdateWindy(DateTime timestamp) if (response.StatusCode != HttpStatusCode.OK) { LogMessage("Windy: ERROR - Response = " + response.StatusCode + ": " + responseBodyAsText); - HttpUploadAlarm.LastError = "Windy: HTTP response - " + response.StatusCode; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "Windy: HTTP response - " + response.StatusCode; + ThirdPartyAlarm.Triggered = true; } else { - HttpUploadAlarm.Triggered = false; + ThirdPartyAlarm.Triggered = false; } } } catch (Exception ex) { LogMessage("Windy: ERROR - " + ex.Message); - HttpUploadAlarm.LastError = "Windy: " + ex.Message; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "Windy: " + ex.Message; + ThirdPartyAlarm.Triggered = true; } finally { @@ -2338,20 +2351,20 @@ internal async void UpdateWindGuru(DateTime timestamp) if (response.StatusCode != HttpStatusCode.OK) { LogMessage("WindGuru: ERROR - " + response.StatusCode + ": " + responseBodyAsText); - HttpUploadAlarm.LastError = "WindGuru: HTTP response - " + response.StatusCode; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "WindGuru: HTTP response - " + response.StatusCode; + ThirdPartyAlarm.Triggered = true; } else { - HttpUploadAlarm.Triggered = false; + ThirdPartyAlarm.Triggered = false; } } } catch (Exception ex) { LogMessage("WindGuru: ERROR - " + ex.Message); - HttpUploadAlarm.LastError = "WindGuru: " + ex.Message; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "WindGuru: " + ex.Message; + ThirdPartyAlarm.Triggered = true; } finally { @@ -2390,14 +2403,14 @@ internal async void UpdateAwekas(DateTime timestamp) if (response.StatusCode != HttpStatusCode.OK) { LogMessage($"AWEKAS: ERROR - Response code = {response.StatusCode}, body = {responseBodyAsText}"); - HttpUploadAlarm.LastError = $"AWEKAS: HTTP Response code = {response.StatusCode}, body = {responseBodyAsText}"; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = $"AWEKAS: HTTP Response code = {response.StatusCode}, body = {responseBodyAsText}"; + ThirdPartyAlarm.Triggered = true; AWEKAS.Updating = false; return; } else { - HttpUploadAlarm.Triggered = false; + ThirdPartyAlarm.Triggered = false; } AwekasResponse respJson; @@ -2409,8 +2422,8 @@ internal async void UpdateAwekas(DateTime timestamp) { LogMessage("AWEKAS: Exception deserializing response = " + ex.Message); LogMessage($"AWEKAS: ERROR - Response body = {responseBodyAsText}"); - HttpUploadAlarm.LastError = "AWEKAS deserializing response: " + ex.Message; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "AWEKAS deserializing response: " + ex.Message; + ThirdPartyAlarm.Triggered = true; AWEKAS.Updating = false; return; } @@ -2467,8 +2480,8 @@ internal async void UpdateAwekas(DateTime timestamp) else { LogMessage("AWEKAS: Unknown error"); - HttpUploadAlarm.LastError = "AWEKAS: Unknown error"; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "AWEKAS: Unknown error"; + ThirdPartyAlarm.Triggered = true; } } @@ -2502,8 +2515,8 @@ internal async void UpdateAwekas(DateTime timestamp) catch (Exception ex) { LogMessage("AWEKAS: Exception = " + ex.Message); - HttpUploadAlarm.LastError = "AWEKAS: " + ex.Message; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "AWEKAS: " + ex.Message; + ThirdPartyAlarm.Triggered = true; } finally { @@ -2540,32 +2553,32 @@ internal async void UpdateWCloud(DateTime timestamp) { case 200: msg = "Success"; - HttpUploadAlarm.Triggered = false; + ThirdPartyAlarm.Triggered = false; break; case 400: msg = "Bad request"; - HttpUploadAlarm.LastError = "WeatherCloud: " + msg; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "WeatherCloud: " + msg; + ThirdPartyAlarm.Triggered = true; break; case 401: msg = "Incorrect WID or Key"; - HttpUploadAlarm.LastError = "WeatherCloud: " + msg; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "WeatherCloud: " + msg; + ThirdPartyAlarm.Triggered = true; break; case 429: msg = "Too many requests"; - HttpUploadAlarm.LastError = "WeatherCloud: " + msg; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "WeatherCloud: " + msg; + ThirdPartyAlarm.Triggered = true; break; case 500: msg = "Server error"; - HttpUploadAlarm.LastError = "WeatherCloud: " + msg; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "WeatherCloud: " + msg; + ThirdPartyAlarm.Triggered = true; break; default: msg = "Unknown error"; - HttpUploadAlarm.LastError = "WeatherCloud: " + msg; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "WeatherCloud: " + msg; + ThirdPartyAlarm.Triggered = true; break; } if ((int) response.StatusCode == 200) @@ -2577,8 +2590,8 @@ internal async void UpdateWCloud(DateTime timestamp) catch (Exception ex) { LogMessage("WeatherCloud: ERROR - " + ex.Message); - HttpUploadAlarm.LastError = "WeatherCloud: " + ex.Message; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "WeatherCloud: " + ex.Message; + ThirdPartyAlarm.Triggered = true; } finally { @@ -2615,20 +2628,20 @@ internal async void UpdateOpenWeatherMap(DateTime timestamp) if (response.StatusCode != HttpStatusCode.NoContent) { LogMessage($"OpenWeatherMap: ERROR - Response code = {response.StatusCode}, Response data = {responseBodyAsText}"); - HttpUploadAlarm.LastError = $"OpenWeatherMap: HTTP response - {response.StatusCode}, Response data = {responseBodyAsText}"; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = $"OpenWeatherMap: HTTP response - {response.StatusCode}, Response data = {responseBodyAsText}"; + ThirdPartyAlarm.Triggered = true; } else { - HttpUploadAlarm.Triggered = false; + ThirdPartyAlarm.Triggered = false; } } } catch (Exception ex) { LogMessage("OpenWeatherMap: ERROR - " + ex.Message); - HttpUploadAlarm.LastError = "OpenWeatherMap: " + ex.Message; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "OpenWeatherMap: " + ex.Message; + ThirdPartyAlarm.Triggered = true; } finally { @@ -2831,7 +2844,7 @@ internal void RealtimeTimerTick(object sender, ElapsedEventArgs elapsedEventArgs } catch (Exception ex) { - LogMessage($"Realtime[{cycle}]: Error during realtime upload. Message = {ex.Message}"); + LogExceptionMessage(ex, $"Realtime[{cycle}]: Error during realtime upload."); } RealtimeFtpInProgress = false; } @@ -2880,6 +2893,8 @@ private async void RealtimeFTPReconnect() return; RealtimeFtpReconnecting = true; + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = "Realtime re-connecting"; await Task.Run(() => { bool connected; @@ -4540,6 +4555,8 @@ private void ReadIniFile() WMR928TempChannel = ini.GetValue("Station", "WMR928TempChannel", 0); WMR200TempChannel = ini.GetValue("Station", "WMR200TempChannel", 1); + WxnowComment = ini.GetValue("Station", "WxnowComment.txt", string.Empty); + // WeatherLink Live device settings WllApiKey = ini.GetValue("WLL", "WLv2ApiKey", ""); WllApiSecret = ini.GetValue("WLL", "WLv2ApiSecret", ""); @@ -5346,16 +5363,16 @@ private void ReadIniFile() UpgradeAlarm.Action = ini.GetValue("Alarms", "UpgradeAlarmAction", ""); UpgradeAlarm.ActionParams = ini.GetValue("Alarms", "UpgradeAlarmActionParams", ""); - HttpUploadAlarm.Enabled = ini.GetValue("Alarms", "HttpUploadAlarmSet", false); - HttpUploadAlarm.Sound = ini.GetValue("Alarms", "HttpUploadAlarmSound", false); - HttpUploadAlarm.SoundFile = ini.GetValue("Alarms", "HttpUploadAlarmSoundFile", DefaultSoundFile); - HttpUploadAlarm.Notify = ini.GetValue("Alarms", "HttpUploadAlarmNotify", false); - HttpUploadAlarm.Email = ini.GetValue("Alarms", "HttpUploadAlarmEmail", false); - HttpUploadAlarm.Latch = ini.GetValue("Alarms", "HttpUploadAlarmLatch", false); - HttpUploadAlarm.LatchHours = ini.GetValue("Alarms", "HttpUploadAlarmLatchHours", 24); - HttpUploadAlarm.TriggerThreshold = ini.GetValue("Alarms", "HttpUploadAlarmTriggerCount", 1); - HttpUploadAlarm.Action = ini.GetValue("Alarms", "HttpUploadAlarmAction", ""); - HttpUploadAlarm.ActionParams = ini.GetValue("Alarms", "HttpUploadAlarmActionParams", ""); + ThirdPartyAlarm.Enabled = ini.GetValue("Alarms", "HttpUploadAlarmSet", false); + ThirdPartyAlarm.Sound = ini.GetValue("Alarms", "HttpUploadAlarmSound", false); + ThirdPartyAlarm.SoundFile = ini.GetValue("Alarms", "HttpUploadAlarmSoundFile", DefaultSoundFile); + ThirdPartyAlarm.Notify = ini.GetValue("Alarms", "HttpUploadAlarmNotify", false); + ThirdPartyAlarm.Email = ini.GetValue("Alarms", "HttpUploadAlarmEmail", false); + ThirdPartyAlarm.Latch = ini.GetValue("Alarms", "HttpUploadAlarmLatch", false); + ThirdPartyAlarm.LatchHours = ini.GetValue("Alarms", "HttpUploadAlarmLatchHours", 24); + ThirdPartyAlarm.TriggerThreshold = ini.GetValue("Alarms", "HttpUploadAlarmTriggerCount", 1); + ThirdPartyAlarm.Action = ini.GetValue("Alarms", "HttpUploadAlarmAction", ""); + ThirdPartyAlarm.ActionParams = ini.GetValue("Alarms", "HttpUploadAlarmActionParams", ""); MySqlUploadAlarm.Enabled = ini.GetValue("Alarms", "MySqlUploadAlarmSet", false); MySqlUploadAlarm.Sound = ini.GetValue("Alarms", "MySqlUploadAlarmSound", false); @@ -5368,10 +5385,30 @@ private void ReadIniFile() MySqlUploadAlarm.Action = ini.GetValue("Alarms", "MySqlUploadAlarmAction", ""); MySqlUploadAlarm.ActionParams = ini.GetValue("Alarms", "MySqlUploadAlarmActionParams", ""); + NewRecordAlarm.Enabled = ini.GetValue("Alarms", "NewRecordAlarmSet", true); + NewRecordAlarm.Sound = ini.GetValue("Alarms", "NewRecordAlarmSound", false); + NewRecordAlarm.SoundFile = ini.GetValue("Alarms", "NewRecordAlarmSoundFile", DefaultSoundFile); + NewRecordAlarm.Notify = ini.GetValue("Alarms", "NewRecordAlarmNotify", false); + NewRecordAlarm.Email = ini.GetValue("Alarms", "NewRecordAlarmEmail", false); + NewRecordAlarm.Latch = ini.GetValue("Alarms", "NewRecordAlarmLatch", false); + NewRecordAlarm.LatchHours = ini.GetValue("Alarms", "NewRecordAlarmLatchHours", 24); + NewRecordAlarm.Action = ini.GetValue("Alarms", "NewRecordAlarmAction", ""); + NewRecordAlarm.ActionParams = ini.GetValue("Alarms", "NewRecordAlarmActionParams", ""); + + FtpAlarm.Enabled = ini.GetValue("Alarms", "FtpAlarmSet", false); + FtpAlarm.Sound = ini.GetValue("Alarms", "FtpAlarmSound", false); + FtpAlarm.SoundFile = ini.GetValue("Alarms", "FtpAlarmSoundFile", DefaultSoundFile); + FtpAlarm.Notify = ini.GetValue("Alarms", "FtpAlarmNotify", false); + FtpAlarm.Email = ini.GetValue("Alarms", "FtpAlarmEmail", false); + FtpAlarm.Latch = ini.GetValue("Alarms", "FtpAlarmLatch", false); + FtpAlarm.LatchHours = ini.GetValue("Alarms", "FtpAlarmLatchHours", 24); + FtpAlarm.Action = ini.GetValue("Alarms", "FtpAlarmAction", ""); + FtpAlarm.ActionParams = ini.GetValue("Alarms", "FtpAlarmActionParams", ""); AlarmFromEmail = ini.GetValue("Alarms", "FromEmail", ""); AlarmDestEmail = ini.GetValue("Alarms", "DestEmail", "").Split(';'); AlarmEmailHtml = ini.GetValue("Alarms", "UseHTML", false); + AlarmEmailUseBcc = ini.GetValue("Alarms", "UseBCC", false); Calib.Press.Offset = ini.GetValue("Offsets", "PressOffset", 0.0); Calib.Temp.Offset = ini.GetValue("Offsets", "TempOffset", 0.0); @@ -5642,7 +5679,6 @@ private void ReadIniFile() MySqlSettings.CustomTimed.SetInitialNextInterval(i, DateTime.Now); } - // MySQL - custom roll-over MySqlSettings.CustomRollover.Enabled = ini.GetValue("MySQL", "CustomMySqlRolloverEnabled", false); MySqlSettings.CustomRollover.Commands[0] = ini.GetValue("MySQL", "CustomMySqlRolloverCommandString", ""); @@ -5652,6 +5688,15 @@ private void ReadIniFile() MySqlSettings.CustomRollover.Commands[i] = ini.GetValue("MySQL", "CustomMySqlRolloverCommandString" + i, ""); } + // MySQL - custom start-up + MySqlSettings.CustomStartUp.Enabled = ini.GetValue("MySQL", "CustomMySqlStartUpEnabled", false); + MySqlSettings.CustomStartUp.Commands[0] = ini.GetValue("MySQL", "CustomMySqlStartUpCommandString", ""); + for (var i = 1; i < 10; i++) + { + if (ini.ValueExists("MySQL", "CustomMySqlStartUpCommandString" + i)) + MySqlSettings.CustomStartUp.Commands[i] = ini.GetValue("MySQL", "CustomMySqlStartUpCommandString" + i, ""); + } + // Custom HTTP - seconds CustomHttpSecondsStrings[0] = ini.GetValue("HTTP", "CustomHttpSecondsString", ""); @@ -5988,6 +6033,7 @@ internal void WriteIniFile() ini.SetValue("Station", "WeatherFlowToken", WeatherFlowOptions.WFToken); ini.SetValue("Station", "WeatherFlowDaysHist", WeatherFlowOptions.WFDaysHist); + ini.SetValue("Station", "WxnowComment.txt", WxnowComment); // WeatherLink Live device settings ini.SetValue("WLL", "AutoUpdateIpAddress", WLLAutoUpdateIpAddress); @@ -6507,16 +6553,16 @@ internal void WriteIniFile() ini.SetValue("Alarms", "UpgradeAlarmAction", UpgradeAlarm.Action); ini.SetValue("Alarms", "UpgradeAlarmActionParams", UpgradeAlarm.ActionParams); - ini.SetValue("Alarms", "HttpUploadAlarmSet", HttpUploadAlarm.Enabled); - ini.SetValue("Alarms", "HttpUploadAlarmSound", HttpUploadAlarm.Sound); - ini.SetValue("Alarms", "HttpUploadAlarmSoundFile", HttpUploadAlarm.SoundFile); - ini.SetValue("Alarms", "HttpUploadAlarmNotify", HttpUploadAlarm.Notify); - ini.SetValue("Alarms", "HttpUploadAlarmEmail", HttpUploadAlarm.Email); - ini.SetValue("Alarms", "HttpUploadAlarmLatch", HttpUploadAlarm.Latch); - ini.SetValue("Alarms", "HttpUploadAlarmLatchHours", HttpUploadAlarm.LatchHours); - ini.SetValue("Alarms", "HttpUploadAlarmTriggerCount", HttpUploadAlarm.TriggerThreshold); - ini.SetValue("Alarms", "HttpUploadAlarmAction", HttpUploadAlarm.Action); - ini.SetValue("Alarms", "HttpUploadAlarmActionParams", HttpUploadAlarm.ActionParams); + ini.SetValue("Alarms", "HttpUploadAlarmSet", ThirdPartyAlarm.Enabled); + ini.SetValue("Alarms", "HttpUploadAlarmSound", ThirdPartyAlarm.Sound); + ini.SetValue("Alarms", "HttpUploadAlarmSoundFile", ThirdPartyAlarm.SoundFile); + ini.SetValue("Alarms", "HttpUploadAlarmNotify", ThirdPartyAlarm.Notify); + ini.SetValue("Alarms", "HttpUploadAlarmEmail", ThirdPartyAlarm.Email); + ini.SetValue("Alarms", "HttpUploadAlarmLatch", ThirdPartyAlarm.Latch); + ini.SetValue("Alarms", "HttpUploadAlarmLatchHours", ThirdPartyAlarm.LatchHours); + ini.SetValue("Alarms", "HttpUploadAlarmTriggerCount", ThirdPartyAlarm.TriggerThreshold); + ini.SetValue("Alarms", "HttpUploadAlarmAction", ThirdPartyAlarm.Action); + ini.SetValue("Alarms", "HttpUploadAlarmActionParams", ThirdPartyAlarm.ActionParams); ini.SetValue("Alarms", "MySqlUploadAlarmSet", MySqlUploadAlarm.Enabled); ini.SetValue("Alarms", "MySqlUploadAlarmSound", MySqlUploadAlarm.Sound); @@ -6529,10 +6575,30 @@ internal void WriteIniFile() ini.SetValue("Alarms", "MySqlUploadAlarmAction", MySqlUploadAlarm.Action); ini.SetValue("Alarms", "MySqlUploadAlarmActionParams", MySqlUploadAlarm.ActionParams); + ini.SetValue("Alarms", "NewRecordAlarmSet", NewRecordAlarm.Enabled); + ini.SetValue("Alarms", "NewRecordAlarmSound", NewRecordAlarm.Sound); + ini.SetValue("Alarms", "NewRecordAlarmSoundFile", NewRecordAlarm.SoundFile); + ini.SetValue("Alarms", "NewRecordAlarmNotify", NewRecordAlarm.Notify); + ini.SetValue("Alarms", "NewRecordAlarmEmail", NewRecordAlarm.Email); + ini.SetValue("Alarms", "NewRecordAlarmLatch", NewRecordAlarm.Latch); + ini.SetValue("Alarms", "NewRecordAlarmLatchHours", NewRecordAlarm.LatchHours); + ini.SetValue("Alarms", "NewRecordAlarmAction", NewRecordAlarm.Action); + ini.SetValue("Alarms", "NewRecordAlarmActionParams", NewRecordAlarm.ActionParams); + + ini.SetValue("Alarms", "FtpAlarmSet", FtpAlarm.Enabled); + ini.SetValue("Alarms", "FtpAlarmSound", FtpAlarm.Sound); + ini.SetValue("Alarms", "FtpAlarmSoundFile", FtpAlarm.SoundFile); + ini.SetValue("Alarms", "FtpAlarmNotify", FtpAlarm.Notify); + ini.SetValue("Alarms", "FtpAlarmEmail", FtpAlarm.Email); + ini.SetValue("Alarms", "FtpAlarmLatch", FtpAlarm.Latch); + ini.SetValue("Alarms", "FtpAlarmLatchHours", FtpAlarm.LatchHours); + ini.SetValue("Alarms", "FtpAlarmAction", FtpAlarm.Action); + ini.SetValue("Alarms", "FtpAlarmActionParams", FtpAlarm.ActionParams); + ini.SetValue("Alarms", "FromEmail", AlarmFromEmail); ini.SetValue("Alarms", "DestEmail", AlarmDestEmail.Join(";")); ini.SetValue("Alarms", "UseHTML", AlarmEmailHtml); - + ini.SetValue("Alarms", "UseBCC", AlarmEmailUseBcc); ini.SetValue("Offsets", "PressOffset", Calib.Press.Offset); ini.SetValue("Offsets", "TempOffset", Calib.Temp.Offset); @@ -6771,6 +6837,7 @@ internal void WriteIniFile() ini.SetValue("MySQL", "CustomMySqlSecondsEnabled", MySqlSettings.CustomSecs.Enabled); ini.SetValue("MySQL", "CustomMySqlMinutesEnabled", MySqlSettings.CustomMins.Enabled); ini.SetValue("MySQL", "CustomMySqlRolloverEnabled", MySqlSettings.CustomRollover.Enabled); + ini.SetValue("MySQL", "CustomMySqlStartUpEnabled", MySqlSettings.CustomStartUp.Enabled); ini.SetValue("MySQL", "CustomMySqlSecondsInterval", MySqlSettings.CustomSecs.Interval); ini.SetValue("MySQL", "CustomMySqlMinutesIntervalIndex", CustomMySqlMinutesIntervalIndex); @@ -6778,6 +6845,7 @@ internal void WriteIniFile() ini.SetValue("MySQL", "CustomMySqlSecondsCommandString", MySqlSettings.CustomSecs.Commands[0]); ini.SetValue("MySQL", "CustomMySqlMinutesCommandString", MySqlSettings.CustomMins.Commands[0]); ini.SetValue("MySQL", "CustomMySqlRolloverCommandString", MySqlSettings.CustomRollover.Commands[0]); + ini.SetValue("MySQL", "CustomMySqlStartUpCommandString", MySqlSettings.CustomStartUp.Commands[0]); for (var i = 1; i < 10; i++) { @@ -6795,6 +6863,11 @@ internal void WriteIniFile() ini.DeleteValue("MySQL", "CustomMySqlRolloverCommandString" + i); else ini.SetValue("MySQL", "CustomMySqlRolloverCommandString" + i, MySqlSettings.CustomRollover.Commands[i]); + + if (string.IsNullOrEmpty(MySqlSettings.CustomStartUp.Commands[i])) + ini.DeleteValue("MySQL", "CustomMySqlStartUpCommandString" + i); + else + ini.SetValue("MySQL", "CustomMySqlStartUpCommandString" + i, MySqlSettings.CustomStartUp.Commands[i]); } // MySql - Timed @@ -7096,9 +7169,11 @@ private void ReadStringsFile() BatteryLowAlarm.EmailMsg = ini.GetValue("AlarmEmails", "batteryLow", "A low battery condition has been detected."); SpikeAlarm.EmailMsg = ini.GetValue("AlarmEmails", "dataSpike", "A data spike from your weather station has been suppressed."); UpgradeAlarm.EmailMsg = ini.GetValue("AlarmEmails", "upgrade", "An upgrade to Cumulus MX is now available."); - HttpUploadAlarm.EmailMsg = ini.GetValue("AlarmEmails", "httpStopped", "HTTP uploads are failing."); + ThirdPartyAlarm.EmailMsg = ini.GetValue("AlarmEmails", "httpStopped", "Third party HTTP uploads are failing."); MySqlUploadAlarm.EmailMsg = ini.GetValue("AlarmEmails", "mySqlStopped", "MySQL uploads are failing."); IsRainingAlarm.EmailMsg = ini.GetValue("AlarmEmails", "isRaining", "It has started to rain."); + NewRecordAlarm.EmailMsg = ini.GetValue("AlarmEmails", "newRecord", "A new all-time record has been set."); + FtpAlarm.EmailMsg = ini.GetValue("AlarmEmails", "ftpStopped", "FTP uploads have stopped."); if (!File.Exists("strings.ini")) { @@ -7259,7 +7334,7 @@ public void WriteStringsFile() ini.SetValue("AlarmEmails", "batteryLow", BatteryLowAlarm.EmailMsg); ini.SetValue("AlarmEmails", "dataSpike", SpikeAlarm.EmailMsg); ini.SetValue("AlarmEmails", "upgrade", UpgradeAlarm.EmailMsg); - ini.SetValue("AlarmEmails", "httpStopped", HttpUploadAlarm.EmailMsg); + ini.SetValue("AlarmEmails", "httpStopped", ThirdPartyAlarm.EmailMsg); ini.SetValue("AlarmEmails", "mySqlStopped", MySqlUploadAlarm.EmailMsg); ini.SetValue("AlarmEmails", "isRaining", IsRainingAlarm.EmailMsg); @@ -7798,7 +7873,7 @@ public async void DoLogFile(DateTime timestamp, bool live) sb.Append(station.ET.ToString(ETFormat) + ListSeparator); sb.Append(station.AnnualETTotal.ToString(ETFormat) + ListSeparator); sb.Append(station.ApparentTemperature.ToString(TempFormat) + ListSeparator); - sb.Append(Math.Round(station.CurrentSolarMax) + ListSeparator); + sb.Append(station.CurrentSolarMax + ListSeparator); sb.Append(station.SunshineHours.ToString(SunFormat) + ListSeparator); sb.Append(station.Bearing + ListSeparator); sb.Append(station.RG11RainToday.ToString(RainFormat) + ListSeparator); @@ -7865,7 +7940,7 @@ public async void DoLogFile(DateTime timestamp, bool live) values.Append(station.ET.ToString(ETFormat, InvC) + ","); values.Append(station.AnnualETTotal.ToString(ETFormat, InvC) + ","); values.Append(station.ApparentTemperature.ToString(TempFormat, InvC) + ","); - values.Append((Math.Round(station.CurrentSolarMax)) + ","); + values.Append(station.CurrentSolarMax + ","); values.Append(station.SunshineHours.ToString(SunFormat, InvC) + ","); values.Append(station.Bearing + ","); values.Append(station.RG11RainToday.ToString(RainFormat, InvC) + ","); @@ -8876,7 +8951,6 @@ public int GetHourInc(DateTime timestamp) // Locale is currently on Daylight time return -10; } - else { // Locale is currently on Standard time or unknown @@ -9016,6 +9090,7 @@ public void Stop() { LogMessage("No data read this session, today.ini not written"); } + station.SaveWindData(); } catch { } } @@ -9791,6 +9866,9 @@ public async Task DoIntervalUpload() { LogFtpMessage($"SFTP[Int]: Error connecting SFTP - {ex.Message}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = "Error connecting SFTP - " + ex.Message; + if ((uint) ex.HResult == 0x80004005) // Could not resolve host { // Disable the DNS cache for the next query @@ -9823,6 +9901,8 @@ public async Task DoIntervalUpload() catch (Exception e) { LogFtpMessage($"SFTP[Int]: Error uploading file - {e.Message}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = "Error uploading NOAA report file - " + e.Message; } NOAAconf.NeedFtp = false; } @@ -9870,11 +9950,15 @@ public async Task DoIntervalUpload() { LogFtpMessage($"SFTP[Int]: Error uploading Extra web file #{i} [{uploadfile}]"); LogFtpMessage($"SFTP[Int]: Error = {e.Message}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading Extra web file #{i} [{uploadfile}"; } } else { LogFtpMessage($"SFTP[Int]: Extra web file #{i} [{uploadfile}] not found!"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error Extra web file #{i} [{uploadfile} not found"; } } } @@ -9914,6 +9998,8 @@ public async Task DoIntervalUpload() { LogFtpMessage($"SFTP[Int]: Error uploading standard data file [{StdWebFiles[i].RemoteFileName}]"); LogFtpMessage($"SFTP[Int]: Error = {e}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading standard web file {StdWebFiles[i].RemoteFileName} - {e.Message}"; } } } @@ -9946,6 +10032,8 @@ public async Task DoIntervalUpload() { LogFtpMessage($"SFTP[Int]: Error uploading graph data file [{uploadfile}]"); LogFtpMessage($"SFTP[Int]: Error = {e}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading graph data file [{uploadfile}] - {e.Message}"; } } } @@ -9973,6 +10061,8 @@ public async Task DoIntervalUpload() { LogFtpMessage($"SFTP[Int]: Error uploading daily graph data file [{uploadfile}]"); LogFtpMessage($"SFTP[Int]: Error = {e}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading daily graph data file [{uploadfile}] - {e.Message}"; } } } @@ -9990,6 +10080,8 @@ public async Task DoIntervalUpload() catch (Exception e) { LogMessage($"SFTP[Int]: Error uploading moon image - {e.Message}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading moon image - {e.Message}"; } } } @@ -10068,6 +10160,9 @@ public async Task DoIntervalUpload() { LogFtpMessage("FTP[Int]: Error connecting ftp - " + ex.Message); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = "Error connecting ftp - " + ex.Message; + if (ex.InnerException != null) { ex = Utils.GetOriginalException(ex); @@ -10106,6 +10201,8 @@ public async Task DoIntervalUpload() catch (Exception e) { LogFtpMessage($"FTP[Int]: Error uploading NOAA files: {e.Message}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = "Error connecting ftp - " + e.Message; } NOAAconf.NeedFtp = false; } @@ -10154,6 +10251,8 @@ public async Task DoIntervalUpload() catch (Exception e) { LogFtpMessage($"FTP[Int]: Error uploading file {uploadfile}: {e.Message}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading extra file {uploadfile} - {e.Message}"; } } else @@ -10199,6 +10298,8 @@ public async Task DoIntervalUpload() catch (Exception e) { LogFtpMessage($"FTP[Int]: Error uploading file {StdWebFiles[i].RemoteFileName}: {e}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading file {StdWebFiles[i].RemoteFileName} - {e.Message}"; } } } @@ -10230,6 +10331,8 @@ public async Task DoIntervalUpload() { LogFtpMessage($"FTP[Int]: Error uploading graph data file [{GraphDataFiles[i].RemoteFileName}]"); LogFtpMessage($"FTP[Int]: Error = {e}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading file {GraphDataFiles[i].RemoteFileName} - {e.Message}"; } } } @@ -10258,6 +10361,8 @@ public async Task DoIntervalUpload() { LogFtpMessage($"FTP[Int]: Error uploading daily graph data file [{GraphDataEodFiles[i].RemoteFileName}]"); LogFtpMessage($"FTP[Int]: Error = {e}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading file {GraphDataEodFiles[i].RemoteFileName} - {e.Message}"; } } } @@ -10275,6 +10380,8 @@ public async Task DoIntervalUpload() catch (Exception e) { LogMessage($"FTP[Int]: Error uploading moon image - {e.Message}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading moon image - {e.Message}"; } } } @@ -10332,6 +10439,8 @@ public async Task DoIntervalUpload() catch (Exception ex) { LogExceptionMessage(ex, $"PHP[Int]: Error uploading NOAA files"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading NOAA files - {ex.Message}"; } finally { @@ -10389,6 +10498,8 @@ public async Task DoIntervalUpload() catch (Exception ex) { LogExceptionMessage(ex, $"PHP[Int]: Error uploading NOAA Year file"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading NOAA files - {ex.Message}"; } finally { @@ -10477,6 +10588,8 @@ public async Task DoIntervalUpload() catch (Exception ex) when (!(ex is TaskCanceledException)) { LogExceptionMessage(ex, $"PHP[Int]: Error uploading file {uploadfile} to: {remotefile}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading file {uploadfile} to: {remotefile} - {ex.Message}"; } finally { @@ -10565,6 +10678,8 @@ public async Task DoIntervalUpload() catch (Exception ex) { LogExceptionMessage(ex, $"PHP[Int]: Error uploading file {item.RemoteFileName}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading file {item.RemoteFileName} - {ex.Message}"; } finally { @@ -10654,6 +10769,8 @@ public async Task DoIntervalUpload() catch (Exception ex) { LogExceptionMessage(ex, $"PHP[Int]: Error uploading graph data file [{item.RemoteFileName}]"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading graph data file [{item.RemoteFileName}] - {ex.Message}"; } finally { @@ -10730,6 +10847,8 @@ public async Task DoIntervalUpload() catch (Exception ex) { LogExceptionMessage(ex, $"PHP[Int]: Error uploading daily graph data file [{item.RemoteFileName}]"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading daily graph data file [{item.RemoteFileName}] - {ex.Message}"; } finally { @@ -10794,6 +10913,8 @@ public async Task DoIntervalUpload() catch (Exception ex) { LogExceptionMessage(ex, "PHP[Int]: Error uploading moon image"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading moon image - {ex.Message}"; } finally { @@ -10829,7 +10950,9 @@ public async Task DoIntervalUpload() } catch(Exception ex) { - LogExceptionMessage(ex, "PHP[Int]: Eror waiting on upload tasks"); + LogExceptionMessage(ex, "PHP[Int]: Error waiting on upload tasks"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = "Error waiting on upload tasks"; } } //LogDebugMessage($"PHP[Int]: EOD Graph files upload complete, {tasklist.Count()} files processed"); @@ -10862,6 +10985,8 @@ private bool UploadFile(FtpClient conn, string localfile, string remotefile, int if (!File.Exists(localfile)) { LogMessage($"FTP[{cycleStr}]: Error! Local file not found, aborting upload: {localfile}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error! Local file not found, aborting upload: {localfile}"; return true; } @@ -10873,6 +10998,9 @@ private bool UploadFile(FtpClient conn, string localfile, string remotefile, int catch (Exception ex) { LogFtpMessage($"FTP[{cycleStr}]: Error reading {localfile} - {ex.Message}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error reading {localfile} - {ex.Message}"; + if (ex.InnerException != null) { LogFtpMessage($"FTP[{cycleStr}]: Inner Exception: {ex.GetBaseException().Message}"); @@ -10892,6 +11020,9 @@ private bool UploadStream(FtpClient conn, string remotefile, Stream dataStream, if (dataStream.Length == 0) { LogMessage($"FTP[{cycleStr}]: The data is empty - skipping upload of {remotefile}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"The data is empty - skipping upload of {remotefile}"; + return true; } @@ -10929,6 +11060,10 @@ private bool UploadStream(FtpClient conn, string remotefile, Stream dataStream, catch (Exception ex) { LogFtpMessage($"FTP[{cycleStr}]: Error deleting {remotefile} : {ex.Message}"); + + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error deleting {remotefile} : {ex.Message}"; + if (ex.InnerException != null) { ex = Utils.GetOriginalException(ex); @@ -10960,6 +11095,10 @@ private bool UploadStream(FtpClient conn, string remotefile, Stream dataStream, catch (Exception ex) { LogFtpMessage($"FTP[{cycleStr}]: Error renaming {remotefiletmp} to {remotefile} : {ex.Message}"); + + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error renaming {remotefiletmp} to {remotefile} : {ex.Message}"; + if (ex.InnerException != null) { ex = Utils.GetOriginalException(ex); @@ -10973,6 +11112,10 @@ private bool UploadStream(FtpClient conn, string remotefile, Stream dataStream, catch (Exception ex) { LogFtpMessage($"FTP[{cycleStr}]: Error uploading {remotefile} : {ex.Message}"); + + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading {remotefile} : {ex.Message}"; + if (ex.InnerException != null) { LogFtpMessage($"FTP[{cycleStr}]: Inner Exception: {ex.GetBaseException().Message}"); @@ -11001,6 +11144,9 @@ private bool UploadFile(SftpClient conn, string localfile, string remotefile, in if (!File.Exists(localfile)) { LogMessage($"SFTP[{cycleStr}]: Error! Local file not found, aborting upload: {localfile}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error! Local file not found, aborting upload: {localfile}"; + return true; } @@ -11009,14 +11155,22 @@ private bool UploadFile(SftpClient conn, string localfile, string remotefile, in if (conn == null || !conn.IsConnected) { LogFtpMessage($"SFTP[{cycleStr}]: The SFTP object is null or not connected - skipping upload of {localfile}"); - RealtimeFTPReconnect(); + + if (cycle >= 0) + RealtimeFTPReconnect(); + return false; } } catch (ObjectDisposedException) { LogFtpMessage($"SFTP[{cycleStr}]: The SFTP object is disposed - skipping upload of {localfile}"); - RealtimeFTPReconnect(); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"The SFTP object is disposed - skipping upload of {localfile}"; + + if (cycle >=0) + RealtimeFTPReconnect(); + return false; } @@ -11030,6 +11184,10 @@ private bool UploadFile(SftpClient conn, string localfile, string remotefile, in catch (Exception ex) { LogFtpMessage($"SFTP[{cycleStr}]: Error reading {localfile} - {ex.Message}"); + + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error reading {localfile} - {ex.Message}"; + if (ex.InnerException != null) { ex = Utils.GetOriginalException(ex); @@ -11048,6 +11206,8 @@ private bool UploadStream(SftpClient conn, string remotefile, Stream dataStream, if (dataStream.Length == 0) { LogFtpMessage($"SFTP[{cycleStr}]: The data is empty - skipping upload of {remotefile}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"The data is empty - skipping upload of {remotefile}"; return false; } @@ -11056,14 +11216,25 @@ private bool UploadStream(SftpClient conn, string remotefile, Stream dataStream, if (conn == null || !conn.IsConnected) { LogFtpMessage($"SFTP[{cycleStr}]: The SFTP object is null or not connected - skipping upload of {remotefile}"); - RealtimeFTPReconnect(); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"The SFTP object is null or not connected - skipping upload of {remotefile}"; + + if (cycle >= 0) + RealtimeFTPReconnect(); + return false; } } catch (ObjectDisposedException) { LogFtpMessage($"SFTP[{cycleStr}]: The SFTP object is disposed - skipping upload of {remotefile}"); - RealtimeFTPReconnect(); + + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"The SFTP object is disposed - skipping upload of {remotefile}"; + + if (cycle >= 0) + RealtimeFTPReconnect(); + return false; } @@ -11083,12 +11254,17 @@ private bool UploadStream(SftpClient conn, string remotefile, Stream dataStream, catch (ObjectDisposedException) { LogFtpMessage($"SFTP[{cycleStr}]: The SFTP object is disposed"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"The SFTP object is disposed - skipping upload of {remotefile}"; return false; } catch (Exception ex) { LogFtpMessage($"SFTP[{cycleStr}]: Error uploading {remotefilename} : {ex.Message}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading {remotefilename} : {ex.Message}"; + if (ex.Message.Contains("Permission denied")) // Non-fatal return true; @@ -11115,11 +11291,17 @@ private bool UploadStream(SftpClient conn, string remotefile, Stream dataStream, catch (ObjectDisposedException) { LogFtpMessage($"SFTP[{cycleStr}]: The SFTP object is disposed"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"The SFTP object is disposed during renaming of {remotefile}"; return false; } catch (Exception ex) { LogFtpMessage($"SFTP[{cycleStr}]: Error renaming {remotefilename} to {remotefile} : {ex.Message}"); + + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error renaming {remotefilename} to {remotefile} : {ex.Message}"; + if (ex.InnerException != null) { ex = Utils.GetOriginalException(ex); @@ -11134,11 +11316,17 @@ private bool UploadStream(SftpClient conn, string remotefile, Stream dataStream, catch (ObjectDisposedException) { LogFtpMessage($"SFTP[{cycleStr}]: The SFTP object is disposed"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = "The SFTP object is disposed"; return false; } catch (Exception ex) { LogFtpMessage($"SFTP[{cycleStr}]: Error uploading {remotefile} - {ex.Message}"); + + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error uploading {remotefile} - {ex.Message}"; + if (ex.InnerException != null) { ex = Utils.GetOriginalException(ex); @@ -11162,6 +11350,10 @@ private async Task UploadFile(HttpClient httpclient, string localfile, str if (!File.Exists(localfile)) { LogMessage($"PHP[{cycleStr}]: Error! Local file not found, aborting upload: {localfile}"); + + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $"Error! Local file not found, aborting upload: {localfile}"; + return false; } @@ -11183,6 +11375,10 @@ private async Task UploadFile(HttpClient httpclient, string localfile, str catch (Exception ex) { LogDebugMessage($"PHP[{cycleStr}]: Error - {ex.Message}"); + + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $" Error - {ex.Message}"; + return false; } } @@ -11194,6 +11390,8 @@ private async Task UploadString(HttpClient httpclient, bool incremental, s if (string.IsNullOrEmpty(data)) { LogMessage($"PHP[{cycleStr}]: Uploading to {remotefile}. Error: The data string is empty, ignoring this upload"); + + return false; } LogDebugMessage($"PHP[{cycleStr}]: Uploading to {remotefile}"); @@ -11229,7 +11427,7 @@ private async Task UploadString(HttpClient httpclient, bool incremental, s // Compress? if supported and payload exceeds 500 bytes if (data.Length < 500 || FtpOptions.PhpCompression == "none") { - request.Content = new StringContent(data, encoding, "application/octet-stream"); + request.Content = new StringContent(data, encoding, "text/plain"); } else { @@ -11258,6 +11456,7 @@ private async Task UploadString(HttpClient httpclient, bool incremental, s outStream = new MemoryStream(compressed); streamContent = new StreamContent(outStream); + streamContent.Headers.ContentType = new System.Net.Http.Headers.MediaTypeHeaderValue("text/plain"); streamContent.Headers.Add("Content-Encoding", FtpOptions.PhpCompression); streamContent.Headers.ContentLength = outStream.Length; @@ -11280,19 +11479,23 @@ private async Task UploadString(HttpClient httpclient, bool incremental, s LogDataMessage($"PHP[{cycleStr}]: Upload to {remotefile}: Response text follows:\n{responseBodyAsText}"); } - if (outStream != null) - outStream.Dispose(); + if (outStream != null) + outStream.Dispose(); - if (streamContent != null) - streamContent.Dispose(); + if (streamContent != null) + streamContent.Dispose(); - return response.StatusCode == HttpStatusCode.OK; + return response.StatusCode == HttpStatusCode.OK; } } } catch (System.Net.Http.HttpRequestException ex) { LogExceptionMessage(ex, $"PHP[{cycleStr}]: Error uploading to {remotefile}"); + + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $" Error uploading to {remotefile} - {ex.Message}"; + retry++; if (retry < 2) { @@ -11302,6 +11505,8 @@ private async Task UploadString(HttpClient httpclient, bool incremental, s catch (Exception ex) { LogExceptionMessage(ex, $"PHP[{cycleStr}]: Error uploading to {remotefile}"); + FtpAlarm.Triggered = true; + FtpAlarm.LastMessage = $" Error uploading to {remotefile} - {ex.Message}"; retry = 99; } finally @@ -11369,7 +11574,11 @@ public void LogFluentFtpMessage(FtpTraceLevel level, string message) } catch (Exception ex) { + LogExceptionMessage(ex, $"LogFluentFtpMessage: Error"); + // Let's try closing and the existing log file and reopening LogDebugMessage($"LogFluentFtpMessage: Error = {ex.Message}"); + ftpLogfile = RemoveOldDiagsFiles("FTP"); + CreateFtpLogFile(ftpLogfile); } } } @@ -11640,7 +11849,7 @@ public void MySqlRealtimeFile(int cycle, bool live, DateTime? logdate = null) values.Append((CloudBaseInFeet ? "ft" : "m") + "',"); values.Append(station.ApparentTemperature.ToString(TempFormat, InvC) + ','); values.Append(station.SunshineHours.ToString(SunFormat, InvC) + ','); - values.Append(((int)Math.Round(station.CurrentSolarMax)).ToString() + ",'"); + values.Append(station.CurrentSolarMax + ",'"); values.Append((station.IsSunny ? "1" : "0") + "',"); values.Append(station.FeelsLike.ToString(TempFormat, InvC)); values.Append(')'); @@ -12081,6 +12290,30 @@ internal async void CustomMySqlTimedUpdate(DateTime now) } } + internal void CustomMySqlStartUp() + { + LogMessage("Starting custom start-up MySQL commands"); + + var tokenParser = new TokenParser(TokenParserOnToken); + + for (var i = 0; i < 10; i++) + { + try + { + if (!string.IsNullOrEmpty(MySqlSettings.CustomStartUp.Commands[i])) + { + tokenParser.InputText = MySqlSettings.CustomStartUp.Commands[i]; + MySqlCommandSync(tokenParser.ToStringFromString(), "CustomMySqlStartUp"); + } + } + catch (Exception ex) + { + LogExceptionMessage(ex, $"CustomSqlStartUp[{i}]: Error excuting: {MySqlSettings.CustomStartUp.Commands[i]} "); + } + } + LogMessage("Custom start-up MySQL commands end"); + } + public async Task CheckMySQLFailedUploads(string callingFunction, string cmd) { await CheckMySQLFailedUploads(callingFunction, new List() { cmd }); @@ -12184,11 +12417,20 @@ public void DoExtraEndOfDayFiles() LogDebugMessage($"EOD: Copying extra file {uploadfile} to {remotefile}"); try { - File.Copy(uploadfile, remotefile, true); + if (ExtraFiles[i].process) + { + var data = ProcessTemplateFile2String(uploadfile, false, ExtraFiles[i].UTF8); + File.WriteAllText(remotefile, data); + } + else + { + // just copy the file + File.Copy(uploadfile, remotefile, true); + } } catch (Exception ex) { - LogDebugMessage($"EOD: Error copying extra file {uploadfile} to {remotefile}: {ex.Message}"); + LogExceptionMessage(ex, $"EOD: Error copying extra file {uploadfile} to {remotefile}"); } //LogDebugMessage("Finished copying extra file " + uploadfile); } @@ -12545,21 +12787,21 @@ public async void UpdatePWSweather(DateTime timestamp) if (response.StatusCode != HttpStatusCode.OK) { LogMessage($"PWS Response: ERROR - Response code = {response.StatusCode}, Body = {responseBodyAsText}"); - HttpUploadAlarm.LastError = $"PWS: HTTP Response code = {response.StatusCode}, Body = {responseBodyAsText}"; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = $"PWS: HTTP Response code = {response.StatusCode}, Body = {responseBodyAsText}"; + ThirdPartyAlarm.Triggered = true; } else { LogDebugMessage("PWS Response: " + response.StatusCode + ": " + responseBodyAsText); - HttpUploadAlarm.Triggered = false; + ThirdPartyAlarm.Triggered = false; } } } catch (Exception ex) { LogMessage("PWS update: " + ex.Message); - HttpUploadAlarm.LastError = "PWS: " + ex.Message; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "PWS: " + ex.Message; + ThirdPartyAlarm.Triggered = true; } finally { @@ -12590,21 +12832,21 @@ public async void UpdateWOW(DateTime timestamp) if (response.StatusCode != HttpStatusCode.OK) { LogMessage($"WOW Response: ERROR - Response code = {response.StatusCode}, body = {responseBodyAsText}"); - HttpUploadAlarm.LastError = $"WOW: HTTP response - Response code = {response.StatusCode}, body = {responseBodyAsText}"; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = $"WOW: HTTP response - Response code = {response.StatusCode}, body = {responseBodyAsText}"; + ThirdPartyAlarm.Triggered = true; } else { LogDebugMessage("WOW Response: " + response.StatusCode + ": " + responseBodyAsText); - HttpUploadAlarm.Triggered = false; + ThirdPartyAlarm.Triggered = false; } } } catch (Exception ex) { LogMessage("WOW update: " + ex.Message); - HttpUploadAlarm.LastError = "WOW: " + ex.Message; - HttpUploadAlarm.Triggered = true; + ThirdPartyAlarm.LastMessage = "WOW: " + ex.Message; + ThirdPartyAlarm.Triggered = true; } finally { @@ -12699,7 +12941,7 @@ await Task.Run(() => } - MySqlUploadAlarm.LastError = ex.Message; + MySqlUploadAlarm.LastMessage = ex.Message; MySqlUploadAlarm.Triggered = true; if (MySqlSettings.BufferOnfailure && !UseFailedList) @@ -12787,7 +13029,7 @@ public void MySqlCommandSync(ConcurrentQueue Cmds, string CallingFunct LogMessage($"{CallingFunction}: SQL = {cachedCmd}"); } - MySqlUploadAlarm.LastError = ex.Message; + MySqlUploadAlarm.LastMessage = ex.Message; MySqlUploadAlarm.Triggered = true; // do we save this command/commands on failure to be resubmitted? @@ -12882,7 +13124,7 @@ public async void GetLatestVersion() var msg = $"You are not running the latest version of Cumulus MX, build {LatestBuild} is available."; LogConsoleMessage(msg, ConsoleColor.Cyan); LogMessage(msg); - UpgradeAlarm.LastError = $"Build {LatestBuild} is available"; + UpgradeAlarm.LastMessage = $"Build {LatestBuild} is available"; UpgradeAlarm.Triggered = true; } else if (int.Parse(Build) == int.Parse(LatestBuild)) @@ -13834,6 +14076,8 @@ public class MySqlGeneralSettings public MySqlTableSettings CustomMins { get; set; } public MySqlTableSettings CustomRollover { get; set; } public MySqlTableTimedSettings CustomTimed { get; set; } + public MySqlTableSettings CustomStartUp { get; set; } + public MySqlGeneralSettings() { @@ -13844,6 +14088,7 @@ public MySqlGeneralSettings() CustomMins = new MySqlTableSettings(); CustomRollover = new MySqlTableSettings(); CustomTimed = new MySqlTableTimedSettings(); + CustomStartUp = new MySqlTableSettings(); CustomSecs.Commands = new string[10]; CustomMins.Commands = new string[10]; @@ -13852,6 +14097,7 @@ public MySqlGeneralSettings() CustomTimed.Intervals = new int[10]; CustomTimed.StartTimes = new TimeSpan[10]; CustomTimed.NextUpdate = new DateTime[10]; + CustomStartUp.Commands = new string[10]; } } diff --git a/CumulusMX/CumulusMX.csproj b/CumulusMX/CumulusMX.csproj index f41518f9..5cacc453 100644 --- a/CumulusMX/CumulusMX.csproj +++ b/CumulusMX/CumulusMX.csproj @@ -49,14 +49,14 @@ AnyCPU - none + pdbonly true bin\Release\ TRACE prompt 4 ".pdb"="" - false + true false @@ -233,25 +233,25 @@ 3.5.2 - 46.0.2 + 47.1.0 2.1.0 - 3.6.0 + 4.1.0 - 4.1.4.563 + 4.2.1.781 - 2.2.5 + 2.2.7 2.2.5 - 6.7.0 + 6.10.0 2020.0.2 @@ -265,10 +265,22 @@ - echo Starting post-build tasks + echo. +echo Starting post-build tasks +echo Copy Updates.txt xcopy "$(ProjectDir)..\Updates.txt" "$(TargetDir)\Updates.txt" /D /-I /Q /Y +echo copy sqlite 32 xcopy "$(ProjectDir)\Libs\sqlite3-x86.dll" "$(TargetDir)\x86\sqlite3.dll" /D /-I /Q /Y -xcopy "$(ProjectDir)\Libs\sqlite3-x64.dll" "$(TargetDir)\x64\sqlite3.dll" /D /-I /Q /Y +echo copy sqlite 64 +xcopy "$(ProjectDir)\Libs\sqlite3-x64.dll" "$(TargetDir)\x64\sqlite3.dll" /D /-I /Q /Y +echo. +echo Update Distribution folder +echo copy MX exe +xcopy "$(TargetPath)" "$(SolutionDir)..\CumulusMX-Dist\CumulusMX" /D /-I /Q /Y +echo copy MX config +xcopy "$(TargetDir)CumulusMX.exe.config" "$(SolutionDir)..\CumulusMX-Dist\CumulusMX" /D /-I /Q /Y + +