/**********************************************************************************************************************/ public List <Tuple <string, string> > Synchronize(string configPath, int networkRetries, string synchronizerConfigurationPath, bool useNotification, Option <MCADCommon.LogCommon.DisposableFileLogger> logger, ref Option <string> mailFrom) { bool disposeLog = false; List <Tuple <string, string> > filesToMove = new List <Tuple <string, string> >(); try { NotifyIcon trayIcon = new NotifyIcon(); trayIcon.Text = "Fetching files to synchronize."; trayIcon.Icon = VaultEagleLib.Properties.Resources.Eagle; trayIcon.BalloonTipText = "Fetching files to synchronize."; ContextMenu trayMenu = new ContextMenu(); trayIcon.ContextMenu = trayMenu; trayIcon.Visible = true; if (useNotification) { trayIcon.ShowBalloonTip(4000); } errors = new List <string>(); // Fetch configuration file, mail on failure. Option <ADSK.File> configurationFile = Option.None; string path; logger.IfSomeDo(l => l.Trace("Before downloading configuration.")); if (synchronizerConfigurationPath.StartsWith("$")) { configurationFile = DownloadConfiguration(configPath, networkRetries, synchronizerConfigurationPath, logger, errors); if (configurationFile.IsNone) { return(filesToMove); } path = Path.Combine(configPath, configurationFile.Get().Name); } else { path = Environment.ExpandEnvironmentVariables(synchronizerConfigurationPath); } logger.IfSomeDo(l => l.Trace("After downloading configuration.")); VaultEagleLib.SynchronizerSettings configuration = VaultEagleLib.SynchronizerSettings.Read(networkRetries, logger, path); if (logger.IsNone && configuration.LogFile.IsSome) { logger = new MCADCommon.LogCommon.DisposableFileLogger(MCADCommon.LogCommon.DisposableFileLogger.CreateLogFilePath(configuration.configPath, configuration.LogFile.Get()), configuration.LogLevel).AsOption(); disposeLog = true; } // Option<Logg // if (configuration.LogFile.IsSome) logger.IfSomeDo(l => l.Info("Synchronizing vault files.")); // Fetch files to sync, mail on failure. // List<FileFolder> filesAndFoldersToUpdate = /*new List<FileFolder>();*/FetchingFilesFromVaultToSynchronize(ref mailInfo, lastSyncTime, logger, errors, configuration); if (configuration.OverrideMailSender.IsSome) { mailFrom = configuration.OverrideMailSender; } /*List<Tuple<ADSK.File, string, bool, bool>>*/ List <VaultEagleLib.Model.DataStructures.DownloadItem> filesToUpdate = FindFilesChangedSinceLastSync(connection, configuration.UseLastSync, configuration.LastSyncTime, configuration.VaultRoot, networkRetries, trayIcon, configuration.Items.ToArray(), logger); foreach (VaultEagleLib.SynchronizationItem item in configuration.Items) { foreach (Tuple <string, string> tempFileAndFinalPath in item.TempFilesAndFinalPath) { filesToMove.Add(tempFileAndFinalPath); } } string now = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"); logger.IfSomeDo(l => l.Info("Synchronizing: " + filesToUpdate.Count + " files.")); // if (filesToUpdate.Count > 0) { trayIcon.Text = "Downloaded 0 of " + filesToUpdate.Count + " files."; try { errors.AddRange(SynchronizeFiles(networkRetries, logger, errors, configuration, filesToUpdate, trayIcon)); List <VaultEagleLib.Model.DataStructures.DownloadFile> downloadedFiles = filesToUpdate.OfType <VaultEagleLib.Model.DataStructures.DownloadFile>().ToList(); foreach (string getAndRun in configuration.GetAndRun) { // string test1 = filesToUpdate[filesToUpdate.Count - 1].Item2.Replace(configuration.VaultRoot, "$").Replace("\\", "/") + "/" + filesToUpdate[filesToUpdate.Count - 1].Item1.Name; if (downloadedFiles.Any(f => getAndRun.Equals(f.VaultFileName(configuration.VaultRoot)))) { VaultEagleLib.Model.DataStructures.DownloadFile file = downloadedFiles.Where(f => getAndRun.Equals(f.VaultFileName(configuration.VaultRoot))).First(); VaultEagle.VaultUtils.HandleNetworkErrors(() => { System.Diagnostics.Process proc = new System.Diagnostics.Process(); proc.StartInfo.FileName = file.LocalFileName; proc.Start(); proc.WaitForExit(); }, networkRetries); } } } catch (Exception ex) { logger.IfSomeDo(l => l.Error(ex.Message)); errors.Add("Failure synchronizing files."); } if (errors.Count == 0 && configuration.LastSyncFile.IsSome) { if (!VaultUtils.HandleNetworkErrors(() => System.IO.Directory.Exists(configuration.configPath), networkRetries)) { VaultUtils.HandleNetworkErrors(() => System.IO.Directory.CreateDirectory(configuration.configPath), networkRetries); } if (VaultUtils.HandleNetworkErrors(() => System.IO.File.Exists(Path.Combine(configuration.configPath, configuration.LastSyncFile.Get() + ".txt")), networkRetries)) { VaultUtils.HandleNetworkErrors(() => System.IO.File.Delete(Path.Combine(configuration.configPath, configuration.LastSyncFile.Get() + ".txt")), networkRetries); } try { using (TextWriter tw = new StreamWriter(VaultUtils.HandleNetworkErrors(() => System.IO.File.Create(Path.Combine(configuration.configPath, configuration.LastSyncFile.Get() + ".txt")), networkRetries))) tw.WriteLine(now); } catch { } } if (useNotification) { if (errors.Count > 0) { trayIcon.BalloonTipText = "Errors synchronizing files."; if (useNotification) { trayIcon.ShowBalloonTip(2000); } } else { trayIcon.BalloonTipText = "Finished synchronizing files."; if (useNotification) { trayIcon.ShowBalloonTip(2000); } } } } trayIcon.DisposeUnlessNull(ref trayIcon); } catch (Exception ex) { logger.IfSomeDo(l => l.Error(ex.Message)); } logger.IfSomeDo(l => l.Trace("Synchronizing complete.")); if (disposeLog && logger.IsSome) { logger.Get().Dispose(); } return(filesToMove); }
private List <string> SynchronizeFiles(int networkRetries, Option <MCADCommon.LogCommon.DisposableFileLogger> logger, List <string> errors, VaultEagleLib.SynchronizerSettings configuration, List <VaultEagleLib.Model.DataStructures.DownloadItem> filesAndFoldersToUpdate, NotifyIcon notify) { List <string> failedFiles = new List <string>(); if (filesAndFoldersToUpdate.Count > 0) { int batchSize = 1000; int maxPageNumber = Convert.ToInt32(Math.Floor(filesAndFoldersToUpdate.Count / (batchSize + 0.0))); for (int i = 0; i <= maxPageNumber; i++) { IEnumerable <VaultEagleLib.Model.DataStructures.DownloadItem> filesToSynchronize = GetBatch(i, filesAndFoldersToUpdate, batchSize); logger.IfSomeDo(l => l.Trace("Fetched: " + filesToSynchronize.Count() + " files to download.")); failedFiles.AddRange(SynchronizeFileBatches(filesToSynchronize.ToList(), configuration.Items.ToArray(), logger, networkRetries)); notify.Text = "downloaded " + (i * batchSize).ToString() + " of " + filesAndFoldersToUpdate.Count + " files.";// +" synchronized files of " + filesAndFoldersToUpdate.Count.ToString() + "."; logger.IfSomeDo(l => l.Info(filesToSynchronize.Count() + " files downloaded.")); } } foreach (VaultEagleLib.SynchronizationItem item in configuration.Items) { item.DeleteFiles(configuration.VaultRoot, networkRetries); item.MirrorFolders(configuration.VaultRoot, networkRetries); item.RunFiles(configuration.VaultRoot, filesAndFoldersToUpdate.OfType <VaultEagleLib.Model.DataStructures.DownloadFile>().ToList(), networkRetries); item.CreateEmptyFolders(configuration.VaultRoot, networkRetries); } return(failedFiles); }
public static SynchronizerSettings Read(int networkRetries, Option <MCADCommon.LogCommon.DisposableFileLogger> logger, string configurationPath = "") { SynchronizerSettings configuration = new SynchronizerSettings(); FileInfo configurationFile; if (!String.IsNullOrWhiteSpace(configurationPath)) { configurationFile = new FileInfo(configurationPath); } else { configurationFile = ConfigurationFile; } if (!configurationFile.Exists) { configurationFile = new FileInfo(Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), configurationPath)); } if (configurationFile.Exists) { XmlDocument document = new XmlDocument(); document.Load(configurationFile.FullName); configuration.configPath = Environment.ExpandEnvironmentVariables(MCAD.XmlCommon.XmlTools.ReadString(document.DocumentElement, "configuration_path")); try { configuration.GetAndRun = MCAD.XmlCommon.XmlTools.ReadStringValues(document.DocumentElement, "run_files", "get_and_run"); } catch { configuration.GetAndRun = new List <string>(); } configuration.VaultRoot = Environment.ExpandEnvironmentVariables(MCAD.XmlCommon.XmlTools.ReadString(document.DocumentElement, "vault_root")); List <SynchronizationItem> items = new List <SynchronizationItem>(); foreach (string syncItem in MCAD.XmlCommon.XmlTools.ReadStringValues(document.DocumentElement, "synchronization_commands", "synchronization_command")) { try { items.Add(SynchronizationItem.ReadString(syncItem)); } catch (Exception ex) { logger.IfSomeDo(l => l.Error(ex.Message)); } } List <SynchronizationItem> RemoveItemsNotLegal = new List <SynchronizationItem>(); foreach (SynchronizationItem item in items) { try { if (!item.HasIllegalItems(configuration.VaultRoot)) { RemoveItemsNotLegal.Add(item); } } catch (Exception ex) { logger.IfSomeDo(l => l.Error(ex.Message)); } } configuration.Items = RemoveItemsNotLegal; configuration.LastSyncFile = MCAD.XmlCommon.XmlTools.SafeReadString(document.DocumentElement, "last_sync_file"); configuration.UseLastSync = false; if ((configuration.LastSyncFile.IsSome) && (VaultEagle.VaultUtils.HandleNetworkErrors(() => File.Exists(Path.Combine(configuration.configPath, configuration.LastSyncFile.Get() + ".txt")), networkRetries))) { configuration.UseLastSync = true; try { configuration.LastSyncTime = DateTime.ParseExact(VaultEagle.VaultUtils.HandleNetworkErrors(() => File.ReadLines(Path.Combine(configuration.configPath, configuration.LastSyncFile.Get() + ".txt")).First(), networkRetries), "yyyy-MM-dd HH:mm:ss", System.Globalization.CultureInfo.InvariantCulture); } catch { configuration.LastSyncTime = DateTime.ParseExact("1990-01-01 00:00:00", "yyyy-MM-dd HH:mm:ss", System.Globalization.CultureInfo.InvariantCulture); } } else { configuration.LastSyncTime = DateTime.ParseExact("1990-01-01 00:00:00", "yyyy-MM-dd HH:mm:ss", System.Globalization.CultureInfo.InvariantCulture); } configuration.OverrideMailSender = MCAD.XmlCommon.XmlTools.SafeReadString(document.DocumentElement, "override_mail_sender"); configuration.LogLevel = MCADCommon.LogCommon.Utils.ParseLogLevel(MCAD.XmlCommon.XmlTools.SafeReadString(document.DocumentElement, "log_level").IsSome ? MCAD.XmlCommon.XmlTools.ReadString(document.DocumentElement, "log_level") : "Info"); configuration.LogFile = MCAD.XmlCommon.XmlTools.SafeReadString(document.DocumentElement, "log_name"); try { configuration.SavedLogCount = MCAD.XmlCommon.XmlTools.SafeReadString(document.DocumentElement, "saved_log_count").IsSome ? Convert.ToInt32(MCAD.XmlCommon.XmlTools.ReadString(document.DocumentElement, "saved_log_count")) : 60; } catch { configuration.SavedLogCount = 60; } } else { configuration.configPath = ""; } return(configuration); }