Skip to content

Commit 93948e4

Browse files
Merge pull request #540 from erikdarlingdata/fix/installer-data-loss-538
Fix installer dropping database on every upgrade
2 parents 3df331a + cfd7d6e commit 93948e4

3 files changed

Lines changed: 51 additions & 8 deletions

File tree

Installer/Program.cs

Lines changed: 30 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -103,6 +103,7 @@ SQL command timeout constants (in seconds)
103103
private const int ShortTimeoutSeconds = 60; // Quick operations (cleanup, queries)
104104
private const int MediumTimeoutSeconds = 120; // Dependency installation
105105
private const int LongTimeoutSeconds = 300; // SQL file execution (5 minutes)
106+
private const int UpgradeTimeoutSeconds = 3600; // Upgrade data migrations (1 hour, large tables)
106107

107108
/*
108109
Exit codes for granular error reporting
@@ -117,6 +118,7 @@ private static class ExitCodes
117118
public const int VersionCheckFailed = 5;
118119
public const int SqlFilesNotFound = 6;
119120
public const int UninstallFailed = 7;
121+
public const int UpgradesFailed = 8;
120122
}
121123

122124
static async Task<int> Main(string[] args)
@@ -523,8 +525,9 @@ Search current directory and up to 5 parent directories
523525
string fileName = Path.GetFileName(f);
524526
if (!SqlFileNamePattern.IsMatch(fileName))
525527
return false;
526-
/*Exclude test and troubleshooting scripts from main install*/
527-
if (fileName.StartsWith("97_", StringComparison.Ordinal) ||
528+
/*Exclude uninstall, test, and troubleshooting scripts from main install*/
529+
if (fileName.StartsWith("00_", StringComparison.Ordinal) ||
530+
fileName.StartsWith("97_", StringComparison.Ordinal) ||
528531
fileName.StartsWith("99_", StringComparison.Ordinal))
529532
return false;
530533
return true;
@@ -699,6 +702,21 @@ Traces are server-level and persist after database drops
699702

700703
Console.WriteLine();
701704
Console.WriteLine($"Upgrades complete: {upgradeSuccessCount} succeeded, {upgradeFailureCount} failed");
705+
706+
/*Abort if any upgrade scripts failed — proceeding would reinstall over a partially-upgraded database*/
707+
if (upgradeFailureCount > 0)
708+
{
709+
Console.WriteLine();
710+
Console.WriteLine("================================================================================");
711+
Console.WriteLine("Installation aborted: upgrade scripts must succeed before installation can proceed.");
712+
Console.WriteLine("Fix the errors above and re-run the installer.");
713+
Console.WriteLine("================================================================================");
714+
if (!automatedMode)
715+
{
716+
WaitForExit();
717+
}
718+
return ExitCodes.UpgradesFailed;
719+
}
702720
}
703721
else
704722
{
@@ -1332,7 +1350,15 @@ FROM PerformanceMonitor.config.installation_history
13321350
return version.ToString();
13331351
}
13341352

1335-
return null;
1353+
/*
1354+
Fallback: database and history table exist but no SUCCESS rows.
1355+
This can happen if a prior GUI install didn't write history (#538/#539).
1356+
Return "1.0.0" so all idempotent upgrade scripts are attempted
1357+
rather than treating this as a fresh install (which would drop the database).
1358+
*/
1359+
Console.WriteLine("Warning: PerformanceMonitor database exists but installation_history has no records.");
1360+
Console.WriteLine("Treating as v1.0.0 to apply all available upgrades.");
1361+
return "1.0.0";
13361362
}
13371363
}
13381364
catch (SqlException ex)
@@ -1480,7 +1506,7 @@ Execute an upgrade folder
14801506

14811507
using (var cmd = new SqlCommand(trimmedBatch, connection))
14821508
{
1483-
cmd.CommandTimeout = LongTimeoutSeconds;
1509+
cmd.CommandTimeout = UpgradeTimeoutSeconds;
14841510
try
14851511
{
14861512
await cmd.ExecuteNonQueryAsync().ConfigureAwait(false);

InstallerGui/MainWindow.xaml.cs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -408,6 +408,16 @@ private async void Install_Click(object sender, RoutedEventArgs e)
408408
upgradeFailure == 0 ? "Success" : "Warning");
409409
LogMessage("", "Info");
410410
}
411+
412+
/*Abort if any upgrade scripts failed — proceeding would reinstall over a partially-upgraded database*/
413+
if (upgradeFailure > 0)
414+
{
415+
LogMessage("", "Info");
416+
LogMessage("Installation aborted: upgrade scripts must succeed before installation can proceed.", "Error");
417+
LogMessage("Fix the errors above and re-run the installer.", "Error");
418+
SetUIState(installing: false);
419+
return;
420+
}
411421
}
412422

413423
/*

InstallerGui/Services/InstallationService.cs

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -238,8 +238,9 @@ public static (string? SqlDirectory, string? MonitorRootDirectory, List<string>
238238
/*Match numbered SQL files but exclude 97 (tests) and 99 (troubleshooting)*/
239239
if (!SqlFilePattern.IsMatch(fileName))
240240
return false;
241-
/*Exclude test and troubleshooting scripts from main install*/
242-
if (fileName.StartsWith("97_", StringComparison.Ordinal) ||
241+
/*Exclude uninstall, test, and troubleshooting scripts from main install*/
242+
if (fileName.StartsWith("00_", StringComparison.Ordinal) ||
243+
fileName.StartsWith("97_", StringComparison.Ordinal) ||
243244
fileName.StartsWith("99_", StringComparison.Ordinal))
244245
return false;
245246
return true;
@@ -1113,7 +1114,13 @@ FROM PerformanceMonitor.config.installation_history
11131114
return version.ToString();
11141115
}
11151116

1116-
return null;
1117+
/*
1118+
Fallback: database and history table exist but no SUCCESS rows.
1119+
This can happen if a prior GUI install didn't write history (#538/#539).
1120+
Return "1.0.0" so all idempotent upgrade scripts are attempted
1121+
rather than treating this as a fresh install (which would drop the database).
1122+
*/
1123+
return "1.0.0";
11171124
}
11181125
catch (SqlException)
11191126
{
@@ -1272,7 +1279,7 @@ Parse versions and filter to only applicable upgrades
12721279
continue;
12731280

12741281
using var cmd = new SqlCommand(trimmedBatch, connection);
1275-
cmd.CommandTimeout = 300;
1282+
cmd.CommandTimeout = 3600; /*1 hour — upgrade migrations on large tables need extended time*/
12761283

12771284
try
12781285
{

0 commit comments

Comments
 (0)