DI for Functions- work–part 2
Let’s begin with tests – we need to have a class with multiple functions that have multiple [FromServices} parameter. Like
public bool TestMyFunc1([FromServices] TestDI1 t1, [FromServices] TestDI2 t2, int x, int y)
public bool TestMyFunc2([FromServices] TestDI1 t12, int x, int y)
// more others
Because there are multiple functions, I need to generate very fast – so Incremental generators to the rescue . They are documented here : https://github.com/dotnet/roslyn/blob/main/docs/features/incremental-generators.md . And a good tutorial is to be found at https://andrewlock.net/creating-a-source-generator-part-1-creating-an-incremental-source-generator/ .
Basically, this is the code
IncrementalValuesProvider<MethodDeclarationSyntax> paramDeclarations = context.SyntaxProvider
predicate: static (s, _) => IsSyntaxTargetForGeneration(s),
transform: static (ctx, _) => GetSemanticTargetForGeneration(ctx))
.Where(static m => m is not null)!; // filter out attributed enums that we don’t care about
IncrementalValueProvider<(Compilation, ImmutableArray<MethodDeclarationSyntax>)> compilationAndEnums = context.CompilationProvider.Combine(paramDeclarations.Collect());
and the idea is to find the parameters of the function that has attributes – and one of those is [FromServices] . After that , find the methods that are the parent – and then the class. After that , is simple to generate a constructor with all (distinct) the [FromServices]parameters and construct the similar method with just the non-DI parameters.
Bonus : We can verify if the parameters are null and throw exception
I could do a template for defining , but – wait to see if gain some traction to modify .
You can find the sources at https://github.com/ignatandrei/functionsdi and the NuGet packages ( one with generator, one with [FromServices] ) at https://www.nuget.org/packages/RSCG_FunctionsWithDI and https://www.nuget.org/packages/RSCG_FunctionsWithDI_Base
Leave a Reply