diff --git a/NAPS2.Lib.Tests/Automation/CommandLineIntegrationTests.cs b/NAPS2.Lib.Tests/Automation/CommandLineIntegrationTests.cs index bf8e8bb26c..bf6ef1e794 100644 --- a/NAPS2.Lib.Tests/Automation/CommandLineIntegrationTests.cs +++ b/NAPS2.Lib.Tests/Automation/CommandLineIntegrationTests.cs @@ -282,6 +282,150 @@ await _automationHelper.RunCommand( AssertRecoveryCleanedUp(); } + [Fact] + public async Task ExistingFile_NoOverwrite_SplitWithPlaceholder() + { + var path = $"{FolderPath}/test$(n).pdf"; + await _automationHelper.RunCommand( + new AutomatedScanningOptions + { + OutputPath = path, + ProfileName = string.Empty, + Split = true, + Verbose = true + }, + new[] { Image1, Image2, Image3 }); + await _automationHelper.WithContainer(container => + { + var profileManager = container.Resolve(); + profileManager.Profiles.Remove(profileManager.Profiles.Where(p => p.IsDefault).First()); + }).RunCommand( + new AutomatedScanningOptions + { + OutputPath = path, + ProfileName = string.Empty, + Split = true, + Verbose = true + }, + new[] { Image1, Image2, Image3 }); + PdfAsserts.AssertImages($"{FolderPath}/test1.pdf", Image1); + PdfAsserts.AssertImages($"{FolderPath}/test2.pdf", Image2); + PdfAsserts.AssertImages($"{FolderPath}/test3.pdf", Image3); + Assert.True(File.Exists($"{FolderPath}/test4.pdf")); + Assert.True(File.Exists($"{FolderPath}/test5.pdf")); + Assert.True(File.Exists($"{FolderPath}/test6.pdf")); + AssertRecoveryCleanedUp(); + } + + [Fact] + public async Task ExistingFile_ForceOverwrite_SplitWithPlaceholder() + { + var path = $"{FolderPath}/test$(n).pdf"; + await _automationHelper.RunCommand( + new AutomatedScanningOptions + { + OutputPath = path, + ForceOverwrite = true, + ProfileName = string.Empty, + Split = true, + Verbose = true + }, + new[] { Image1, Image2, Image3 }); + await _automationHelper.WithContainer(container => + { + var profileManager = container.Resolve(); + profileManager.Profiles.Remove(profileManager.Profiles.Where(p => p.IsDefault).First()); + }).RunCommand( + new AutomatedScanningOptions + { + OutputPath = path, + ForceOverwrite = true, + ProfileName = string.Empty, + Split = true, + Verbose = true + }, + new[] { Image1, Image2, Image3 }); + PdfAsserts.AssertImages($"{FolderPath}/test1.pdf", Image1); + PdfAsserts.AssertImages($"{FolderPath}/test2.pdf", Image2); + PdfAsserts.AssertImages($"{FolderPath}/test3.pdf", Image3); + Assert.False(File.Exists($"{FolderPath}/test4.pdf")); + Assert.False(File.Exists($"{FolderPath}/test5.pdf")); + Assert.False(File.Exists($"{FolderPath}/test6.pdf")); + AssertRecoveryCleanedUp(); + } + + [Fact] + public async Task ExistingFile_NoOverwrite_SplitWithNoPlaceholder() + { + var path = $"{FolderPath}/test.pdf"; + await _automationHelper.RunCommand( + new AutomatedScanningOptions + { + OutputPath = path, + ProfileName = string.Empty, + Split = true, + Verbose = true + }, + new[] { Image1, Image2, Image3 }); + await _automationHelper.WithContainer(container => + { + var profileManager = container.Resolve(); + profileManager.Profiles.Remove(profileManager.Profiles.Where(p => p.IsDefault).First()); + }).RunCommand( + new AutomatedScanningOptions + { + OutputPath = path, + ProfileName = string.Empty, + Split = true, + Verbose = true + }, + new[] { Image1, Image2, Image3 }); + PdfAsserts.AssertPageCount(1, $"{FolderPath}/test.1.pdf"); + PdfAsserts.AssertPageCount(1, $"{FolderPath}/test.2.pdf"); + PdfAsserts.AssertPageCount(1, $"{FolderPath}/test.3.pdf"); + Assert.True(File.Exists($"{FolderPath}/test.4.pdf")); + Assert.True(File.Exists($"{FolderPath}/test.5.pdf")); + Assert.True(File.Exists($"{FolderPath}/test.6.pdf")); + AssertRecoveryCleanedUp(); + } + + [Fact] + public async Task ExistingFile_ForceOverwrite_SplitWithNoPlaceholder() + { + var path = $"{FolderPath}/test.pdf"; + await _automationHelper.RunCommand( + new AutomatedScanningOptions + { + OutputPath = path, + ForceOverwrite = true, + ProfileName = string.Empty, + Split = true, + Verbose = true + }, + new[] { Image1, Image2, Image3 }); + await _automationHelper.WithContainer(container => + { + var profileManager = container.Resolve(); + profileManager.Profiles.Remove(profileManager.Profiles.Where(p => p.IsDefault).First()); + }).RunCommand( + new AutomatedScanningOptions + { + OutputPath = path, + ForceOverwrite = true, + ProfileName = string.Empty, + Split = true, + Verbose = true + }, + new[] { Image1, Image2, Image3 }); + PdfAsserts.AssertPageCount(1, $"{FolderPath}/test.1.pdf"); + PdfAsserts.AssertPageCount(1, $"{FolderPath}/test.2.pdf"); + PdfAsserts.AssertPageCount(1, $"{FolderPath}/test.3.pdf"); + Assert.False(File.Exists($"{FolderPath}/test.4.pdf")); + Assert.False(File.Exists($"{FolderPath}/test.5.pdf")); + Assert.False(File.Exists($"{FolderPath}/test.6.pdf")); + AssertRecoveryCleanedUp(); + } + [Fact] public async Task MultipleImages() { diff --git a/NAPS2.Lib/Automation/AutomatedScanning.cs b/NAPS2.Lib/Automation/AutomatedScanning.cs index f9f7c389fe..d008044bd9 100644 --- a/NAPS2.Lib/Automation/AutomatedScanning.cs +++ b/NAPS2.Lib/Automation/AutomatedScanning.cs @@ -585,7 +585,8 @@ private async Task DoExportToPdf(string path, bool email) } }; int digits = (int) Math.Floor(Math.Log10(_scanList.Count)) + 1; - string actualPath = _placeholders.Substitute(path, true, scanIndex++, _scanList.Count > 1 ? digits : 0); + string actualPath = _placeholders.Substitute(path, !_options.ForceOverwrite, + scanIndex++, _scanList.Count > 1 ? digits : 0, !_options.ForceOverwrite); op.Start(actualPath, _placeholders, fileContents, _config.Get(c => c.PdfSettings), _ocrParams); if (!await op.Success) { diff --git a/NAPS2.Lib/Pdf/SavePdfOperation.cs b/NAPS2.Lib/Pdf/SavePdfOperation.cs index e149b1c3d8..89d15aac5c 100644 --- a/NAPS2.Lib/Pdf/SavePdfOperation.cs +++ b/NAPS2.Lib/Pdf/SavePdfOperation.cs @@ -72,8 +72,8 @@ public bool Start(string fileName, Placeholders placeholders, ICollectionWhether to use an auto-incrementing file number to make the file name unique. /// The file number will be at least one bigger than this value. /// The minimum number of digits in the file number. Only has an effect if the path does not contain a numeric placeholder like $(n) or $(nnn). + /// Whether to increment the placeholder number to make the file name unique. /// The file path with substitutions. [return: NotNullIfNotNull("filePath")] public abstract string? Substitute(string? filePath, bool incrementIfExists = true, int numberSkip = 0, - int autoNumberDigits = 0); + int autoNumberDigits = 0, bool incrementPlaceholderIfExists = true); public class StubPlaceholders : Placeholders { public override string? Substitute(string? filePath, bool incrementIfExists = true, int numberSkip = 0, - int autoNumberDigits = 0) => filePath; + int autoNumberDigits = 0, bool incrementPlaceholderIfExists = true) => filePath; } public class EnvironmentPlaceholders : Placeholders { public override string? Substitute(string? filePath, bool incrementIfExists = true, int numberSkip = 0, - int autoNumberDigits = 0) + int autoNumberDigits = 0, bool incrementPlaceholderIfExists = true) { if (filePath == null) return null; return Environment.ExpandEnvironmentVariables(filePath); @@ -99,7 +100,7 @@ public DefaultPlaceholders(DateTime? dateTimeOverride = null) [return: NotNullIfNotNull("filePath")] public override string? Substitute(string? filePath, bool incrementIfExists = true, int numberSkip = 0, - int autoNumberDigits = 0) + int autoNumberDigits = 0, bool incrementPlaceholderIfExists = true) { if (filePath == null) { @@ -116,7 +117,7 @@ public DefaultPlaceholders(DateTime? dateTimeOverride = null) if (match.Success) { result = NumberPlaceholderPattern.Replace(result, ""); - result = SubstituteNumber(result, match.Index, match.Length - 3, numberSkip, true); + result = SubstituteNumber(result, match.Index, match.Length - 3, numberSkip, incrementPlaceholderIfExists); } else if (autoNumberDigits > 0) {