IIncrementalGenerator How To: Unit Tests add Additional File? #75338
Answered
by
333fred
FrankKubis
asked this question in
Q&A
-
I try to add a File with BuildAction "AdditonalFile" to the UnitTest of my IIncrementalGenerator. I did follow the cookbock. Relevant parts of my IncrementalGenerator: public class ApplicationModelIncrementalSourceGenerator : IIncrementalGenerator
{
private const string ModelFileName = @"Model.yaml";
public void Initialize(IncrementalGeneratorInitializationContext context)
{
// Model file has to be marked as "AdditionalFile" in build action
var provider = context.AdditionalTextsProvider
// Find the model file
.Where(x => x.Path.EndsWith(ModelFileName))
// Convert the reference into AdditionalFile Type that we use below
.Select((x, cancellationToken) =>
{
var path = x.Path;
var sourceText = x.GetText(cancellationToken);
if (string.IsNullOrEmpty(path) || sourceText is null)
{
return null;
}
return new AdditionalFile(path, sourceText.ToString());
});
// Runs for each change of model
context.RegisterSourceOutput(provider, Execute);
}
private static void Execute(SourceProductionContext context, AdditionalFile? modelFile)
{
}
} I tried to add the file as additional text using this. driver.AddAdditionalTexts([
new InMemoryAdditionalText(@"c:\src\Model.yaml", @"
Alias: ExampleApplication")]); This seems not working, how to add a file for testing? The complete test fact: [Fact]
public void ExpectedFilesGetGenerated()
{
var inputCompilation = CreateCompilation(@"
namespace UnitTest.Generated
{
public class Program
{
public static void Main(string[] args)
{
}
}
}
");
// // Create an instance of the source generator.
var generator = new ApplicationModelIncrementalSourceGenerator();
//
// Create the driver that will control the generation, passing in our generator
var driver = CSharpGeneratorDriver.Create(generator.AsSourceGenerator());
driver.AddAdditionalTexts([
new InMemoryAdditionalText(@"c:\src\Model.yaml", @"
Alias: ExampleApplication")]);
// Run the generation pass
// (Note: the generator driver itself is immutable, and all calls return an updated version of the driver that you should use for subsequent calls)
var generatorDriver = driver.RunGeneratorsAndUpdateCompilation(inputCompilation, out var outputCompilation, out var diagnostics);
var runResult = generatorDriver.GetRunResult();
var generatorResult = runResult.Results.FirstOrDefault();
diagnostics.IsEmpty.Should().BeTrue();
outputCompilation.GetDiagnostics().Should().BeEmpty();
generatorResult.Exception.Should().BeNull();
generatorResult.GeneratedSources.Length.Should().Be(6);
}
private static Compilation CreateCompilation(string source)
{
var assemblyLocation = typeof(Binder).GetTypeInfo().Assembly.Location;
return CSharpCompilation.Create("compilation",
[CSharpSyntaxTree.ParseText(source)],
[MetadataReference.CreateFromFile(assemblyLocation)],
new CSharpCompilationOptions(OutputKind.ConsoleApplication));
} The helper class internal class InMemoryAdditionalText(string path, string content) : AdditionalText
{
private readonly SourceText _content = SourceText.From(content, Encoding.UTF8);
public override string Path { get; } = path;
public override SourceText GetText(CancellationToken cancellationToken = default)
=> _content;
} |
Beta Was this translation helpful? Give feedback.
Answered by
333fred
Oct 2, 2024
Replies: 1 comment
-
You're not saving the results of the Add call. Practically every public api in Roslyn is immutable; if you're not saving the result somewhere, it's a good indicator that you've done something wrong. |
Beta Was this translation helpful? Give feedback.
0 replies
Answer selected by
FrankKubis
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
You're not saving the results of the Add call. Practically every public api in Roslyn is immutable; if you're not saving the result somewhere, it's a good indicator that you've done something wrong.