From e0ef31c25e7f9b21ee3bae53167f2c7851b94748 Mon Sep 17 00:00:00 2001 From: Roy Ben-Shabat Date: Thu, 28 Nov 2019 13:16:26 +0200 Subject: Completed PPC Backup/Restore !!! --- .../Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) (limited to 'Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs') diff --git a/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs b/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs index b7573ec60..d312609bb 100644 --- a/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs +++ b/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs @@ -284,13 +284,20 @@ namespace Tango.PPC.Common.MachineUpdate var tfpPath = Path.Combine(_newPackageTempFolder, "firmware_package.tfp"); var stream = new FileStream(tfpPath, FileMode.Open); - if (setupFPGA) + if (!_machineProvider.Machine.IsDemo) { - op.FirmwareUpgradeMode = FirmwareUpgradeModes.DFU | FirmwareUpgradeModes.TFP_PACKAGE; + if (setupFPGA) + { + op.FirmwareUpgradeMode = FirmwareUpgradeModes.DFU | FirmwareUpgradeModes.TFP_PACKAGE; + } + else + { + op.FirmwareUpgradeMode = FirmwareUpgradeModes.DFU; + } } else { - op.FirmwareUpgradeMode = FirmwareUpgradeModes.DFU; + op.FirmwareUpgradeMode = FirmwareUpgradeModes.TFP_PACKAGE; } var handler = await op.UpgradeFirmware(stream); -- cgit v1.3.1 From e6e91a5c5435e524876d44d91b92c90f990a60c7 Mon Sep 17 00:00:00 2001 From: Roy Ben-Shabat Date: Thu, 28 Nov 2019 16:53:09 +0200 Subject: Implemented setup and update notifications from PPC to service. --- .../MachineSetup/MachineSetupManager.cs | 66 ++++- .../MachineUpdate/MachineUpdateManager.cs | 274 ++++++++++++++------- .../PPC/Tango.PPC.Common/Web/PPCWebClientBase.cs | 9 + 3 files changed, 246 insertions(+), 103 deletions(-) (limited to 'Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs') diff --git a/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineSetup/MachineSetupManager.cs b/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineSetup/MachineSetupManager.cs index 29c5bc6a2..537e652e6 100644 --- a/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineSetup/MachineSetupManager.cs +++ b/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineSetup/MachineSetupManager.cs @@ -99,6 +99,51 @@ namespace Tango.PPC.Common.MachineSetup }); } + private async void OnFailed(Exception ex, TaskCompletionSource completionSource, MachineSetupResponse response) + { + LogManager.Log(ex, "An error occurred in machine setup."); + + completionSource.SetException(ex); + + if (response != null) + { + try + { + var result = await _client.NotifyUpdateCompleted(new MachineUpdateCompletedRequest() + { + Token = response.NotifyCompletedToken, + Status = BL.Enumerations.TangoUpdateStatuses.SetupFailed, + FailedReason = ex.FlattenMessage(), + }); + } + catch (Exception xx) + { + LogManager.Log(xx, "Error notifying setup completed."); + } + } + } + + private async void OnCompleted(MachineSetupResult result, TaskCompletionSource completionSource, MachineSetupResponse response) + { + completionSource.SetResult(result); + + if (response != null) + { + try + { + var r = await _client.NotifyUpdateCompleted(new MachineUpdateCompletedRequest() + { + Token = response.NotifyCompletedToken, + Status = BL.Enumerations.TangoUpdateStatuses.SetupCompleted, + }); + } + catch (Exception xx) + { + LogManager.Log(xx, "Error notifying setup completed."); + } + } + } + #endregion #region Public Methods @@ -113,6 +158,8 @@ namespace Tango.PPC.Common.MachineSetup { TaskCompletionSource result = new TaskCompletionSource(); + MachineSetupResponse setup_response = null; + try { LogManager.Log($"Starting machine setup for serial number {serialNumber}..."); @@ -135,8 +182,6 @@ namespace Tango.PPC.Common.MachineSetup request.DeviceID = await _windows_manager.GetDeviceId(); request.DeviceName = await _windows_manager.GetDeviceName(); - MachineSetupResponse setup_response = null; - try { LogManager.Log($"Sending setup request...\n{request.ToJsonString()}"); @@ -180,7 +225,7 @@ namespace Tango.PPC.Common.MachineSetup { LogManager.Log("Installing remote assistance..."); UpdateProgress("Installing remote assistance", "Installing..."); - await _remoteAssistance.InstallRemoteAssistance(serialNumber,settings.DeploymentSlot.ToString()); + await _remoteAssistance.InstallRemoteAssistance(serialNumber, settings.DeploymentSlot.ToString()); } if (setup_response.SetupUWF) @@ -324,21 +369,21 @@ namespace Tango.PPC.Common.MachineSetup handler.Failed += (_, ex) => { stream.Dispose(); - result.SetException(ex); + OnFailed(ex, result, setup_response); }; handler.Completed += (_, __) => { UpdateProgress("Updating Firmware", "Firmware update completed successfully."); stream.Dispose(); - result.SetResult(new MachineSetupResult() + OnCompleted(new MachineSetupResult() { UpdatePackagePath = _newPackageTempFolder, - }); + }, result, setup_response); }; handler.Canceled += (_, __) => { stream.Dispose(); - result.SetException(new Exception("The operation has been canceled.")); + OnFailed(new Exception("The operation has been canceled."), result, setup_response); }; handler.Progress += (_, e) => { @@ -347,16 +392,15 @@ namespace Tango.PPC.Common.MachineSetup } else { - result.SetResult(new MachineSetupResult() + OnCompleted(new MachineSetupResult() { UpdatePackagePath = _newPackageTempFolder, - }); + }, result, setup_response); } } catch (Exception ex) { - LogManager.Log(ex, "An error occurred in machine setup."); - result.SetException(ex); + OnFailed(ex, result, setup_response); } return await result.Task; diff --git a/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs b/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs index d312609bb..591a1293d 100644 --- a/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs +++ b/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs @@ -84,6 +84,124 @@ namespace Tango.PPC.Common.MachineUpdate }); } + private async void OnFailed(Exception ex, TaskCompletionSource completionSource, DownloadUpdateResponse response, bool performDatabaseRollback, String dbBackupFile, Tango.Core.DataSource localDataSource) + { + LogManager.Log(ex, "An error occurred in machine update."); + + if (performDatabaseRollback) + { + LogManager.Log("Rolling back database changes..."); + + using (DbManager db = DbManager.FromDataSource(localDataSource)) + { + try + { + UpdateProgress("Rollback", "Rolling back database changes..."); + await Task.Factory.StartNew(() => db.Restore(localDataSource.Catalog, dbBackupFile)); + LogManager.Log("Database restored successfully."); + } + catch (Exception e) + { + LogManager.Log(e, "Could not rollback the database."); + throw ex; + } + finally + { + try + { + File.Delete(dbBackupFile); + } + catch { } + } + } + } + + completionSource.SetException(ex); + + if (response != null) + { + try + { + var result = await _client.NotifyUpdateCompleted(new MachineUpdateCompletedRequest() + { + Token = response.NotifyCompletedToken, + Status = BL.Enumerations.TangoUpdateStatuses.UpdateFailed, + FailedReason = ex.FlattenMessage(), + }); + } + catch (Exception xx) + { + LogManager.Log(xx, "Error notifying update completed."); + } + } + } + + private async void OnCompleted(MachineUpdateResult result, TaskCompletionSource completionSource, DownloadUpdateResponse response, String dbBackupFile) + { + try + { + File.Delete(dbBackupFile); + } + catch { } + + completionSource.SetResult(result); + + if (response != null) + { + try + { + var r = await _client.NotifyUpdateCompleted(new MachineUpdateCompletedRequest() + { + Token = response.NotifyCompletedToken, + Status = BL.Enumerations.TangoUpdateStatuses.UpdateCompleted, + }); + } + catch (Exception ex) + { + LogManager.Log(ex, "Error notifying update completed."); + } + } + } + + private async void OnCompleted(UpdateDBResponse response) + { + if (response != null) + { + try + { + var r = await _client.NotifyUpdateCompleted(new MachineUpdateCompletedRequest() + { + Token = response.NotifyCompletedToken, + Status = BL.Enumerations.TangoUpdateStatuses.DatabaseCompleted, + }); + } + catch (Exception ex) + { + LogManager.Log(ex, "Error notifying update completed."); + } + } + } + + private async void OnFailed(Exception ex, UpdateDBResponse response) + { + if (response != null) + { + try + { + var r = await _client.NotifyUpdateCompleted(new MachineUpdateCompletedRequest() + { + Token = response.NotifyCompletedToken, + Status = BL.Enumerations.TangoUpdateStatuses.DatabaseFailed, + FailedReason = ex.FlattenMessage(), + }); + } + catch (Exception xx) + { + LogManager.Log(xx, "Error notifying update completed."); + } + } + } + #endregion #region Public Methods @@ -108,6 +226,7 @@ namespace Tango.PPC.Common.MachineUpdate var localDataSource = SettingsManager.Default.GetOrCreate().DataSource; bool performDatabaseRollback = false; String dbBackupFile = null; + DownloadUpdateResponse update_response = null; try { @@ -148,8 +267,6 @@ namespace Tango.PPC.Common.MachineUpdate DownloadUpdateRequest request = new DownloadUpdateRequest(); request.SerialNumber = serialNumber; - DownloadUpdateResponse update_response = null; - update_response = await _client.MachineUpdate(request); LogManager.Log($"Machine update response received: {Environment.NewLine}{update_response.ToJsonString()}"); @@ -304,21 +421,21 @@ namespace Tango.PPC.Common.MachineUpdate handler.Failed += (_, ex) => { stream.Dispose(); - throw ex; + OnFailed(ex, result, update_response, performDatabaseRollback, dbBackupFile, localDataSource); }; handler.Completed += (_, __) => { UpdateProgress("Updating Firmware", "Firmware update completed successfully."); stream.Dispose(); - result.SetResult(new MachineUpdateResult() + OnCompleted(new MachineUpdateResult() { UpdatePackagePath = _newPackageTempFolder, - }); + }, result, update_response, dbBackupFile); }; handler.Canceled += (_, __) => { stream.Dispose(); - throw new Exception("The operation has been canceled."); + OnFailed(new Exception("The operation has been canceled."), result, update_response, performDatabaseRollback, dbBackupFile, localDataSource); }; handler.Progress += (_, e) => { @@ -327,53 +444,15 @@ namespace Tango.PPC.Common.MachineUpdate } else { - result.SetResult(new MachineUpdateResult() + OnCompleted(new MachineUpdateResult() { UpdatePackagePath = _newPackageTempFolder, - }); + }, result, update_response, dbBackupFile); } } catch (Exception ex) { - LogManager.Log(ex, "An error occurred in machine update."); - - if (performDatabaseRollback) - { - LogManager.Log("Rolling back database changes..."); - - using (DbManager db = DbManager.FromDataSource(localDataSource)) - { - try - { - UpdateProgress("Rollback", "Rolling back database changes..."); - await Task.Factory.StartNew(() => db.Restore(localDataSource.Catalog, dbBackupFile)); - LogManager.Log("Database restored successfully."); - } - catch (Exception e) - { - LogManager.Log(e, "Could not rollback the database."); - throw ex; - } - finally - { - try - { - File.Delete(dbBackupFile); - } - catch { } - } - } - } - - result.SetException(ex); - } - finally - { - try - { - File.Delete(dbBackupFile); - } - catch { } + OnFailed(ex, result, update_response, performDatabaseRollback, dbBackupFile, localDataSource); } return await result.Task; @@ -421,73 +500,84 @@ namespace Tango.PPC.Common.MachineUpdate { return Task.Factory.StartNew(() => { - LogManager.Log("Starting database update..."); + UpdateDBResponse update_response = null; - UpdateProgress("Updating Database", "Initializing..."); + try + { + LogManager.Log("Starting database update..."); - LogManager.Log("Looking for update scripts configuration on application path..."); + UpdateProgress("Updating Database", "Initializing..."); - String config_file = Path.Combine(PathHelper.GetStartupPath(), "Update Scripts", "config.xml"); + LogManager.Log("Looking for update scripts configuration on application path..."); - if (!File.Exists(config_file)) - { - throw LogManager.Log(new FileNotFoundException($"Could not locate '{config_file}' file on application folder.")); - } + String config_file = Path.Combine(PathHelper.GetStartupPath(), "Update Scripts", "config.xml"); - UpdateDBResponse update_response = dbCompareResult.UpdateDBResponse; - - var localDataSource = SettingsManager.Default.GetOrCreate().DataSource; + if (!File.Exists(config_file)) + { + throw LogManager.Log(new FileNotFoundException($"Could not locate '{config_file}' file on application folder.")); + } - LogManager.Log($"Updating database '{update_response.DataSource.ToString()}' => '{localDataSource.ToString()}'..."); + update_response = dbCompareResult.UpdateDBResponse; - UpdateProgress("Updating Database", "Initializing update sequence..."); + var localDataSource = SettingsManager.Default.GetOrCreate().DataSource; - ExaminerSequenceConfiguration config_sequence = ExaminerSequenceConfiguration.FromFile(config_file); + LogManager.Log($"Updating database '{update_response.DataSource.ToString()}' => '{localDataSource.ToString()}'..."); - foreach (var item in config_sequence.Items.Where(x => x.Type == ExaminerSequenceItemType.Data || update_response.PerformSchemaUpdate).OrderBy(x => x.Index)) - { - LogManager.Log($"Executing update script '{item.FileName}...'"); + UpdateProgress("Updating Database", "Initializing update sequence..."); - ExaminerConfigurationBuilder builder = new ExaminerConfigurationBuilder(Path.Combine(Path.GetDirectoryName(config_file), item.FileName)); - builder.SetSource(update_response.DataSource); - builder.SetTarget(localDataSource); + ExaminerSequenceConfiguration config_sequence = ExaminerSequenceConfiguration.FromFile(config_file); - if (item.RequiresSerialNumber) + foreach (var item in config_sequence.Items.Where(x => x.Type == ExaminerSequenceItemType.Data || update_response.PerformSchemaUpdate).OrderBy(x => x.Index)) { - builder.SetMachineSerialNumber(serialNumber); - } + LogManager.Log($"Executing update script '{item.FileName}...'"); - builder.Synchronize(); + ExaminerConfigurationBuilder builder = new ExaminerConfigurationBuilder(Path.Combine(Path.GetDirectoryName(config_file), item.FileName)); + builder.SetSource(update_response.DataSource); + builder.SetTarget(localDataSource); - var config = builder.Build(); + if (item.RequiresSerialNumber) + { + builder.SetMachineSerialNumber(serialNumber); + } - ExaminerProcess process = new ExaminerProcess(config, item.Type == ExaminerSequenceItemType.Data ? ExaminerProcessType.Data : ExaminerProcessType.Schema); - process.Progress += (x, msg) => - { - LogManager.Log(msg); - }; + builder.Synchronize(); - try - { - UpdateProgress("Updating Database", item.Name + "..."); + var config = builder.Build(); - var result = process.Execute().Result; + ExaminerProcess process = new ExaminerProcess(config, item.Type == ExaminerSequenceItemType.Data ? ExaminerProcessType.Data : ExaminerProcessType.Schema); + process.Progress += (x, msg) => + { + LogManager.Log(msg); + }; - if (result.ExitCode != ExaminerProcessExitCode.Success) + try { - throw LogManager.Log(new InvalidDataException($"{item.FileName} script has terminated with exit code '{result.ExitCode}'.")); - } + UpdateProgress("Updating Database", item.Name + "..."); - LogManager.Log("Script executed successfully."); - } - catch (Exception ex) - { - throw LogManager.Log(ex, "Setup manager error while trying to update the database."); + var result = process.Execute().Result; + + if (result.ExitCode != ExaminerProcessExitCode.Success) + { + throw LogManager.Log(new InvalidDataException($"{item.FileName} script has terminated with exit code '{result.ExitCode}'.")); + } + + LogManager.Log("Script executed successfully."); + } + catch (Exception ex) + { + throw LogManager.Log(ex, "Setup manager error while trying to update the database."); + } } - } - UpdateProgress("Updating Database", "Database synchronization completed successfully."); - LogManager.Log("Update completed successfully."); + UpdateProgress("Updating Database", "Database synchronization completed successfully."); + LogManager.Log("Update completed successfully."); + OnCompleted(update_response); + } + catch (Exception ex) + { + OnFailed(ex, update_response); + throw; + } }); } diff --git a/Software/Visual_Studio/PPC/Tango.PPC.Common/Web/PPCWebClientBase.cs b/Software/Visual_Studio/PPC/Tango.PPC.Common/Web/PPCWebClientBase.cs index 2df343241..5520f8b5a 100644 --- a/Software/Visual_Studio/PPC/Tango.PPC.Common/Web/PPCWebClientBase.cs +++ b/Software/Visual_Studio/PPC/Tango.PPC.Common/Web/PPCWebClientBase.cs @@ -58,6 +58,15 @@ namespace Tango.PPC.Common.Web return Post("MachineUpdate", request); } + /// + /// Executes the NotifyUpdateCompleted action and returns Tango.PPC.Common.Web.MachineUpdateCompletedResponse. + /// + /// + public Task NotifyUpdateCompleted(Tango.PPC.Common.Web.MachineUpdateCompletedRequest request) + { + return Post("NotifyUpdateCompleted", request); + } + /// /// Executes the CheckForUpdates action and returns Tango.PPC.Common.Web.CheckForUpdateResponse. /// -- cgit v1.3.1 From 363138a9a1e653b8e76b01f8e3b76319f1752e5c Mon Sep 17 00:00:00 2001 From: Roy Ben Shabat Date: Tue, 3 Dec 2019 12:55:53 +0200 Subject: Implemented db rollback for db only update. Improved db rollback for PPC update. Changed device reset to use Stub insead of DFU. --- .../ViewModels/SystemViewVM.cs | 2 +- .../MachineUpdate/MachineUpdateManager.cs | 124 +++++++++++++++------ 2 files changed, 92 insertions(+), 34 deletions(-) (limited to 'Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs') diff --git a/Software/Visual_Studio/PPC/Modules/Tango.PPC.Technician/ViewModels/SystemViewVM.cs b/Software/Visual_Studio/PPC/Modules/Tango.PPC.Technician/ViewModels/SystemViewVM.cs index 9ce3e11d9..b46e566d1 100644 --- a/Software/Visual_Studio/PPC/Modules/Tango.PPC.Technician/ViewModels/SystemViewVM.cs +++ b/Software/Visual_Studio/PPC/Modules/Tango.PPC.Technician/ViewModels/SystemViewVM.cs @@ -102,7 +102,7 @@ namespace Tango.PPC.Technician.ViewModels { _resettingDevice = true; ResetDeviceCommand.RaiseCanExecuteChanged(); - await MachineProvider.MachineOperator.ResetDFU(); + await MachineProvider.MachineOperator.Reset(); await NotificationProvider.ShowInfo("Embedded device has been reset successfully."); } catch (Exception ex) diff --git a/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs b/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs index 591a1293d..dacd1b69a 100644 --- a/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs +++ b/Software/Visual_Studio/PPC/Tango.PPC.Common/MachineUpdate/MachineUpdateManager.cs @@ -131,7 +131,7 @@ namespace Tango.PPC.Common.MachineUpdate } catch (Exception xx) { - LogManager.Log(xx, "Error notifying update completed."); + LogManager.Log(xx, "Error notifying update failed."); } } } @@ -163,41 +163,71 @@ namespace Tango.PPC.Common.MachineUpdate } } - private async void OnCompleted(UpdateDBResponse response) + private void OnCompleted(UpdateDBResponse response) { if (response != null) { try { - var r = await _client.NotifyUpdateCompleted(new MachineUpdateCompletedRequest() + var r = _client.NotifyUpdateCompleted(new MachineUpdateCompletedRequest() { Token = response.NotifyCompletedToken, Status = BL.Enumerations.TangoUpdateStatuses.DatabaseCompleted, - }); + }).Result; } catch (Exception ex) { - LogManager.Log(ex, "Error notifying update completed."); + LogManager.Log(ex, "Error notifying database completed."); } } } - private async void OnFailed(Exception ex, UpdateDBResponse response) + private void OnFailed(Exception ex, UpdateDBResponse response, bool performDatabaseRollback, String dbBackupFile, Tango.Core.DataSource localDataSource) { + LogManager.Log(ex, "An error occurred in database update."); + + if (performDatabaseRollback) + { + LogManager.Log("Rolling back database changes..."); + + using (DbManager db = DbManager.FromDataSource(localDataSource)) + { + try + { + UpdateProgress("Rollback", "Rolling back database changes..."); + db.Restore(localDataSource.Catalog, dbBackupFile); + LogManager.Log("Database restored successfully."); + } + catch (Exception e) + { + LogManager.Log(e, "Could not rollback the database."); + throw ex; + } + finally + { + try + { + File.Delete(dbBackupFile); + } + catch { } + } + } + } + if (response != null) { try { - var r = await _client.NotifyUpdateCompleted(new MachineUpdateCompletedRequest() + var r = _client.NotifyUpdateCompleted(new MachineUpdateCompletedRequest() { Token = response.NotifyCompletedToken, Status = BL.Enumerations.TangoUpdateStatuses.DatabaseFailed, FailedReason = ex.FlattenMessage(), - }); + }).Result; } catch (Exception xx) { - LogManager.Log(xx, "Error notifying update completed."); + LogManager.Log(xx, "Error notifying database failed."); } } } @@ -329,24 +359,23 @@ namespace Tango.PPC.Common.MachineUpdate throw new InvalidProgramException("Database tango does not exists."); } - if (setupFirmware) - { - LogManager.Log("Setup firmware is active so a database rollback procedure should be configured."); - UpdateProgress("Updating Database", "Creating database backup..."); + UpdateProgress("Updating Database", "Creating database backup..."); - try - { - Directory.CreateDirectory("C:\\Backups"); - dbBackupFile = $"C:\\Backups\\{Path.GetRandomFileName()}.bak"; - LogManager.Log($"Creating database backup to '{dbBackupFile}'..."); - await Task.Factory.StartNew(() => db.Backup(localDataSource.Catalog, dbBackupFile)); - LogManager.Log("Database backup created successfully."); - } - catch (Exception ex) - { - throw LogManager.Log(ex, "Setup manager error while trying to create a database backup."); - } + //Create Database Backup + try + { + Directory.CreateDirectory("C:\\Backups"); + dbBackupFile = $"C:\\Backups\\{Path.GetRandomFileName()}.bak"; + LogManager.Log($"Creating database backup to '{dbBackupFile}'..."); + await Task.Factory.StartNew(() => db.Backup(localDataSource.Catalog, dbBackupFile)); + performDatabaseRollback = true; + LogManager.Log("Database backup created successfully."); } + catch (Exception ex) + { + throw LogManager.Log(ex, "Update manager error while trying to create a database backup."); + } + LogManager.Log("Disposing database manager."); db.Dispose(); @@ -384,14 +413,12 @@ namespace Tango.PPC.Common.MachineUpdate } catch (Exception ex) { - throw LogManager.Log(ex, "Setup manager error while trying to synchronize database."); + throw LogManager.Log(ex, "Update manager error while trying to synchronize database."); } //Updating firmware if (setupFirmware) { - performDatabaseRollback = true; - UpdateProgress("Updating Firmware", "Connecting to firmware device..."); LogManager.Log(""); LogManager.Log("-------------------------------------------------------------------------"); @@ -501,6 +528,9 @@ namespace Tango.PPC.Common.MachineUpdate return Task.Factory.StartNew(() => { UpdateDBResponse update_response = null; + var localDataSource = SettingsManager.Default.GetOrCreate().DataSource; + bool performDatabaseRollback = false; + String dbBackupFile = null; try { @@ -519,14 +549,42 @@ namespace Tango.PPC.Common.MachineUpdate update_response = dbCompareResult.UpdateDBResponse; - var localDataSource = SettingsManager.Default.GetOrCreate().DataSource; - LogManager.Log($"Updating database '{update_response.DataSource.ToString()}' => '{localDataSource.ToString()}'..."); UpdateProgress("Updating Database", "Initializing update sequence..."); ExaminerSequenceConfiguration config_sequence = ExaminerSequenceConfiguration.FromFile(config_file); + UpdateProgress("Updating Database", "Connecting to local database..."); + LogManager.Log("Initializing database manager..."); + DbManager db = DbManager.FromDataSource(localDataSource); + + LogManager.Log("Checking Tango database exists on the local machine..."); + if (!db.Exists(localDataSource.Catalog)) + { + throw new InvalidProgramException("Database tango does not exists."); + } + + UpdateProgress("Updating Database", "Creating database backup..."); + + //Create Database Backup + try + { + Directory.CreateDirectory("C:\\Backups"); + dbBackupFile = $"C:\\Backups\\{Path.GetRandomFileName()}.bak"; + LogManager.Log($"Creating database backup to '{dbBackupFile}'..."); + db.Backup(localDataSource.Catalog, dbBackupFile); + performDatabaseRollback = true; + LogManager.Log("Database backup created successfully."); + } + catch (Exception ex) + { + throw LogManager.Log(ex, "Update manager error while trying to create a database backup."); + } + + LogManager.Log("Disposing database manager."); + db.Dispose(); + foreach (var item in config_sequence.Items.Where(x => x.Type == ExaminerSequenceItemType.Data || update_response.PerformSchemaUpdate).OrderBy(x => x.Index)) { LogManager.Log($"Executing update script '{item.FileName}...'"); @@ -565,7 +623,7 @@ namespace Tango.PPC.Common.MachineUpdate } catch (Exception ex) { - throw LogManager.Log(ex, "Setup manager error while trying to update the database."); + throw LogManager.Log(ex, "Upudate manager error while trying to update the database."); } } @@ -575,8 +633,8 @@ namespace Tango.PPC.Common.MachineUpdate } catch (Exception ex) { - OnFailed(ex, update_response); - throw; + OnFailed(ex, update_response, performDatabaseRollback, dbBackupFile, localDataSource); + throw ex; } }); } -- cgit v1.3.1