protected void CompareManifestsRecursiveSource( ManifestDirectoryInfo sourceDir, ManifestDirectoryInfo destDir, HashSet <ManifestFileInfo> destFileMatch) { foreach (ManifestFileInfo sourceFile in sourceDir.Files.Values) { if (destDir != null && destDir.Files.ContainsKey(sourceFile.Name)) { ManifestFileInfo destFile = destDir.Files[sourceFile.Name]; destFileMatch.Add(destFile); if (sourceFile.FileHash.Equals(destFile.FileHash) == false) { ChangedFiles.Add(sourceFile, destFile); } else { if (Manifest.CompareManifestDates( sourceFile.LastModifiedUtc, destFile.LastModifiedUtc) == false) { LastModifiedDateFiles.Add(sourceFile, destFile); } if (Manifest.CompareManifestDates( sourceFile.RegisteredUtc, destFile.RegisteredUtc) == false) { RegisteredDateFiles.Add(sourceFile, destFile); } } } else { SourceOnlyFiles.Add(sourceFile); } } foreach (ManifestDirectoryInfo nextSourceDir in sourceDir.Subdirectories.Values) { ManifestDirectoryInfo nextDestDir = null; if (destDir != null && destDir.Subdirectories.ContainsKey(nextSourceDir.Name)) { nextDestDir = destDir.Subdirectories[nextSourceDir.Name]; } CompareManifestsRecursiveSource( nextSourceDir, nextDestDir, destFileMatch); } }
public void Clear() { SourceOnlyFiles.Clear(); DestOnlyFiles.Clear(); ChangedFiles.Clear(); LastModifiedDateFiles.Clear(); RegisteredDateFiles.Clear(); MovedFiles.Clear(); MovedFileOrder.Clear(); ErrorFiles.Clear(); }
public GitFileStatus GetFileStatus(string fileName) { var file = ChangedFiles.Where(f => string.Compare(f.FileName, fileName, true) == 0).FirstOrDefault(); if (file != null) { return(file.Status); } if (FileExistsInRepo(fileName)) { return(GitFileStatus.Tracked); } // did not check if the file is ignored for performance reason return(GitFileStatus.NotControlled); }
public void Clear() { FileCheckedCount = 0; NewFiles.Clear(); NewFilesForGroom.Clear(); ChangedFiles.Clear(); MissingFiles.Clear(); LastModifiedDateFiles.Clear(); ErrorFiles.Clear(); IgnoredFiles.Clear(); NewlyIgnoredFiles.Clear(); IgnoredFilesForGroom.Clear(); MovedFiles.Clear(); MovedFileOrder.Clear(); DuplicateFiles.Clear(); }
private static PredictionRequest BuildRequest(ChangedFiles changedFiles) { var request = new PredictionRequest(); foreach (var loopFile in changedFiles.Files) { request.Items.Add(new PredictionRequestFile { Author = loopFile.Author, Path = loopFile.Path, OldPath = loopFile.OldPath, NumberOfModifiedLines = loopFile.NumberOfModifiedLines, CCMMd = loopFile.CCMMd, CCMAvg = loopFile.CCMAvg, CCMMax = loopFile.CCMMax }); } return(request); }
/// <summary> /// Add a new fileinfo to the list of changed files. /// </summary> /// <param name="change"></param> internal void AddNewChange(ChangedFile change) { if (Application.Current == null) { return; } if (Application.Current.Dispatcher.CheckAccess()) { if (!ChangedFiles.Contains(change)) { ChangedFiles.Add(change); } } else { AddChangeDelegate del = new AddChangeDelegate(AddNewChange); Application.Current.Dispatcher.Invoke(del, new object[] { change }); } }
internal void AddNewChangeSet(IEnumerable <ChangedFile> changes) { if (Application.Current == null) { return; } if (Application.Current.Dispatcher.CheckAccess()) { foreach (var change in changes) { if (!ChangedFiles.Contains(change)) { ChangedFiles.Add(change); } } } else { AddChangesDelegate del = new AddChangesDelegate(AddNewChangeSet); Application.Current.Dispatcher.Invoke(del, new object[] { changes }); } }
public GitFileStatus GetFileStatus(string fileName) { try { fileName = Path.GetFullPath(fileName); var file = ChangedFiles.FirstOrDefault(f => string.Equals(f.FilePath, fileName, StringComparison.OrdinalIgnoreCase)); if (file != null) { return(file.Status); } if (FileExistsInRepo(fileName)) { return(GitFileStatus.Tracked); } // did not check if the file is ignored for performance reason return(GitFileStatus.NotControlled); } catch (Exception ex) { Debug.WriteLine("Error In File System Changed Event: " + ex.Message); return(GitFileStatus.NotControlled); } }
private static ChangedFiles GetChangedFiles(string repositoryPath, IEnumerable <string> filePaths) { try { using (var repository = new Repository(repositoryPath)) { string userName = repository.Config.GetValueOrDefault("user.name", string.Empty); var status = repository.RetrieveStatus( new StatusOptions { DetectRenamesInIndex = true, DetectRenamesInWorkDir = true, DisablePathSpecMatch = true, ExcludeSubmodules = true, IncludeUnaltered = true, Show = StatusShowOption.IndexAndWorkDir, }); var statusEntries = status.Where(g => g.State.HasFlag(FileStatus.ModifiedInWorkdir) || g.State.HasFlag(FileStatus.RenamedInWorkdir) || g.State.HasFlag(FileStatus.DeletedFromWorkdir)).ToList(); var result = new ChangedFiles(); if (filePaths != null) { statusEntries = statusEntries .Where(g => filePaths.Any(path => path.IndexOf(g.FilePath, StringComparison.OrdinalIgnoreCase) > -1)) .ToList(); } if (!statusEntries.Any()) { return(result); } var changesLookup = repository.Diff.Compare <Patch>(statusEntries.Select(g => g.FilePath), true) .ToDictionary(g => g.Path, g => g); foreach (var loopEntry in statusEntries) { string filePath = loopEntry.FilePath; PatchEntryChanges patchEntryChanges; if (!changesLookup.TryGetValue(filePath, out patchEntryChanges)) { continue; } string oldFilePath = filePath; if (loopEntry.IndexToWorkDirRenameDetails != null) { oldFilePath = loopEntry.IndexToWorkDirRenameDetails.OldFilePath; } CyclomaticComplexityMetric metric = null; if (CyclomaticComplexityHelper.IsSupportedFile(filePath)) { var fullFilePath = Path.Combine(repositoryPath, filePath); if (File.Exists(fullFilePath)) { metric = CyclomaticComplexityHelper.CalculateMetric( File.OpenRead(fullFilePath), filePath, true); } } result.Files.Add(new ChangedFile { Author = userName, Path = filePath, OldPath = oldFilePath, NumberOfModifiedLines = patchEntryChanges.LinesAdded + patchEntryChanges.LinesDeleted, CCMMd = metric?.CCMMd, CCMAvg = metric?.CCMAvg, CCMMax = metric?.CCMMax }); } return(result); } } catch (RepositoryNotFoundException) { return(null); } }
protected void UpdateRecursive( DirectoryInfo currentDirectoryInfo, ManifestDirectoryInfo currentManfestDirInfo) { // Setup data for current directory Dictionary <String, FileInfo> fileDict = new Dictionary <string, FileInfo>(); Dictionary <String, DirectoryInfo> dirDict = new Dictionary <string, DirectoryInfo>(); if (currentDirectoryInfo != null) { FileInfo[] fileList = null; try { fileList = currentDirectoryInfo.GetFiles(); } catch (Exception) { WriteLine(Manifest.MakeStandardPathString( currentManfestDirInfo)); if (IgnoreFile(Manifest.MakeStandardPathString( currentManfestDirInfo)) == true) { // This was implemented primarily to allow the user to // silence the process of skipping over inaccessible // system directories by ignoring them. For example, // in some cases the "$RECYCLE BIN" under Windows // is not accessible and will generate an error. The // user can now add such directories to the ignore list // and they will be silently ignored. The special // message for showProgress alerts the user that the // directory is actually being skipped altogether // since it can't be accessed. The only significant // implication of this is that the ignored files won't // be enumerated and counted as being ignored. if (ShowProgress) { WriteLine( Manifest.MakeStandardPathString(currentManfestDirInfo) + " [IGNORED DIRECTORY AND CANNOT ACCESS]"); } } else { ForceWriteLine("Could not access contents of: " + currentDirectoryInfo.FullName); } return; } foreach (FileInfo nextFileInfo in fileList) { fileDict.Add(nextFileInfo.Name.Normalize(), nextFileInfo); } DirectoryInfo[] dirList = currentDirectoryInfo.GetDirectories(); foreach (DirectoryInfo nextDirInfo in dirList) { dirDict.Add(nextDirInfo.Name.Normalize(), nextDirInfo); } } // Clone in case we modify during iteration List <ManifestFileInfo> fileListClone = new List <ManifestFileInfo>(currentManfestDirInfo.Files.Values); // Iterate through existing manifest entries foreach (ManifestFileInfo nextManFileInfo in fileListClone) { if (ShowProgress) { Write(Manifest.MakeStandardPathString(nextManFileInfo)); } if (fileDict.ContainsKey(nextManFileInfo.Name)) { FileCheckedCount++; FileInfo nextFileInfo = fileDict[nextManFileInfo.Name]; if (IgnoreFile(Manifest.MakeStandardPathString(nextManFileInfo))) { Write(" [NEWLY IGNORED]"); currentManfestDirInfo.Files.Remove( nextManFileInfo.Name); NewlyIgnoredFiles.Add(nextManFileInfo); } else if (nextFileInfo.Length != nextManFileInfo.FileLength && Update == false && AlwaysCheckHash == false) { // Don't compute hash if we aren't doing an update Write(" [DIFFERENT]"); ChangedFiles.Add(nextManFileInfo); } else if (AlwaysCheckHash == true || MakeNewHash == true || nextManFileInfo.FileHash == null || Manifest.CompareManifestDateToFilesystemDate(nextFileInfo.LastWriteTimeUtc, nextManFileInfo.LastModifiedUtc) == false || nextFileInfo.Length != nextManFileInfo.FileLength) { FileHash checkHash = null; Exception exception = null; try { string hashType = Manifest.DefaultHashMethod; if (nextManFileInfo.FileHash != null) { hashType = nextManFileInfo.FileHash.HashType; } checkHash = FileHash.ComputeHash( nextFileInfo, hashType); } catch (Exception ex) { exception = ex; } if (exception != null) { WriteLine(" [ERROR]"); WriteLine(exception.ToString()); ErrorFiles.Add(nextManFileInfo); } else { if (nextManFileInfo.FileHash == null) { Write(" [NULL HASH IN MANIFEST]"); ChangedFiles.Add(nextManFileInfo); } else if (checkHash.Equals(nextManFileInfo.FileHash) == false) { Write(" [DIFFERENT]"); ChangedFiles.Add(nextManFileInfo); } else { if (Manifest.CompareManifestDateToFilesystemDate( nextFileInfo.LastWriteTimeUtc, nextManFileInfo.LastModifiedUtc) == false) { Write(" [LAST MODIFIED DATE]"); LastModifiedDateFiles.Add(nextManFileInfo); if (BackDate == true) { nextFileInfo.LastWriteTimeUtc = nextManFileInfo.LastModifiedUtc; } } } } FileHash newHash = checkHash; if (MakeNewHash) { newHash = FileHash.ComputeHash( nextFileInfo, GetNewHashType(Manifest)); } // Update hash and last modified date accordingly nextManFileInfo.FileHash = newHash; nextManFileInfo.LastModifiedUtc = nextFileInfo.LastWriteTimeUtc; nextManFileInfo.FileLength = nextFileInfo.Length; } else { Write(" [SKIPPED]"); } } else { Write(" [MISSING]"); currentManfestDirInfo.Files.Remove(nextManFileInfo.Name); MissingFiles.Add(nextManFileInfo); } WriteLine(""); } // Clone in case we modify during iteration List <ManifestDirectoryInfo> directoryListClone = new List <ManifestDirectoryInfo>( currentManfestDirInfo.Subdirectories.Values); foreach (ManifestDirectoryInfo nextManDirInfo in directoryListClone) { DirectoryInfo nextDirInfo = null; if (dirDict.ContainsKey(nextManDirInfo.Name)) { nextDirInfo = dirDict[nextManDirInfo.Name]; } UpdateRecursive( nextDirInfo, nextManDirInfo); if (nextManDirInfo.Empty) { currentManfestDirInfo.Subdirectories.Remove( nextManDirInfo.Name); } } // Look for new files foreach (String nextFileName in fileDict.Keys) { FileInfo nextFileInfo = fileDict[nextFileName]; if (currentManfestDirInfo.Files.ContainsKey( nextFileName) == false) { ManifestFileInfo newManFileInfo = new ManifestFileInfo( nextFileName, currentManfestDirInfo); Write(Manifest.MakeStandardPathString(newManFileInfo)); if (IgnoreFile(Manifest.MakeStandardPathString(newManFileInfo))) { IgnoredFiles.Add(newManFileInfo); // Don't groom the manifest file! if (Manifest.MakeNativePathString(newManFileInfo) != ManifestNativeFilePath) { IgnoredFilesForGroom.Add(nextFileInfo); } Write(" [IGNORED]"); } else { FileCheckedCount++; bool checkHash = false; if (Update == true || AlwaysCheckHash == true || TrackMoves == true) { checkHash = true; } Exception exception = null; if (checkHash) { try { newManFileInfo.FileHash = FileHash.ComputeHash( nextFileInfo, GetNewHashType(Manifest)); } catch (Exception ex) { exception = ex; } } if (checkHash && newManFileInfo.FileHash == null) { ErrorFiles.Add(newManFileInfo); WriteLine(" [ERROR]"); WriteLine(exception.ToString()); } else { NewFiles.Add(newManFileInfo); NewFilesForGroom.Add(nextFileInfo); Write(" [NEW]"); } newManFileInfo.FileLength = nextFileInfo.Length; newManFileInfo.LastModifiedUtc = nextFileInfo.LastWriteTimeUtc; newManFileInfo.RegisteredUtc = DateTime.Now.ToUniversalTime(); currentManfestDirInfo.Files.Add( nextFileName, newManFileInfo); } WriteLine(""); } } // Recurse looking for new directories foreach (String nextDirName in dirDict.Keys) { DirectoryInfo nextDirInfo = dirDict[nextDirName]; if (currentManfestDirInfo.Subdirectories.ContainsKey( nextDirName) == false) { ManifestDirectoryInfo nextManDirInfo = new ManifestDirectoryInfo( nextDirName, currentManfestDirInfo); currentManfestDirInfo.Subdirectories.Add( nextDirName, nextManDirInfo); UpdateRecursive( nextDirInfo, nextManDirInfo); if (nextManDirInfo.Empty) { currentManfestDirInfo.Subdirectories.Remove( nextDirName); } } } }
static void Main(string[] args) { NameValueCollection settings = ConfigurationManager.AppSettings; var listName = "FileChangedLog"; var siteUrl = new Uri("http://xxxx.xxxxx.xxx"); var credentials = new NetworkCredential("xxxxx", "xxxxx", "xxxxx"); var downloadQueue = new ChangedFiles(siteUrl, listName, credentials, 10, 0); downloadQueue.Start(); Console.ReadLine(); downloadQueue.Stop(); }
public async Task <UpdateImpactResults> Analyze( Stream appxBlockMap1, Stream appxBlockMap2, CancellationToken cancellationToken = default, IProgress <ProgressData> progressData = default) { var progressReadFiles1 = new RangeProgress(progressData, 0, 30); var progressReadFiles2 = new RangeProgress(progressData, 30, 60); var progressCalculatingStatus = new RangeProgress(progressData, 60, 75); var progressDuplicates = new RangeProgress(progressData, 75, 90); var progressRemainingCalculation = new RangeProgress(progressData, 90, 100); var filesInOldPackage = new SortedDictionary <string, AppxFile>(); var filesInNewPackage = new SortedDictionary <string, AppxFile>(); var blocksInPackage1 = new Dictionary <string, AppxBlock>(); var blocksInPackage2 = new Dictionary <string, AppxBlock>(); progressReadFiles1.Report(new ProgressData(0, "Reading the first package...")); var files1 = await this.GetFiles(appxBlockMap1, cancellationToken, progressReadFiles1).ConfigureAwait(false); foreach (var file1 in files1) { foreach (var block in file1.Blocks) { blocksInPackage1[block.Hash] = block; } filesInOldPackage.Add(file1.Name, file1); } progressReadFiles2.Report(new ProgressData(0, "Reading the second package...")); var files2 = await this.GetFiles(appxBlockMap2, cancellationToken, progressReadFiles2).ConfigureAwait(false); foreach (var file2 in files2) { foreach (var block in file2.Blocks) { blocksInPackage2[block.Hash] = block; } filesInNewPackage.Add(file2.Name, file2); } progressCalculatingStatus.Report(new ProgressData(0, "Calculating file status (1/2)...")); foreach (var file in filesInOldPackage) { cancellationToken.ThrowIfCancellationRequested(); if (!filesInNewPackage.TryGetValue(file.Key, out var fileFromPackage2)) { file.Value.Status = ComparisonStatus.Old; file.Value.UpdateImpact = 0; // file removed = no update on impact file.Value.SizeDifference = -file.Value.UncompressedSize; continue; } if (file.Value.UncompressedSize == fileFromPackage2.UncompressedSize && file.Value.Blocks.Select(b => b.Hash).SequenceEqual(fileFromPackage2.Blocks.Select(b => b.Hash))) { file.Value.Status = ComparisonStatus.Unchanged; file.Value.UpdateImpact = 0; // file unchanged = no update on impact file.Value.SizeDifference = 0; fileFromPackage2.Status = ComparisonStatus.Unchanged; fileFromPackage2.UpdateImpact = 0; // file unchanged = no update on impact fileFromPackage2.SizeDifference = 0; } else { file.Value.Status = ComparisonStatus.Changed; file.Value.UpdateImpact = 0; // file changed = show no update impact. The impact should be shown in the other package. file.Value.SizeDifference = file.Value.UncompressedSize - fileFromPackage2.UncompressedSize; var blocksOnlyInPackage2 = fileFromPackage2.Blocks.Select(b => b.Hash).Except(file.Value.Blocks.Select(b => b.Hash)); fileFromPackage2.Status = ComparisonStatus.Changed; fileFromPackage2.UpdateImpact = blocksOnlyInPackage2.Select(b => blocksInPackage2[b]).Sum(b => b.CompressedSize); fileFromPackage2.SizeDifference = fileFromPackage2.UncompressedSize - file.Value.UncompressedSize; } } foreach (var block1KeyValuePair in blocksInPackage1) { cancellationToken.ThrowIfCancellationRequested(); var block1 = block1KeyValuePair.Value; if (!blocksInPackage2.TryGetValue(block1KeyValuePair.Key, out var block2)) { block1.Status = ComparisonStatus.Old; block1.UpdateImpact = 0; // block removed, no update impact } else { block1.Status = ComparisonStatus.Unchanged; block1.UpdateImpact = 0; block2.Status = ComparisonStatus.Unchanged; block2.UpdateImpact = 0; } } progressCalculatingStatus.Report(new ProgressData(50, "Calculating file status (2/2)...")); foreach (var file in filesInNewPackage) { cancellationToken.ThrowIfCancellationRequested(); if (!filesInOldPackage.TryGetValue(file.Key, out _)) { file.Value.Status = ComparisonStatus.New; file.Value.UpdateImpact = file.Value.Blocks.Sum(b => b.CompressedSize); // sum of all blocks file.Value.SizeDifference = file.Value.UncompressedSize; } } foreach (var block2KeyValuePair in blocksInPackage2) { cancellationToken.ThrowIfCancellationRequested(); var block2 = block2KeyValuePair.Value; if (!blocksInPackage1.ContainsKey(block2KeyValuePair.Key)) { block2.Status = ComparisonStatus.New; block2.UpdateImpact = block2.CompressedSize; } } var duplicates1 = new Dictionary <string, IList <AppxFile> >(); var duplicates2 = new Dictionary <string, IList <AppxFile> >(); progressDuplicates.Report(new ProgressData(0, "Finding duplicates...")); using (var md5 = MD5.Create()) { foreach (var file in filesInOldPackage.Values) { cancellationToken.ThrowIfCancellationRequested(); var hash = string.Join(Environment.NewLine, file.Blocks.Select(b => b.Hash)); var allBlocksHash = System.Text.Encoding.ASCII.GetString(md5.ComputeHash(System.Text.Encoding.ASCII.GetBytes(hash))); if (!duplicates1.TryGetValue(allBlocksHash, out var list)) { list = new List <AppxFile>(); duplicates1[allBlocksHash] = list; } list.Add(file); } foreach (var file in filesInNewPackage.Values) { cancellationToken.ThrowIfCancellationRequested(); var hash = string.Join(System.Environment.NewLine, file.Blocks.Select(b => b.Hash)); var allBlocksHash = System.Text.Encoding.ASCII.GetString(md5.ComputeHash(System.Text.Encoding.ASCII.GetBytes(hash))); if (!duplicates2.TryGetValue(allBlocksHash, out var list)) { list = new List <AppxFile>(); duplicates2[allBlocksHash] = list; } list.Add(file); } } var duplicatedFiles1 = new AppxDuplication { Duplicates = new List <ComparedDuplicate>(), FileCount = duplicates1.Count(d => d.Value.Count > 1) * 2, FileSize = duplicates1.Where(d => d.Value.Count > 1).Sum(d => d.Value[0].UncompressedSize) }; var duplicatedFiles2 = new AppxDuplication { Duplicates = new List <ComparedDuplicate>(), FileCount = duplicates2.Count(d => d.Value.Count > 1) * 2, FileSize = duplicates2.Where(d => d.Value.Count > 1).Sum(d => d.Value[0].UncompressedSize) }; progressDuplicates.Report(new ProgressData(55, "Analyzing duplication impact (1/3)...")); foreach (var file in duplicates1.Where(d => d.Value.Count > 1)) { cancellationToken.ThrowIfCancellationRequested(); var duplicate = new ComparedDuplicate { Files = new List <ComparedDuplicateFile>() }; foreach (var df in file.Value) { var mdf = new ComparedDuplicateFile { Name = df.Name, PossibleSizeReduction = df.UncompressedSize, PossibleImpactReduction = df.Blocks.Sum(d => blocksInPackage1[d.Hash].CompressedSize) }; duplicate.Files.Add(mdf); } duplicate.PossibleSizeReduction = duplicate.Files[0].PossibleSizeReduction * (duplicate.Files.Count - 1); duplicate.PossibleImpactReduction = duplicate.Files[0].PossibleImpactReduction * (duplicate.Files.Count - 1); duplicatedFiles1.Duplicates.Add(duplicate); } progressDuplicates.Report(new ProgressData(70, "Analyzing duplication impact (2/3)...")); foreach (var file in duplicates2.Where(d => d.Value.Count > 1)) { cancellationToken.ThrowIfCancellationRequested(); var duplicate = new ComparedDuplicate { Files = new List <ComparedDuplicateFile>() }; foreach (var df in file.Value) { var mdf = new ComparedDuplicateFile { Name = df.Name, PossibleSizeReduction = df.UncompressedSize, PossibleImpactReduction = df.Blocks.Sum(d => blocksInPackage2[d.Hash].CompressedSize) }; duplicate.Files.Add(mdf); } duplicate.PossibleSizeReduction = duplicate.Files[0].PossibleSizeReduction * (duplicate.Files.Count - 1); duplicate.PossibleImpactReduction = duplicate.Files[0].PossibleImpactReduction * (duplicate.Files.Count - 1); duplicatedFiles2.Duplicates.Add(duplicate); } progressDuplicates.Report(new ProgressData(85, "Analyzing duplication impact (3/3)...")); duplicatedFiles1.PossibleImpactReduction = duplicatedFiles1.Duplicates.Sum(d => d.PossibleImpactReduction); duplicatedFiles1.PossibleSizeReduction = duplicatedFiles1.Duplicates.Sum(d => d.PossibleSizeReduction); duplicatedFiles2.PossibleImpactReduction = duplicatedFiles2.Duplicates.Sum(d => d.PossibleImpactReduction); duplicatedFiles2.PossibleSizeReduction = duplicatedFiles2.Duplicates.Sum(d => d.PossibleSizeReduction); cancellationToken.ThrowIfCancellationRequested(); progressRemainingCalculation.Report(new ProgressData(0, "Analyzing changed files...")); var changedFiles = new ChangedFiles { // Shared parameters UpdateImpact = filesInNewPackage.Values.Where(b => b.Status == ComparisonStatus.Changed).SelectMany(b => b.Blocks).Sum(b => b.UpdateImpact), ActualUpdateImpact = blocksInPackage2.Values.Where(b => b.Status == ComparisonStatus.Changed).Sum(b => b.UpdateImpact), SizeDifference = filesInNewPackage.Values.Where(b => b.Status == ComparisonStatus.Changed).Sum(b => b.SizeDifference), FileCount = filesInOldPackage.Values.Count(b => b.Status == ComparisonStatus.Changed), // Old package OldPackageFiles = filesInOldPackage.Values.Where(f => f.Status == ComparisonStatus.Changed).ToList(), OldPackageFileSize = filesInOldPackage.Values.Where(b => b.Status == ComparisonStatus.Changed).Sum(b => b.UncompressedSize), OldPackageBlockCount = filesInOldPackage.Values.Where(b => b.Status == ComparisonStatus.Changed).Sum(b => b.Blocks.Count), OldPackageBlockSize = filesInOldPackage.Values.Where(b => b.Status == ComparisonStatus.Changed).SelectMany(b => b.Blocks).Sum(b => b.CompressedSize), // New package NewPackageFiles = filesInNewPackage.Values.Where(f => f.Status == ComparisonStatus.Changed).ToList(), NewPackageFileSize = filesInNewPackage.Values.Where(b => b.Status == ComparisonStatus.Changed).Sum(b => b.UncompressedSize), NewPackageBlockCount = filesInNewPackage.Values.Where(b => b.Status == ComparisonStatus.Changed).Sum(b => b.Blocks.Count), NewPackageBlockSize = filesInNewPackage.Values.Where(b => b.Status == ComparisonStatus.Changed).SelectMany(b => b.Blocks).Sum(b => b.CompressedSize) }; cancellationToken.ThrowIfCancellationRequested(); progressRemainingCalculation.Report(new ProgressData(25, "Analyzing added files...")); var addedFiles = new AddedFiles { UpdateImpact = filesInNewPackage.Values.Where(b => b.Status == ComparisonStatus.New).SelectMany(b => b.Blocks).Sum(b => b.UpdateImpact), ActualUpdateImpact = blocksInPackage2.Values.Where(b => b.Status == ComparisonStatus.New).Sum(b => b.UpdateImpact), BlockCount = blocksInPackage2.Values.Count(b => b.Status == ComparisonStatus.New), BlockSize = blocksInPackage2.Values.Where(b => b.Status == ComparisonStatus.New).Sum(b => b.CompressedSize), FileCount = filesInNewPackage.Values.Count(s => s.Status == ComparisonStatus.New), SizeDifference = filesInNewPackage.Values.Where(s => s.Status == ComparisonStatus.New).Sum(f => f.SizeDifference), FileSize = filesInNewPackage.Values.Where(s => s.Status == ComparisonStatus.New).Sum(f => f.UncompressedSize), Files = filesInNewPackage.Values.Where(f => f.Status == ComparisonStatus.New).ToList() }; cancellationToken.ThrowIfCancellationRequested(); progressRemainingCalculation.Report(new ProgressData(50, "Analyzing deleted files...")); var deletedFiles = new DeletedFiles { FileSize = filesInOldPackage.Values.Where(s => s.Status == ComparisonStatus.Old).Sum(f => f.UncompressedSize), SizeDifference = filesInOldPackage.Values.Where(s => s.Status == ComparisonStatus.Old).Sum(f => f.SizeDifference), FileCount = filesInOldPackage.Values.Count(s => s.Status == ComparisonStatus.Old), BlockSize = blocksInPackage1.Values.Where(b => b.Status == ComparisonStatus.Old).Sum(b => b.CompressedSize), BlockCount = blocksInPackage1.Values.Count(b => b.Status == ComparisonStatus.Old), ActualUpdateImpact = blocksInPackage1.Values.Where(s => s.Status == ComparisonStatus.Old).Sum(f => f.UpdateImpact), Files = filesInOldPackage.Values.Where(f => f.Status == ComparisonStatus.Old).ToList() }; deletedFiles.UpdateImpact = deletedFiles.ActualUpdateImpact; cancellationToken.ThrowIfCancellationRequested(); progressRemainingCalculation.Report(new ProgressData(75, "Analyzing unchanged files...")); var unchangedFiles = new UnchangedFiles { FileCount = filesInNewPackage.Values.Count(b => b.Status == ComparisonStatus.Unchanged), BlockCount = blocksInPackage2.Values.Count(b => b.Status == ComparisonStatus.Unchanged), BlockSize = blocksInPackage2.Values.Where(b => b.Status == ComparisonStatus.Unchanged).Sum(b => b.CompressedSize), FileSize = filesInNewPackage.Values.Where(b => b.Status == ComparisonStatus.Unchanged).Sum(b => b.UncompressedSize), Files = filesInOldPackage.Values.Where(f => f.Status == ComparisonStatus.Unchanged).ToList() }; cancellationToken.ThrowIfCancellationRequested(); progressRemainingCalculation.Report(new ProgressData(90, "Please wait...")); var comparisonResult = new UpdateImpactResults { OldPackageLayout = new AppxLayout { FileSize = filesInOldPackage.Sum(f => f.Value.UncompressedSize), FileCount = filesInOldPackage.Count, BlockSize = blocksInPackage1.Sum(f => f.Value.CompressedSize), BlockCount = blocksInPackage1.Count, Layout = new PackageLayout { Blocks = this.GetChartForBlocks(filesInOldPackage), Files = this.GetChartForFiles(filesInOldPackage) } }, NewPackageLayout = new AppxLayout { FileSize = filesInNewPackage.Sum(f => f.Value.UncompressedSize), FileCount = filesInNewPackage.Count, BlockSize = blocksInPackage2.Sum(f => f.Value.CompressedSize), BlockCount = blocksInPackage2.Count, Layout = new PackageLayout { Blocks = this.GetChartForBlocks(filesInNewPackage), Files = this.GetChartForFiles(filesInNewPackage) } }, OldPackageDuplication = duplicatedFiles1, NewPackageDuplication = duplicatedFiles2, UpdateImpact = blocksInPackage2.Where(b => b.Value.Status == ComparisonStatus.New).Sum(b => b.Value.UpdateImpact) + blocksInPackage1.Sum(b => b.Value.UpdateImpact), ChangedFiles = changedFiles, DeletedFiles = deletedFiles, AddedFiles = addedFiles, UnchangedFiles = unchangedFiles }; comparisonResult.OldPackageLayout.Size = comparisonResult.OldPackageLayout.BlockSize + filesInOldPackage.Values.Sum(f => f.HeaderSize); comparisonResult.NewPackageLayout.Size = comparisonResult.NewPackageLayout.BlockSize + filesInNewPackage.Values.Sum(f => f.HeaderSize); comparisonResult.SizeDifference = comparisonResult.AddedFiles.SizeDifference + comparisonResult.ChangedFiles.SizeDifference + comparisonResult.DeletedFiles.SizeDifference; comparisonResult.ActualUpdateImpact = comparisonResult.UpdateImpact; return(comparisonResult); }