public void UpdateItems(IEnumerable<SyncAction> syncActions) { syncActions = syncActions.ToList(); if (!syncActions.Any()) { return; } // make sure all to be updated actions exist (no need to check the state, this property might have changed) AssertSyncActionsExist(syncActions, false); using (var workingDir = new TemporaryWorkingDirectory(GitGroup.Repository.Info.Path, BranchName.ToString())) { var root = new Directory(null, "root"); foreach (var syncAction in syncActions) { PathValidator.EnsureIsRootedPath(syncAction.Path); // remove existing files for this sync action var filesToDelete = Enum.GetValues(typeof (SyncActionState)).Cast<SyncActionState>() .Where(state => state != syncAction.State) .Select(state => GetRelativeSyncActionDirectoryPath(state, syncAction.Path)) .Select(relativeDirectoryPath => Path.Combine(relativeDirectoryPath, SyncActionFile.GetFileName(syncAction))) .Select(relativePath => Path.Combine(workingDir.Location, relativePath)) .Where(System.IO.File.Exists).ToList(); foreach (var file in filesToDelete) { System.IO.File.Delete(file); } // add a new file var directory = DirectoryHelper.GetOrAddDirectory(root, GetRelativeSyncActionDirectoryPath(syncAction)); directory.Add(d => new SyncActionFile(d, syncAction)); } var localItemCreator = new LocalItemCreator(); localItemCreator.CreateDirectoryInPlace(root, workingDir.Location); workingDir.Commit($"{nameof(GitSyncActionService)}: Updated {syncActions.Count()} items"); workingDir.Push(); } }
public static GitBasedMultiFileSystemSnapshot Create(Repository repository, BranchName branchName, IHistoryService historyService) { var directoryCreator = new LocalItemCreator(); var branch = repository.GetBranch(branchName); string commitId; using (var workingRepository = new TemporaryWorkingDirectory(repository.Info.Path, branch.FriendlyName)) { var snapshotDirectory = new Directory(null, s_SnapshotDirectoryName); foreach (var fileSystemHistory in historyService.Items) { var fileName = fileSystemHistory.Name + s_FileNameSuffix; var content = fileSystemHistory.LatestFileSystemSnapshot?.Id ?? ""; snapshotDirectory.Add(d => new TextFile(d, fileName, content)); } var snapshotDirectoryPath = Path.Combine(workingRepository.Location, s_SnapshotDirectoryName); directoryCreator.CreateDirectoryInPlace(snapshotDirectory, snapshotDirectoryPath, true); if (workingRepository.HasChanges) { try { commitId = workingRepository.Commit("Created multi-filesystem snapshot"); workingRepository.Push(); } catch (EmptyCommitException) { // no changes after all (HasChanges does not seem to be a 100% accurate) commitId = repository.GetBranch(branchName).Tip.Sha; } } else { commitId = repository.GetBranch(branchName).Tip.Sha; } } var commit = repository.Lookup<Commit>(commitId); return IsSnapshot(commit) ? new GitBasedMultiFileSystemSnapshot(commit, historyService) : null; }
public void AddItems(IEnumerable<SyncAction> syncActions) { syncActions = syncActions.ToArray(); if (!syncActions.Any()) { return; } // make sure, the action does not already exist foreach (var action in syncActions) { var exisitingActions = this[action.State, action.Path].Where(a => a.Id == action.Id); if (exisitingActions.Any()) { throw new DuplicateSyncActionException($"A sync action with id {action.Id} already exists"); } } // create the branch if it does not already exist EnsureBranchExists(); // create a file system tree for the actions var root = new Directory(null, "root"); foreach (var syncAction in syncActions) { PathValidator.EnsureIsRootedPath(syncAction.Path); var directory = DirectoryHelper.GetOrAddDirectory(root, GetRelativeSyncActionDirectoryPath(syncAction)); directory.Add(d => new SyncActionFile(d, syncAction)); } // store the actions using (var workingDir = new TemporaryWorkingDirectory(GitGroup.Repository.Info.Path, BranchName.ToString())) { // create the actions on disk var localItemCreator = new LocalItemCreator(); localItemCreator.CreateDirectoryInPlace(root, workingDir.Location); // commit (no check if there are pending changes, because there will always be changes (we made sure that syncActions is not empty and action do not yet exist)) workingDir.Commit($"{nameof(GitSyncActionService)}: Added {syncActions.Count()} items"); workingDir.Push(); } }
public void AddItems(IEnumerable<ConflictInfo> conflicts) { if (conflicts == null) { throw new ArgumentNullException(nameof(conflicts)); } conflicts = conflicts.ToArray(); if(!conflicts.Any()) { return; } EnsureBranchExists(); var exisitngRoot = new GitDirectory(null, "root", GitGroup.Repository.GetLocalBranch(BranchName).Tip); var createdRoot = new Directory(null, "root"); // verify conflicts foreach (var conflict in conflicts) { var relativePath = GetRelativeConflictInfoFilePath(conflict.FilePath); if (exisitngRoot.FileExists(relativePath)) { throw new DuplicateItemException($"A ConflictInfo for '{conflict.FilePath}' already exists"); } var directory = DirectoryHelper.GetOrAddDirectory(createdRoot, PathParser.GetDirectoryName(relativePath)); directory.Add(f => new ConflictInfoFile(f, conflict)); } using (var workingDirectory = new TemporaryWorkingDirectory(GitGroup.Repository.Info.Path, BranchName.ToString())) { var localItemCreator = new LocalItemCreator(); localItemCreator.CreateDirectoryInPlace(createdRoot, workingDirectory.Location); workingDirectory.Commit($"{nameof(GitConflictService)}: Added {conflicts.Count()} items"); workingDirectory.Push(); } }