public override void Run() { var backups = BackupFolder.GetBackups(this.Folder, this.Pattern).OrderByDescending(b => b.BackupDate).ToList(); if (backups.Count < 1) { Logger.Root.Warning("No backups found, that match the specified pattern {0}!", Pattern); return; } var end = backups[0].BackupDate; var remove = new Action <TimeSpan, int>((interval, count) => { DateTime start; if (backups.Count <= this.KeepMin) { return; } for (var i = 0; i < count; i++) { start = end.Subtract(interval); var removeList = backups.Where(backup => (start < backup.BackupDate) && (backup.BackupDate <= end)).Skip(1).ToArray(); foreach (var item2Remove in removeList) { if (backups.Count <= this.KeepMin) { return; } backups.Remove(item2Remove); this.DeletedFolders.Add(item2Remove.Folder); } end = start; } }); foreach (var rule in this.Rules) { remove(rule.Interval, rule.Count); } Logger.Root.WriteLine(Verbosity.Message, "keeping {0} folders:", backups.Count); foreach (var backup in backups) { Logger.Root.WriteLine(Verbosity.Message, "\t+ {0}", backup.Folder); } foreach (var f in this.DeletedFolders) { Logger.Root.WriteLine(Verbosity.Message, "Deleting backup folder {0}...", f); var start = DateTime.Now; try { Monitor.Root.DeleteDirectory(f); Logger.Root.WriteLine(Verbosity.Message, "...completed after {0}", DateTime.Now.Subtract(start)); } catch (Exception error) { Logger.Root.Error("...failed with {0}: {1} after {2}", error.GetType().Name, error.Message, DateTime.Now.Subtract(start)); } } }
public override void Run() { // format the target directory if (!this.Target.EndsWith("\\")) { this.Target += "\\"; } var wildCardPos = this.Target.IndexOf(@"\*\"); string backupFolderSuffix = ""; if (wildCardPos >= 0) { if (String.IsNullOrEmpty(HashDir)) { this.HashDir = Path.Combine(this.Target.Substring(0, wildCardPos), "Hash"); } if (String.IsNullOrEmpty(this.PrevBackupFolderRoot)) { this.PrevBackupFolderRoot = this.Target.Substring(0, wildCardPos + 1); backupFolderSuffix = this.Target.Substring(wildCardPos + 3); } this.Target = this.Target.Replace(@"\*\", @"\" + DateTime.Now.ToString(this.Pattern.ToLower().Replace("mm", "MM").Replace("hh", "HH").Replace("nn", "mm").Replace("nn", "mm")) + @"\"); if (this.Target.IndexOf('*') >= 0) { throw new InvalidOperationException("The target folder may only contain one date/time wildcard * and must be surrounded by \\!"); } } else { this.HashDir = (String.IsNullOrEmpty(this.HashDir) ? Path.Combine(this.Target, @"..\Hash") : this.HashDir); } this.Target = Path.GetFullPath(this.Target); Directory.CreateDirectory(this.Target); Logger.Root.Logfilename = Path.Combine(this.Target, "Backup.log"); this.HashDir = Path.GetFullPath(this.HashDir).ToLower(); if (!this.HashDir.EndsWith("\\")) { this.HashDir += "\\"; } // search for old backups if (this.usePreviousBackup && !String.IsNullOrEmpty(this.PrevBackupFolderRoot)) { if (!this.PrevBackupFolderRoot.EndsWith("\\")) { this.PrevBackupFolderRoot += "\\"; } Logger.Root.PrintInfo("Backup folder", "{0}{1}{2}", this.PrevBackupFolderRoot, wildCardPos >= 0 ? @"\*\" : "", backupFolderSuffix); var backups = BackupFolder .GetBackups(this.PrevBackupFolderRoot, this.Pattern) .Where(backup => String.Compare(backup.Folder + "\\" + backupFolderSuffix, this.Target, true) != 0) .OrderByDescending(backup => backup.BackupDate) .ToArray(); Logger.Root.WriteLine(Verbosity.Message, "Found {0} previous backups in {1}, matching pattern {2}", backups.Length, this.PrevBackupFolderRoot, this.Pattern); if (backups.Length > 0) { var newestBackup = backups[0]; this.PreviousBackup = newestBackup.Folder + "\\" + backupFolderSuffix; Logger.Root.PrintInfo("Previous backup folder", this.PreviousBackup); } } Logger.Root.PrintInfo("Pattern", this.Pattern); Logger.Root.PrintInfo("Source folder", this.Folder); Logger.Root.PrintInfo("Target folder", this.Target); Logger.Root.PrintInfo("Hash folder", this.HashDir); // create own hash provider for each task for (var i = 0; i < (this.multiThread ? maxBackgroundJobs : 1); i++) { this.hashProviders.Enqueue(SHA1.Create()); } base.Run(); if (this.multiThread) { Console.Write("Waiting for background jobs to complete..."); var x = Console.CursorLeft; while (true) { int c; lock (this.hashProviders) c = this.hashProviders.Count; if (c == maxBackgroundJobs) { break; } else { Thread.Sleep(50); } Console.CursorLeft = x; Console.Write("{0,5}", c); } Console.WriteLine("done."); } }