/// <summary> /// Runs each installer on every VM in specified by config file /// </summary> /// <returns>List of all the results from the RemoteInstalls</returns> public List <ResultsGroup> Run() { STPStartInfo poolStartInfo = new STPStartInfo(); List <IWorkItemResult <IList <IList <ResultsGroup> > > > poolResults = new List <IWorkItemResult <IList <IList <ResultsGroup> > > >(); // build parallelizable tasks ParallelizableRemoteInstallDriverTaskCollections ptasks = new ParallelizableRemoteInstallDriverTaskCollections(); if (_configuration.VirtualMachines.Count == 0) { throw new InvalidConfigurationException("Missing virtual machines in configuration."); } // build the sequence that is going to be run foreach (VirtualMachineConfig vm in _configuration.VirtualMachines) { DriverTaskCollection tasks = new DriverTaskCollection(); if (vm.Snapshots.Count == 0) { throw new InvalidConfigurationException(string.Format("Missing snapshots in {0}. Define a 'current' snapshot with <snapshot name='*' />.", vm.Name)); } switch (_configuration.Installers.Sequence) { case InstallersSequence.alternate: tasks.Add(new DriverTasks.DriverTask_Alternate(_configuration, _logpath, _simulationOnly, vm, _configuration.Installers, true, true)); break; case InstallersSequence.install: tasks.Add(new DriverTasks.DriverTask_Alternate(_configuration, _logpath, _simulationOnly, vm, _configuration.Installers, true, false)); break; case InstallersSequence.uninstall: tasks.Add(new DriverTasks.DriverTask_Alternate(_configuration, _logpath, _simulationOnly, vm, _configuration.Installers, false, true)); break; case InstallersSequence.fifo: tasks.Add(new DriverTasks.DriverTask_Fifo(_configuration, _logpath, _simulationOnly, vm, _configuration.Installers)); break; case InstallersSequence.lifo: tasks.Add(new DriverTasks.DriverTask_Lifo(_configuration, _logpath, _simulationOnly, vm, _configuration.Installers)); break; case InstallersSequence.clean: default: tasks.Add(new DriverTasks.DriverTask_Clean(_configuration, _logpath, _simulationOnly, vm, _configuration.Installers)); break; } ptasks.Add(tasks); } // the number of threads in the pipeline is either user-defined // or the number of virtual machines (default) if (_pipelineCount > 0) { poolStartInfo.MaxWorkerThreads = _pipelineCount; } else { poolStartInfo.MaxWorkerThreads = ptasks.Count; } if (ptasks.Count == 0) { throw new InvalidConfigurationException("Number of tasks cannot be zero."); } ConsoleOutput.WriteLine(string.Format("Starting {0} parallel installation(s) ({1} max) ...", poolStartInfo.MaxWorkerThreads, ptasks.Count)); SmartThreadPool pool = new SmartThreadPool(poolStartInfo); ConsoleOutput.ShowThreadID = (poolStartInfo.MaxWorkerThreads > 1); foreach (DriverTaskCollections tasks in ptasks) { poolResults.Add(pool.QueueWorkItem <DriverTaskCollections, IList <IList <ResultsGroup> > >( RunTasks, tasks)); } // wait for the pool to finish all the work SmartThreadPool.WaitAll(poolResults.ToArray()); // collect results List <ResultsGroup> groups = new List <ResultsGroup>(); foreach (IWorkItemResult <IList <IList <ResultsGroup> > > poolResult in poolResults) { foreach (IList <ResultsGroup> poolResultItem in poolResult.GetResult()) { groups.AddRange(poolResultItem); } } ConsoleOutput.WriteLine("Finished installation(s) with {0} result(s)", groups.Count); return(groups); }
/// <summary> /// Execute a file from a remote vm. /// </summary> private TaskResult Execute(SnapshotTaskConfig snapshotConfig) { TaskResult snapshotTaskResult = new TaskResult(); snapshotTaskResult.CmdLine = string.Format("Snapshot: {0} '{1}'", snapshotConfig.Command, snapshotConfig.Name); snapshotTaskResult.Name = snapshotConfig.Name; try { ConsoleOutput.WriteLine(snapshotTaskResult.CmdLine); if (!_installInstance.SimulationOnly) { switch (snapshotConfig.Command) { case SnapshotCommand.create: _installInstance.VirtualMachine.Snapshots.CreateSnapshot( snapshotConfig.Name, snapshotConfig.Description, snapshotConfig.IncludeMemory ? Constants.VIX_SNAPSHOT_INCLUDE_MEMORY : 0, VMWareInterop.Timeouts.CreateSnapshotTimeout); break; case SnapshotCommand.remove: _installInstance.VirtualMachine.Snapshots.RemoveSnapshot( snapshotConfig.Name); break; case SnapshotCommand.removeifexists: VMWareSnapshot snapshot = _installInstance.VirtualMachine.Snapshots.FindSnapshotByName( snapshotConfig.Name); if (snapshot != null) { ConsoleOutput.WriteLine("Removing {0}", snapshotTaskResult.CmdLine); snapshot.RemoveSnapshot(); } else { ConsoleOutput.WriteLine("No {0}", snapshotTaskResult.CmdLine); } break; case SnapshotCommand.revert: _installInstance.VirtualMachine.Snapshots.FindSnapshotByName( snapshotConfig.Name).RevertToSnapshot(Constants.VIX_VMPOWEROP_SUPPRESS_SNAPSHOT_POWERON); break; default: throw new Exception(string.Format("Unsupported command '{0}'", snapshotConfig.Command)); } ConsoleOutput.WriteLine(string.Format("Finished {0}", snapshotTaskResult.CmdLine)); } } catch (Exception ex) { snapshotTaskResult.LastError = ex.Message; snapshotTaskResult.Success = false; ConsoleOutput.WriteLine(ex); } return(snapshotTaskResult); }
/// <summary> /// Install/uninstall MSI /// </summary> /// <returns></returns> public Result InstallUninstall(InstanceOptions options) { ConsoleOutput.WriteLine("Running 'Remote:{0}', '{1}'", _installerConfig.Name, _installerConfig.DestinationPath); // remote logfiles string install_logfile = string.Empty; string uninstall_logfile = string.Empty; // the remote install result Result result = new Result( _installerConfig.Name, _installerConfig.SvnRevision); if (!Directory.Exists(LogPath)) { ConsoleOutput.WriteLine("Creating directory '{0}'", LogPath); Directory.CreateDirectory(LogPath); } ConsoleOutput.WriteLine("Saving logs in '{0}'", LogPath); SequenceDrivers additionalSequences = new SequenceDrivers(); ExecuteDriver executeDriver = new ExecuteDriver(this); executeDriver.Add(_config.Tasks); executeDriver.Add(_config.VirtualMachines.Tasks); executeDriver.Add(_vmConfig.Tasks); executeDriver.Add(_vmConfig.Snapshots.Tasks); executeDriver.Add(_snapshotConfig.Tasks); executeDriver.Add(_config.Installers.Tasks); executeDriver.Add(_installerConfig.Tasks); additionalSequences.Add(executeDriver); CopyFilesDriver copyFilesDriver = new CopyFilesDriver(this); copyFilesDriver.Add(_config.CopyFiles); copyFilesDriver.Add(_config.VirtualMachines.CopyFiles); copyFilesDriver.Add(_vmConfig.CopyFiles); copyFilesDriver.Add(_vmConfig.Snapshots.CopyFiles); copyFilesDriver.Add(_snapshotConfig.CopyFiles); copyFilesDriver.Add(_config.Installers.CopyFiles); copyFilesDriver.Add(_installerConfig.CopyFiles); additionalSequences.Add(copyFilesDriver); // execute and copy files before all result.AddRange(additionalSequences.ExecuteSequence( SequenceWhen.beforeall)); DateTime start = DateTime.UtcNow; try { // execute the installers try { VirtualMachineDeployment deploy = null; if (!_simulationOnly) { deploy = _installerConfig.CreateDeployment(_vm); } // install if (options.Install) { // execute and copy files before install result.AddRange(additionalSequences.ExecuteSequence( SequenceWhen.beforeinstall)); ConsoleOutput.WriteLine("Installing 'Remote:{0}', '{1}'", _installerConfig.Name, _installerConfig.DestinationPath); result.SuccessfulInstall = InstallResult.False; if (!_simulationOnly) { deploy.Install(out install_logfile); } result.SuccessfulInstall = InstallResult.True; result.AddRange(additionalSequences.ExecuteSequence( SequenceWhen.aftersuccessfulinstall)); } // uninstall if (options.Uninstall) { // execute and copy files before uninstall result.AddRange(additionalSequences.ExecuteSequence( SequenceWhen.beforeuninstall)); DateTime startUnInstall = DateTime.UtcNow; ConsoleOutput.WriteLine("Uninstalling 'Remote:{0}', '{1}'", _installerConfig.Name, _installerConfig.DestinationPath); result.SuccessfulUnInstall = InstallResult.False; if (!_simulationOnly) { deploy.UnInstall(out uninstall_logfile); } result.SuccessfulUnInstall = InstallResult.True; result.AddRange(additionalSequences.ExecuteSequence( SequenceWhen.aftersuccessfuluninstall)); } if (!_simulationOnly && deploy != null && deploy.IsRebootRequired()) { ConsoleOutput.WriteLine("Reboot required after 'Remote:{0}'", _installerConfig.Name); result.RebootRequired = true; } } catch (Exception ex) { result.LastError = ex.Message; result.Success = false; ConsoleOutput.WriteLine(ex); result.AddRange(additionalSequences.ExecuteSequence( SequenceWhen.afterfailedinstalluninstall)); } } finally { result.Duration = DateTime.UtcNow.Subtract(start); ConsoleOutput.WriteLine("Done after '{0}'", result.Duration); } result.AddRange(additionalSequences.ExecuteSequence( SequenceWhen.afterall)); // copy the remote logfiles back if (!string.IsNullOrEmpty(install_logfile)) { string target_install_logfile = Path.Combine(LogPath, Path.GetFileName(install_logfile)); ConsoleOutput.WriteLine("Collecting 'Remote:{0}' => '{1}'", install_logfile, target_install_logfile); _vm.CopyFileFromGuestToHost(install_logfile, target_install_logfile); result.InstallLogfile = Path.Combine(ShortLogPath, Path.GetFileName(install_logfile)); } if (!string.IsNullOrEmpty(uninstall_logfile)) { string target_uninstall_logfile = Path.Combine(LogPath, Path.GetFileName(uninstall_logfile)); ConsoleOutput.WriteLine("Collecting 'Remote:{0}' => '{1}'", uninstall_logfile, target_uninstall_logfile); _vm.CopyFileFromGuestToHost(uninstall_logfile, target_uninstall_logfile); result.UnInstallLogfile = Path.Combine(ShortLogPath, Path.GetFileName(uninstall_logfile)); } return(result); }