1414using Microsoft . CodeAnalysis . CSharp ;
1515using Microsoft . CodeAnalysis . Text ;
1616using Xunit ;
17+ using Xunit . Abstractions ;
1718
1819namespace System . Text . Json . SourceGeneration . UnitTests
1920{
@@ -133,7 +134,10 @@ public static CSharpGeneratorDriver CreateJsonSourceGeneratorDriver(Compilation
133134#endif
134135 }
135136
136- public static JsonSourceGeneratorResult RunJsonSourceGenerator ( Compilation compilation , bool disableDiagnosticValidation = false )
137+ public static JsonSourceGeneratorResult RunJsonSourceGenerator (
138+ Compilation compilation ,
139+ bool disableDiagnosticValidation = false ,
140+ ITestOutputHelper ? logger = null )
137141 {
138142 var generatedSpecs = ImmutableArray < ContextGenerationSpec > . Empty ;
139143 var generator = new JsonSourceGenerator
@@ -144,6 +148,19 @@ public static JsonSourceGeneratorResult RunJsonSourceGenerator(Compilation compi
144148 CSharpGeneratorDriver driver = CreateJsonSourceGeneratorDriver ( compilation , generator ) ;
145149 driver . RunGeneratorsAndUpdateCompilation ( compilation , out Compilation outCompilation , out ImmutableArray < Diagnostic > diagnostics ) ;
146150
151+ if ( logger is not null )
152+ {
153+ foreach ( Diagnostic diagnostic in outCompilation . GetDiagnostics ( ) . Concat ( diagnostics ) )
154+ {
155+ logger . WriteLine ( diagnostic . ToString ( ) ) ;
156+ }
157+
158+ foreach ( var tree in outCompilation . SyntaxTrees )
159+ {
160+ LogGeneratedCode ( tree , logger ) ;
161+ }
162+ }
163+
147164 if ( ! disableDiagnosticValidation )
148165 {
149166 outCompilation . GetDiagnostics ( ) . AssertMaxSeverity ( DiagnosticSeverity . Info ) ;
@@ -831,6 +848,59 @@ internal static void AssertMaxSeverity(this IEnumerable<Diagnostic> diagnostics,
831848 {
832849 Assert . DoesNotContain ( diagnostics , diagnostic => diagnostic . Severity > maxSeverity ) ;
833850 }
851+
852+ private static void LogGeneratedCode ( SyntaxTree tree , ITestOutputHelper logger )
853+ {
854+ logger . WriteLine ( FileSeparator ) ;
855+ logger . WriteLine ( $ "{ tree . FilePath } content:") ;
856+ logger . WriteLine ( FileSeparator ) ;
857+ using NumberedSourceFileWriter lineWriter = new ( logger ) ;
858+ tree . GetRoot ( ) . WriteTo ( lineWriter ) ;
859+ lineWriter . WriteLine ( string . Empty ) ;
860+ }
861+
862+ private static readonly string FileSeparator = new string ( '=' , 140 ) ;
863+
864+ private sealed class NumberedSourceFileWriter : TextWriter
865+ {
866+ private readonly ITestOutputHelper _logger ;
867+ private readonly StringBuilder _lineBuilder = new StringBuilder ( ) ;
868+ private int _lineNumber ;
869+
870+ internal NumberedSourceFileWriter ( ITestOutputHelper logger )
871+ {
872+ _logger = logger ;
873+ }
874+
875+ public override Encoding Encoding => Encoding . Unicode ;
876+
877+ public override void WriteLine ( string ? value )
878+ {
879+ _logger . WriteLine ( $ "{ ++ _lineNumber , 6 } : { _lineBuilder } { value } ") ;
880+ _lineBuilder . Clear ( ) ;
881+ }
882+
883+ public override void Write ( string ? value )
884+ {
885+ if ( value is null )
886+ {
887+ return ;
888+ }
889+
890+ if ( value . EndsWith ( "\r \n " , StringComparison . Ordinal ) )
891+ {
892+ WriteLine ( value . Substring ( 0 , value . Length - 2 ) ) ;
893+ }
894+ else if ( value . EndsWith ( "\n " , StringComparison . Ordinal ) )
895+ {
896+ WriteLine ( value . Substring ( 0 , value . Length - 1 ) ) ;
897+ }
898+ else
899+ {
900+ _lineBuilder . Append ( value ) ;
901+ }
902+ }
903+ }
834904 }
835905
836906 public record struct DiagnosticData (
0 commit comments