/// <summary> /// /// </summary> public void Synchronize() { Directory.CreateDirectory(Source); Directory.CreateDirectory(Target); var src = new DirectoryStructure(Source); var trg = new DirectoryStructure(Target); bool waserror = false; foreach (var fileItem in src.GetDiff(trg)) { try{ Log.Trace("start " + fileItem); Apply(fileItem); Log.Info("complete " + fileItem); } catch (Exception ex) { Log.Error("error " + fileItem, ex); waserror = true; } } if (!waserror) { var hash = src.GetStampFile().ToString(); File.WriteAllText(Path.Combine(Target, DirectoryStructure.SyncFileName), hash); File.WriteAllText(Path.Combine(Source, DirectoryStructure.SyncFileName), hash); Log.Info("stamp file wrote"); } else { Log.Error("stamp not written due to some exceptions"); } }
/// <summary> /// Получить разницу между исходной и целевой директорией /// </summary> /// <returns></returns> public IEnumerable <FileItem> GetDifference() { var src = new DirectoryStructure(Source); var trg = new DirectoryStructure(Target); return(src.GetDiff(trg)); }
/// <summary> /// Получить разницу между директориями /// </summary> /// <param name="other"></param> /// <returns></returns> public IEnumerable <FileItem> GetDiff(DirectoryStructure other) { var src = this.GetStampFile(); var trg = other.GetStampFile(); if (src.ToString() == trg.ToString()) { yield break; } var srce = src.Elements().Select(_ => new FileItem(_, FileOperation.None)).ToArray(); var trge = trg.Elements().Select(_ => new FileItem(_, FileOperation.None)).ToArray(); var leftOuterJoin = from s in srce join t in trge on s.Name equals t.Name into temp from t in temp.DefaultIfEmpty(new FileItem()) select new FileItem { Hash = s.Hash, Name = s.Name, OtherHash = t.Hash }; var rightOuterJoin = from t in trge join s in srce on t.Name equals s.Name into temp from s in temp.DefaultIfEmpty(new FileItem()) select new FileItem { Hash = s.Hash, Name = t.Name, OtherHash = t.Hash }; var fullOuterJoin = leftOuterJoin.Union(rightOuterJoin.Where(_ => string.IsNullOrWhiteSpace(_.Hash))).ToArray(); foreach (FileItem i in fullOuterJoin) { if (i.Hash == i.OtherHash) { continue; } if (string.IsNullOrWhiteSpace(i.Hash)) { i.Operation = FileOperation.Delete; yield return(i); } else if (string.IsNullOrWhiteSpace(i.OtherHash)) { i.Operation = FileOperation.Create; yield return(i); } else { i.Operation = FileOperation.Update; yield return(i); } } }
/// <summary> /// Получить разницу между директориями /// </summary> /// <param name="other"></param> /// <returns></returns> public IEnumerable<FileItem> GetDiff(DirectoryStructure other){ var src = this.GetStampFile(); var trg = other.GetStampFile(); if (src.ToString() == trg.ToString()){ yield break; } var srce = src.Elements().Select(_=>new FileItem(_,FileOperation.None)).ToArray(); var trge = trg.Elements().Select(_ => new FileItem(_, FileOperation.None)).ToArray(); var leftOuterJoin = from s in srce join t in trge on s.Name equals t.Name into temp from t in temp.DefaultIfEmpty(new FileItem()) select new FileItem{Hash = s.Hash, Name = s.Name, OtherHash = t.Hash}; var rightOuterJoin = from t in trge join s in srce on t.Name equals s.Name into temp from s in temp.DefaultIfEmpty(new FileItem()) select new FileItem { Hash = s.Hash, Name = t.Name, OtherHash = t.Hash }; var fullOuterJoin = leftOuterJoin.Union(rightOuterJoin.Where(_=>string.IsNullOrWhiteSpace(_.Hash))).ToArray(); foreach (FileItem i in fullOuterJoin){ if (i.Hash == i.OtherHash) continue; if (string.IsNullOrWhiteSpace(i.Hash)){ i.Operation = FileOperation.Delete; yield return i; }else if (string.IsNullOrWhiteSpace(i.OtherHash)){ i.Operation = FileOperation.Create; yield return i; } else{ i.Operation = FileOperation.Update; yield return i; } } }