///<summary>Returns an ODGridCell formatted to show the status of the backport.</summary> private GridCell GetStatusCell(string backportVersion, ODFileChanges changedFile) { GridCell cell = new GridCell(); ODBackportResult backportResult = _listBackportResults.Find(x => x.FilePathHead == changedFile.FilePathHead); if (backportResult != null) { ResultType result = backportResult.GetResult(backportVersion); int numFailed = backportResult.GetFailedChanges(backportVersion).Count; cell.Text = result.ToString(); switch (result) { case ResultType.Ok: cell.ColorText = Color.DarkGreen; break; case ResultType.Partial: cell.ColorText = Color.YellowGreen; cell.Text += " (" + (changedFile.ListLineChanges.Count - numFailed).ToString() + "/" + changedFile.ListLineChanges.Count + ")"; break; case ResultType.Failed: cell.ColorText = Color.DarkRed; break; case ResultType.None: default: cell.ColorText = Color.Black; cell.Text = ""; break; } } return(cell); }
///<summary>This backports the files that have not been backported yet.</summary> ///<param name="backportVersion">The version that is being backported.</param> ///<param name="listFileChanges">A list of the files that will be backported.</param> public bool BackportFiles(string backportVersion, List <ODFileChanges> listFileChanges) { bool areAllFilesSuccessful = true; foreach (ODFileChanges file in listFileChanges) { ODBackportResult backportResult = new ODBackportResult(); backportResult.FilePathHead = file.FilePathHead; if (_listBackportResults.Any(x => x.FilePathHead == file.FilePathHead)) { backportResult = _listBackportResults.Find(x => x.FilePathHead == file.FilePathHead); } ResultType resultType = backportResult.GetResult(backportVersion); if (resultType != ResultType.None) //Skip already backported files { areAllFilesSuccessful &= resultType == ResultType.Ok; continue; } if (file.ModificationType == FileModificationType.Modified) { resultType = ModifyFile(file, backportVersion, backportResult); } else if (file.ModificationType == FileModificationType.Added) { resultType = AddFile(file, backportVersion); } else if (file.ModificationType == FileModificationType.Deleted) { resultType = DeleteFile(file, backportVersion); } areAllFilesSuccessful &= resultType == ResultType.Ok; backportResult.UpdateResult(backportVersion, resultType); if (!_listBackportResults.Any(x => x.FilePathHead == file.FilePathHead)) //If not added yet, add here. { _listBackportResults.Add(backportResult); } } return(areAllFilesSuccessful); }
///<summary>This modifies the files with the passed in changes. The core of the logic for backporting is here.</summary> ///<param name="changeFile">The file that is being modified.</param> ///<param name="backportVersion">The version the file is being backported to.</param> ///<param name="backportResult">The objects where the results are stored.</param> public static ResultType ModifyFile(ODFileChanges changeFile, string backportVersion, ODBackportResult backportResult) { ResultType result = ResultType.None; string filePath = changeFile.DictVersionFilePath[backportVersion]; //Get the correct encoding of the head file. Filstream.CurrentEncoding is not accurate. Because our code uses special symbols on occasion, we //need to ensure when backporting files, files do not lose characters as they could be crucial. Get the head path as the encoding may have //changed. Encoding fileEncodingHead = GetEncoding(changeFile.FilePathHead); //The encoding of the file to be backported before any changes. Encoding fileEncodingOld = GetEncoding(filePath); //Read in file with the encoding. string originalFile = File.ReadAllText(filePath, fileEncodingOld).Replace("\r\n", "\n").Replace("\n", "\r\n"); //Create a copy of the original lines so that we have something to safely manipulate. string changedFile = originalFile; List <ODLineChange> listFailedLineChanges = new List <ODLineChange>(); foreach (ODLineChange lineChange in changeFile.ListLineChanges) { //If there's at least one match if (changedFile.Contains(lineChange.SVNChangesBefore)) { //Replace the string to see how many lines it got rid of. This is preferred over Regex.Match.Count as that has been unreliable //for special characters. string fileNoMatches = changedFile.Replace(lineChange.SVNChangesBefore, ""); int numberOfMatches = (changedFile.Length - fileNoMatches.Length) / lineChange.SVNChangesBefore.Length; if (numberOfMatches == 1) { //One match. Replace the before text with the after text. changedFile = changedFile.Replace(lineChange.SVNChangesBefore, lineChange.SVNChangesAfter); } else { //More than one match. Just fail it. They will have to manually copy over the change. listFailedLineChanges.Add(lineChange); result = ResultType.Partial; } } else //no match { listFailedLineChanges.Add(lineChange); result = ResultType.Partial; } } if (changedFile == originalFile) { result = ResultType.Failed; return(result); } //Overwrites file File.WriteAllText(filePath, changedFile, fileEncodingHead); if (result == ResultType.None) //if nothing bad happened, set it to Ok { result = ResultType.Ok; } //Update list of failed changes. backportResult.UpdateListFailedChanges(backportVersion, listFailedLineChanges); return(result); }