diff --git a/CHANGELOG.md b/CHANGELOG.md index c0426f9..060a2c1 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,9 @@ Represents the **NuGet** versions. +## v1.0.8 +- *Fixed:* Added comparison context where reporting a file update as a result of using `ExpectNoChanges`. + ## v1.0.7 - *Fixed:* `CodeGenerator` now supports inheritance as intended; new `CreateAsync` added to enable. - *Fixed:* The `CodeGeneratorArgsBase.ConfigFileName` per script `IRootConfig` instance included within `CodeGenStatistics` per script item execution to enable access from `CodeGenerator`. diff --git a/src/OnRamp/CodeGenerator.cs b/src/OnRamp/CodeGenerator.cs index b1b3505..5f7b9de 100644 --- a/src/OnRamp/CodeGenerator.cs +++ b/src/OnRamp/CodeGenerator.cs @@ -9,6 +9,7 @@ using System.Diagnostics; using System.IO; using System.Linq; +using System.Text; using System.Threading.Tasks; namespace OnRamp @@ -272,16 +273,20 @@ protected virtual void OnCodeGenerated(CodeGenOutputArgs outputArgs, CodeGenStat } } + // Convert content into lines. + var lines = ConvertContentIntoLines(outputArgs.Content); + statistics.LinesOfCodeCount += lines.Length; + // Create or override. if (fi.Exists) { - var prevContent = File.ReadAllText(fi.FullName); - if (string.Compare(outputArgs.Content, prevContent, StringComparison.InvariantCulture) == 0) + var diff = CompareLines(File.ReadAllLines(fi.FullName), lines); + if (diff is null) statistics.NotChangedCount++; else { if (Scripts!.CodeGenArgs!.ExpectNoChanges) - throw new CodeGenChangesFoundException($"File '{fi.FullName}' would be updated as a result of the code generation."); + throw new CodeGenChangesFoundException($"File '{fi.FullName}' would be updated as a result of the code generation:{Environment.NewLine}{diff}"); if (!Scripts!.CodeGenArgs!.IsSimulation) File.WriteAllText(fi.FullName, outputArgs.Content); @@ -301,12 +306,47 @@ protected virtual void OnCodeGenerated(CodeGenOutputArgs outputArgs, CodeGenStat statistics.CreatedCount++; outputArgs.Script.Root?.CodeGenArgs?.Logger?.LogWarning(" Created -> {fileName}", fi.FullName); } + } + + /// + /// Converts the content into lines. + /// + private static string[] ConvertContentIntoLines(string? content) + { + if (content is null) + return Array.Empty(); + + string line; + var lines = new List(); + using var sr = new StringReader(content); + while ((line = sr.ReadLine()) is not null) + { + lines.Add(line); + } - if (outputArgs.Content != null) + return lines.ToArray(); + } + + /// + /// Compare the existing lines with the new lines and return initial differences. + /// + private static string? CompareLines(string[] previousLines, string[] newLines) + { + var sb = new StringBuilder(); + if (previousLines.Length != newLines.Length) + sb.AppendLine($"> Line count difference; previous '{previousLines.Length}' versus generated '{newLines.Length}'."); + + for (int i = 0; i < Math.Min(previousLines.Length, newLines.Length); i ++) { - using var s = new StringReader(outputArgs.Content); - for (; s.ReadLine() != null; statistics.LinesOfCodeCount++) { } + if (string.Compare(previousLines[i], newLines[i], StringComparison.InvariantCulture) != 0) + { + sb.AppendLine($"> Line '{i + 1}' content difference (no further lines compared);"); + sb.AppendLine($"> previous--> {previousLines[i]}"); + sb.AppendLine($"> generated-> {newLines[i]}"); + } } + + return sb.Length > 0 ? sb.ToString() : null; } /// diff --git a/src/OnRamp/OnRamp.csproj b/src/OnRamp/OnRamp.csproj index 9a82d54..cebb6bc 100644 --- a/src/OnRamp/OnRamp.csproj +++ b/src/OnRamp/OnRamp.csproj @@ -4,7 +4,7 @@ Exe netstandard2.1 OnRamp - 1.0.7 + 1.0.8 true Avanade Avanade diff --git a/tests/OnRamp.Test/CodeGenConsoleTest.cs b/tests/OnRamp.Test/CodeGenConsoleTest.cs index d99b7fc..f5ee543 100644 --- a/tests/OnRamp.Test/CodeGenConsoleTest.cs +++ b/tests/OnRamp.Test/CodeGenConsoleTest.cs @@ -6,6 +6,7 @@ using System; using System.Text; using System.Runtime.InteropServices; +using System.Linq; namespace OnRamp.Test { @@ -144,9 +145,26 @@ public async Task A400_ErrorExpectNoChanges() if (Directory.Exists("XA400")) Directory.Delete("XA400", true); + // Run and it should fail as it cannot create. var c = new CodeGenConsole(); var r = await c.RunAsync("-s ValidEntity.yaml -c Data/ValidEntity.yaml -enc -p Directory=XA400 -p AppName=Zzz -a \"OnRamp.Test, Version=1.2.3.0, Culture=neutral, PublicKeyToken=null\""); Assert.AreEqual(3, r); + + // Run again and let it make changes. + c = new CodeGenConsole(); + r = await c.RunAsync("-s ValidEntity.yaml -c Data/ValidEntity.yaml -p Directory=XA400 -p AppName=Zzz -a \"OnRamp.Test, Version=1.2.3.0, Culture=neutral, PublicKeyToken=null\""); + Assert.AreEqual(0, r); + + // Change the file and run again and it should fail as it cannot update. + var files = Directory.GetFiles("XA400"); + Assert.AreNotEqual(0, files.Length); + + var content = File.ReadAllText(files.Last()); + File.WriteAllText(files.Last(), content + "X"); + + c = new CodeGenConsole(); + r = await c.RunAsync("-s ValidEntity.yaml -c Data/ValidEntity.yaml -enc -p Directory=XA400 -p AppName=Zzz -a \"OnRamp.Test, Version=1.2.3.0, Culture=neutral, PublicKeyToken=null\""); + Assert.AreEqual(3, r); } [Test]