Skip to content

Commit ae9ee36

Browse files
committed
Add support for multiple projects
1 parent 7a7b667 commit ae9ee36

File tree

4 files changed

+65
-16
lines changed

4 files changed

+65
-16
lines changed

src/Foundatio.Mediator.SourceGenerator/DIRegistrationGenerator.cs

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,11 @@ namespace Foundatio.Mediator;
66

77
internal static class DIRegistrationGenerator
88
{
9-
public static void Execute(SourceProductionContext context, List<HandlerInfo> handlers)
9+
public static void Execute(SourceProductionContext context, List<HandlerInfo> handlers, Compilation compilation)
1010
{
11+
var assemblyName = compilation.AssemblyName?.ToIdentifier() ?? Guid.NewGuid().ToString("N").Substring(0, 10);
12+
var className = $"{assemblyName}_MediatorHandlers";
13+
1114
var source = new IndentedStringBuilder();
1215

1316
source.AddGeneratedFileHeader();
@@ -19,18 +22,18 @@ public static void Execute(SourceProductionContext context, List<HandlerInfo> ha
1922
source.AppendLine("using System.Threading;");
2023
source.AppendLine("using System.Threading.Tasks;");
2124
source.AppendLine();
25+
source.AppendLine("[assembly: Foundatio.Mediator.FoundatioHandlerModule]");
26+
source.AppendLine();
2227
source.AppendLine("namespace Foundatio.Mediator;");
2328
source.AppendLine();
2429
source.AppendLine("[DebuggerStepThrough]");
2530
source.AppendLine("[DebuggerNonUserCode]");
2631
source.AppendLine("[ExcludeFromCodeCoverage]");
27-
source.AppendLine("public static partial class ServiceCollectionExtensions");
32+
source.AppendLine($"public static class {className}");
2833
source.AppendLine("{");
2934
source.AppendLine(" [DebuggerStepThrough]");
30-
source.AppendLine(" public static IServiceCollection AddMediator(this IServiceCollection services)");
35+
source.AppendLine(" public static void AddHandlers(this IServiceCollection services)");
3136
source.AppendLine(" {");
32-
source.AppendLine(" services.AddSingleton<IMediator, Mediator>();");
33-
source.AppendLine();
3437
source.AppendLine(" // Register HandlerRegistration instances keyed by message type name");
3538
source.AppendLine(" // Note: Handlers themselves are NOT auto-registered in DI");
3639
source.AppendLine(" // Users can register them manually if they want specific lifetimes");
@@ -59,13 +62,10 @@ public static void Execute(SourceProductionContext context, List<HandlerInfo> ha
5962
source.AppendLine($" {handler.IsAsync.ToString().ToLower()}));");
6063
}
6164

62-
source.AppendLine();
63-
source.AppendLine("return services;");
64-
6565
source.DecrementIndent().DecrementIndent();
6666
source.AppendLine(" }");
6767
source.AppendLine("}");
6868

69-
context.AddSource("ServiceCollectionExtensions.g.cs", source.ToString());
69+
context.AddSource($"{className}.g.cs", source.ToString());
7070
}
7171
}

src/Foundatio.Mediator.SourceGenerator/MediatorGenerator.cs

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -54,18 +54,20 @@ public void Initialize(IncrementalGeneratorInitializationContext context)
5454
.Combine(middleware.Collect())
5555
.Combine(callSites.Collect())
5656
.Combine(interceptionEnabled)
57+
.Combine(context.CompilationProvider)
5758
.Select(static (spc, _) => (
58-
Handlers: spc.Left.Left.Left,
59-
Middleware: spc.Left.Left.Right,
60-
CallSites: spc.Left.Right,
61-
InterceptorsEnabled: spc.Right
59+
Handlers: spc.Left.Left.Left.Left,
60+
Middleware: spc.Left.Left.Left.Right,
61+
CallSites: spc.Left.Left.Right,
62+
InterceptorsEnabled: spc.Left.Right,
63+
Compilation: spc.Right
6264
));
6365

6466
context.RegisterImplementationSourceOutput(compilationAndData,
65-
static (spc, source) => Execute(source.Handlers, source.Middleware, source.CallSites, source.InterceptorsEnabled, spc));
67+
static (spc, source) => Execute(source.Handlers, source.Middleware, source.CallSites, source.InterceptorsEnabled, source.Compilation, spc));
6668
}
6769

68-
private static void Execute(ImmutableArray<HandlerInfo> handlers, ImmutableArray<MiddlewareInfo> middleware, ImmutableArray<CallSiteInfo> callSites, bool interceptorsEnabled, SourceProductionContext context)
70+
private static void Execute(ImmutableArray<HandlerInfo> handlers, ImmutableArray<MiddlewareInfo> middleware, ImmutableArray<CallSiteInfo> callSites, bool interceptorsEnabled, Compilation compilation, SourceProductionContext context)
6971
{
7072
if (handlers.IsDefaultOrEmpty)
7173
return;
@@ -87,7 +89,7 @@ private static void Execute(ImmutableArray<HandlerInfo> handlers, ImmutableArray
8789

8890
HandlerGenerator.Execute(context, handlersWithInfo, interceptorsEnabled);
8991

90-
DIRegistrationGenerator.Execute(context, handlersWithInfo);
92+
DIRegistrationGenerator.Execute(context, handlersWithInfo, compilation);
9193
}
9294

9395
private static EquatableArray<MiddlewareInfo> GetApplicableMiddlewares(ImmutableArray<MiddlewareInfo> middlewares, HandlerInfo handler)
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
namespace Foundatio.Mediator;
2+
3+
[AttributeUsage(AttributeTargets.Assembly)]
4+
public sealed class FoundatioHandlerModuleAttribute : Attribute { }
Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
using System.Reflection;
2+
using Microsoft.Extensions.DependencyInjection;
3+
4+
namespace Foundatio.Mediator;
5+
6+
public static class MediatorExtensions
7+
{
8+
/// <summary>
9+
/// Adds Foundatio.Mediator to the service collection.
10+
/// </summary>
11+
/// <param name="services"></param>
12+
/// <returns>The updated service collection with Foundatio.Mediator registered.</returns>
13+
public static IServiceCollection AddMediator(this IServiceCollection services)
14+
{
15+
services.AddSingleton<IMediator, Mediator>();
16+
17+
foreach (var assembly in AppDomain.CurrentDomain.GetAssemblies())
18+
{
19+
if (!IsAssemblyMarkedWithFoundatioHandlerModule(assembly))
20+
continue;
21+
22+
var moduleType = assembly.GetTypes().FirstOrDefault(t =>
23+
t.IsClass &&
24+
t.IsAbstract &&
25+
t.IsSealed &&
26+
t.Name.EndsWith("_MediatorHandlers"));
27+
28+
var method = moduleType?.GetMethod("AddHandlers", BindingFlags.Public | BindingFlags.Static);
29+
30+
if (method != null)
31+
{
32+
method.Invoke(null, [services]);
33+
}
34+
}
35+
36+
return services;
37+
}
38+
39+
private static bool IsAssemblyMarkedWithFoundatioHandlerModule(Assembly assembly)
40+
{
41+
return assembly.GetCustomAttributes(typeof(FoundatioHandlerModuleAttribute), false).Any();
42+
}
43+
}

0 commit comments

Comments
 (0)