自托管SignalR2多层依赖注入
Self-hosted SignalR2 multi-layer dependency injection
我刚刚使用 Ninject 为我的自托管 SignalR2 项目实现了 DI。
public class NinjectSignalRDependencyResolver : DefaultDependencyResolver
{
private readonly IKernel _kernel;
public NinjectSignalRDependencyResolver(IKernel kernel)
{
_kernel = kernel;
}
public override object GetService(Type serviceType)
{
return _kernel.TryGet(serviceType) ?? base.GetService(serviceType);
}
public override IEnumerable<object> GetServices(Type serviceType)
{
return _kernel.GetAll(serviceType).Concat(base.GetServices(serviceType));
}
}
还有我的创业公司class:
public class Startup
{
public void Configuration(IAppBuilder app)
{
app.UseCors(CorsOptions.AllowAll);
var kernel = new StandardKernel();
var resolver = new NinjectSignalRDependencyResolver(kernel);
kernel.Bind<MyDbContext>().ToSelf();
kernel.Bind<IRealTimeDataEngine>().To<RealTimeDataEngine>().InSingletonScope();
kernel.Bind<IHistoricalDataEngine>().To<HistoricalDataEngine>().InSingletonScope();
kernel.Bind(typeof(IHubConnectionContext<dynamic>)).ToMethod(context =>
resolver.Resolve<IConnectionManager>().GetHubContext<MyHub>().Clients
).WhenInjectedInto<IRealTimeDataEngine>();
var config = new HubConfiguration {Resolver = resolver};
ConfigureSignalR(app, config);
}
public static void ConfigureSignalR(IAppBuilder app, HubConfiguration config)
{
app.MapSignalR(config);
}
}
在我的信号器集线器构造函数中,我希望有一个 IRealTimeDataEngine。
public MyHub(IRealTimeDataEngine realTimeDataEngine, IHistoricalDataEngine historicalDataEngine)
在我的主机(一个控制台应用程序)中,我需要注入相同的 IRealTimeDataEngine。
public DummyProvider(IRealTimeDataEngine realTimeDataEngine)
在我的 Main 方法中,我需要创建一个 DummyProvider 对象。
如果我没记错的话,创建一个新内核不会在两个不同的项目中给我相同的对象,那么我应该如何在我的组合根中请求相同的 IRealTimeDataEngine?
你说得对,每个应用程序只能使用一个内核。这意味着您应该在 Startup
class 之外创建您的内核。这可以通过使用 WebApp.Start
方法的重载调用来实现,例如:
class Program
{
static void Main(string[] args)
{
var kernel = new StandardKernel();
var server = WebApp.Start("http://localhost:8080/", (appBuilder) =>
{
var resolver = new NinjectSignalRDependencyResolver(kernel);
var config = new HubConfiguration {Resolver = resolver};
...
});
...
我刚刚使用 Ninject 为我的自托管 SignalR2 项目实现了 DI。
public class NinjectSignalRDependencyResolver : DefaultDependencyResolver
{
private readonly IKernel _kernel;
public NinjectSignalRDependencyResolver(IKernel kernel)
{
_kernel = kernel;
}
public override object GetService(Type serviceType)
{
return _kernel.TryGet(serviceType) ?? base.GetService(serviceType);
}
public override IEnumerable<object> GetServices(Type serviceType)
{
return _kernel.GetAll(serviceType).Concat(base.GetServices(serviceType));
}
}
还有我的创业公司class:
public class Startup
{
public void Configuration(IAppBuilder app)
{
app.UseCors(CorsOptions.AllowAll);
var kernel = new StandardKernel();
var resolver = new NinjectSignalRDependencyResolver(kernel);
kernel.Bind<MyDbContext>().ToSelf();
kernel.Bind<IRealTimeDataEngine>().To<RealTimeDataEngine>().InSingletonScope();
kernel.Bind<IHistoricalDataEngine>().To<HistoricalDataEngine>().InSingletonScope();
kernel.Bind(typeof(IHubConnectionContext<dynamic>)).ToMethod(context =>
resolver.Resolve<IConnectionManager>().GetHubContext<MyHub>().Clients
).WhenInjectedInto<IRealTimeDataEngine>();
var config = new HubConfiguration {Resolver = resolver};
ConfigureSignalR(app, config);
}
public static void ConfigureSignalR(IAppBuilder app, HubConfiguration config)
{
app.MapSignalR(config);
}
}
在我的信号器集线器构造函数中,我希望有一个 IRealTimeDataEngine。
public MyHub(IRealTimeDataEngine realTimeDataEngine, IHistoricalDataEngine historicalDataEngine)
在我的主机(一个控制台应用程序)中,我需要注入相同的 IRealTimeDataEngine。
public DummyProvider(IRealTimeDataEngine realTimeDataEngine)
在我的 Main 方法中,我需要创建一个 DummyProvider 对象。
如果我没记错的话,创建一个新内核不会在两个不同的项目中给我相同的对象,那么我应该如何在我的组合根中请求相同的 IRealTimeDataEngine?
你说得对,每个应用程序只能使用一个内核。这意味着您应该在 Startup
class 之外创建您的内核。这可以通过使用 WebApp.Start
方法的重载调用来实现,例如:
class Program
{
static void Main(string[] args)
{
var kernel = new StandardKernel();
var server = WebApp.Start("http://localhost:8080/", (appBuilder) =>
{
var resolver = new NinjectSignalRDependencyResolver(kernel);
var config = new HubConfiguration {Resolver = resolver};
...
});
...