using System.Reflection;
using Abp.Configuration.Startup;
using Abp.Dependency;
using Abp.Events.Bus.Factories;
using Abp.Events.Bus.Handlers;
using Castle.MicroKernel;
using Castle.MicroKernel.Registration;
using Castle.MicroKernel.SubSystems.Configuration;
using Castle.Windsor;
namespace Abp.Events.Bus
{
///
/// Installs event bus system and registers all handlers automatically.
///
internal class EventBusInstaller : IWindsorInstaller
{
private readonly IIocResolver _iocResolver;
private readonly IEventBusConfiguration _eventBusConfiguration;
private IEventBus _eventBus;
public EventBusInstaller(IIocResolver iocResolver)
{
_iocResolver = iocResolver;
_eventBusConfiguration = iocResolver.Resolve();
}
public void Install(IWindsorContainer container, IConfigurationStore store)
{
if (_eventBusConfiguration.UseDefaultEventBus)
{
container.Register(
Component.For().Instance(EventBus.Default).LifestyleSingleton()
);
}
else
{
container.Register(
Component.For().ImplementedBy().LifestyleSingleton()
);
}
_eventBus = container.Resolve();
container.Kernel.ComponentRegistered += Kernel_ComponentRegistered;
}
private void Kernel_ComponentRegistered(string key, IHandler handler)
{
/* This code checks if registering component implements any IEventHandler interface, if yes,
* gets all event handler interfaces and registers type to Event Bus for each handling event.
*/
if (!typeof(IEventHandler).GetTypeInfo().IsAssignableFrom(handler.ComponentModel.Implementation))
{
return;
}
var interfaces = handler.ComponentModel.Implementation.GetTypeInfo().GetInterfaces();
foreach (var @interface in interfaces)
{
if (!typeof(IEventHandler).GetTypeInfo().IsAssignableFrom(@interface))
{
continue;
}
var genericArgs = @interface.GetGenericArguments();
if (genericArgs.Length == 1)
{
_eventBus.Register(genericArgs[0], new IocHandlerFactory(_iocResolver, handler.ComponentModel.Implementation));
}
}
}
}
}