From fe1d3a75518fd23076499e920b4e5fc122fd90c5 Mon Sep 17 00:00:00 2001 From: Mark Date: Fri, 19 Feb 2021 15:37:13 +0900 Subject: [PATCH] Show progress indicator when finding files and decrypting --- src/QnapBackupDecryptor.Console/Program.cs | 66 +++++++++++++++------- src/QnapBackupDecryptor.Core/JobMaker.cs | 4 +- 2 files changed, 48 insertions(+), 22 deletions(-) diff --git a/src/QnapBackupDecryptor.Console/Program.cs b/src/QnapBackupDecryptor.Console/Program.cs index 97b333a..61ebc1b 100644 --- a/src/QnapBackupDecryptor.Console/Program.cs +++ b/src/QnapBackupDecryptor.Console/Program.cs @@ -1,6 +1,8 @@ using CommandLine; using QnapBackupDecryptor.Core; +using Spectre.Console; using System.Collections.Concurrent; +using System.Collections.Generic; using System.Diagnostics; using System.IO; using System.Threading.Tasks; @@ -18,32 +20,60 @@ static void Main(string[] args) private static void Run(Options options) { + // Double check delete is wanted if (Prompts.EnsureDeleteWanted(options) == false) return; + // get the password byes var password = Prompts.GetPassword(options); + var decryptResults = new ConcurrentBag(); + var deleteResults = new ConcurrentBag(); + var decryptJobs = new List(); + var sw = Stopwatch.StartNew(); - var decryptJobs = JobMaker.GetDecryptJobs(options.EncryptedSource, options.OutputDestination, options.Overwrite, options.IncludeSubfolders); + // get file list to process + AnsiConsole.Status() + .Start("Getting Files...", ctx => + { + ctx.Spinner(Spinner.Known.SimpleDots); + ctx.SpinnerStyle(Style.Parse("green")); - var decryptResults = new ConcurrentBag(); - var deleteResults = new ConcurrentBag(); + decryptJobs = JobMaker.GetDecryptJobs(options.EncryptedSource, options.OutputDestination, options.Overwrite, options.IncludeSubfolders); + }); - Parallel.ForEach(decryptJobs, - job => + // decrypt & delete if requested + AnsiConsole.Progress() + .Columns(new ProgressColumn[] + { + new TaskDescriptionColumn(), + new ProgressBarColumn(), + new PercentageColumn(), + new SpinnerColumn(Spinner.Known.SimpleDots) + }) + .Start(ctx => { - if (job.IsValid == false) - decryptResults.Add(new DecryptResult(job.EncryptedFile, job.OutputFile, job.IsValid, job.ErrorMessage)); - else - { - var result = OpenSsl.Decrypt(new FileInfo(job.EncryptedFile.FullName), password, new FileInfo(job.OutputFile.FullName)); - decryptResults.Add(new DecryptResult(job.EncryptedFile, job.OutputFile, result.IsSuccess, result.ErrorMessage)); - - // Delete encrypted file only if success and option chosen - if (result.IsSuccess && options.RemoveEncrypted) - deleteResults.Add(FileService.TryDelete(job.EncryptedFile)); - } + var progressTask = ctx.AddTask("[green]Decrypting Files[/]"); + + Parallel.ForEach( + decryptJobs, + job => + { + if (job.IsValid == false) + decryptResults.Add(new DecryptResult(job.EncryptedFile, job.OutputFile, job.IsValid, job.ErrorMessage)); + else + { + var decryptionResult = OpenSsl.Decrypt(new FileInfo(job.EncryptedFile.FullName), password, new FileInfo(job.OutputFile.FullName)); + decryptResults.Add(new DecryptResult(job.EncryptedFile, job.OutputFile, decryptionResult.IsSuccess, decryptionResult.ErrorMessage)); + + // Delete encrypted file only if success and option chosen + if (decryptionResult.IsSuccess && options.RemoveEncrypted) + deleteResults.Add(FileService.TryDelete(job.EncryptedFile)); + + progressTask.Increment(((double)decryptResults.Count / (double)decryptJobs.Count) * (double)100); + } + }); }); sw.Stop(); @@ -51,10 +81,6 @@ private static void Run(Options options) Output.ShowResults(decryptResults, deleteResults, options.Verbose, sw.Elapsed); } - } - - - } diff --git a/src/QnapBackupDecryptor.Core/JobMaker.cs b/src/QnapBackupDecryptor.Core/JobMaker.cs index fffdd9d..1684ae2 100644 --- a/src/QnapBackupDecryptor.Core/JobMaker.cs +++ b/src/QnapBackupDecryptor.Core/JobMaker.cs @@ -40,7 +40,7 @@ private static FileJob GetJob(FileInfo encrytedFile, FileInfo outputFile, bool o if (outputFile.Exists & overwrite == false) return new FileJob(encrytedFile, outputFile, false, "Output file already exists, use --overwrite to overwrite files."); - if (outputFile.Exists & outputFile.Attributes == FileAttributes.ReadOnly) + if (outputFile.Exists & outputFile.Attributes.HasFlag(FileAttributes.ReadOnly)) return new FileJob(encrytedFile, outputFile, false, "Cannot write to output file - it's ReadOnly in the file system."); if (OpenSsl.IsOpenSslEncrypted(encrytedFile) == false) @@ -60,7 +60,7 @@ private static List GetJobs(DirectoryInfo encrytedFolder, DirectoryInfo if (encrytedFolder.Exists == false) return new List { new FileJob(encrytedFolder, outputFolder, false, "Encrypted folder doesn't exist") }; - if (outputFolder.Exists & outputFolder.Attributes == FileAttributes.ReadOnly) + if (outputFolder.Exists & outputFolder.Attributes.HasFlag(FileAttributes.ReadOnly)) return new List { new FileJob(encrytedFolder, outputFolder, false, "Cannot write to output folder - it's ReadOnly in the file system.") }; var fileInfos = encrytedFolder.EnumerateFiles("*.*", includeSubfolders ? SearchOption.AllDirectories : SearchOption.TopDirectoryOnly);