2012-03-15 66 views
0

我使用Unity作为我的DI容器,在解析SignalR集线器时我无法使其工作。有没有人有过这个成功?我已经试过如下:使用UnityContainer作为SignalR依赖关系解析器

public class UnityDependencyResolver : DefaultDependencyResolver 
    { 
     private readonly IUnityContainer _Container; 



    public UnityDependencyResolver (IUnityContainer container) 
      { 
       _Container = container; 
       //edit to add 
       container.RegisterInstance<IJavaScriptMinifier>(NullJavaScriptMinifier.Instance); 

      } 

     public override object GetService(Type serviceType) 
     { 
      return base.GetService(serviceType) ?? _Container.Resolve(serviceType); 
     } 

     public override IEnumerable<object> GetServices(Type serviceType) 
     { 
      return base.GetServices(serviceType) ?? _Container.ResolveAll(serviceType); 
     } 

    } 

,但我发现指示错误无法解析SignalR.Infrastructure.IJavaScriptMinifier

+0

您是否注册过使用Unity的'IJavaScriptMinifier'实现? – 2012-03-15 08:37:02

+0

我发布这个后,我试过,但它感觉像一个黑客。 (我将编辑帖子以显示如何)。我没有明确地使用它,它是一个SignalR接口。 – timDunham 2012-03-15 12:52:51

+0

也许你没有明确地在你的应用程序中使用它。但是如果你的基础设施依赖于它并且SignalR使用'DependencyResolver'来实现'IJavaScriptMinifier'的实现,你需要在你的容器中注册它。我不会将它注册到解析器的构造函数中,而是与您应用程序的应用程序根目录中的所有其他依赖项一起注册。 – 2012-03-15 13:35:45

回答

0

我作为一个有点困惑,为什么你试着先做好基本分辨率统一解析器第二。通常,如果您要用自己的实现来替换基本实现,两者都将解决,但您的应该是第一个,以便返回您的重写类的实例。例如,假设你想覆盖SignalR中的IConnectionIdFactory。您可以创建自己的类,该类继承自给定的接口,然后使用Unity注册它。那么你的依赖解析器应该能够解析给定的依赖关系并返回,而不会触及SignalR解析器。我把一个小的测试应用程序,我的依赖解析器是这样的:

扶养解析器:

public class UnityResolver : DefaultDependencyResolver 
{ 
    private readonly IUnityContainer _container; 
    public UnityResolver(IUnityContainer container) 
    { 
     _container = container; 
    } 

    public override object GetService(Type serviceType) 
    { 
     if (_container.IsRegistered(serviceType)) 
     { 
      return _container.Resolve(serviceType); 
     } 
     return base.GetService(serviceType); 
    } 

    public override IEnumerable<object> GetServices(Type serviceType) 
    { 
     if (_container.IsRegistered(serviceType)) 
     { 
      return _container.ResolveAll(serviceType); 
     } 
     return base.GetServices(serviceType); 
    } 
} 

它来测试我们是否拥有一个分辨率路径Resolve将引发与团结的重要如果不存在,则为例外。

为了完整起见,这里是实现:

ConnectionIDFactory:

public class ConnectionIdFactory : IConnectionIdFactory 
{     
    public string CreateConnectionId(IRequest request) 
    {    
     return Guid.NewGuid().ToString(); 
    } 
} 

报名:

public class Bootstrapper 
{ 
    public static void Pre_Start() 
    { 
     Container.DefaultContainer.Instance.RegisterType(
      typeof(IConnectionIdFactory), 
      typeof(Repositories.ConnectionIdFactory), 
      null, 
      new Microsoft.Practices.Unity.ContainerControlledLifetimeManager()); 

     AspNetHost.SetResolver(new Resolvers.UnityResolver(Container.DefaultContainer.Instance)); 
    } 
} 
+0

感谢您的回复。我最初是在检查我的容器,然后是基类,但一直运行到我提到的'IJavaScriptMinifier'错误。我认为这可能与Unity有关,因为样本(使用Ninject)似乎有效。最后,我认为这可能是SignalR中的一个错误。 – timDunham 2012-03-19 02:22:42

+0

@timDunham不,它不是signalR中的一个bug,如果它不能解决,只是返回null而SignalR会做正确的事情。你看到的错误是来自Unity,而不是来自SignalR。如前所述,Unity会在呼叫中抛出异常,以解决未注册的服务。 – 2012-03-19 03:38:24

0

昨天我通过以下方式解决了这个问题:

注册容器:

AspNetHost.SetResolver(dependencyResolver); 
    DependencyResolver.SetResolver(dependencyResolver); 

解析器:

public class UnityDependencyResolver : DefaultDependencyResolver, IDependencyResolver 
    { 
     private readonly IUnityContainer _container; 

     public UnityDependencyResolver(IUnityContainer container) 
     { 
      _container = container; 
     } 

     #region IDependencyResolver Members 

     public override object GetService(Type serviceType) 
     { 
      try 
      { 
       return _container.Resolve(serviceType); 
      } 
      catch 
      { 
       return base.GetService(serviceType); 
      } 
     } 

     public override IEnumerable<object> GetServices(Type serviceType) 
     { 
      try 
      { 
       return _container.ResolveAll(serviceType); 
      } 
      catch 
      { 
       return base.GetServices(serviceType); 
      } 
     } 

     #endregion 
    } 

枢纽:

public class Chat : Hub 
    { 
     [Dependency] 
     public UserService _userService { get; set; } 

     public void Send(string message) 
     {     
      _userService.SomeMethod();     
     } 
    } 

完美的作品!

+1

使用捕获所有捕获解决异常是不好的,并会降低性能,更好地确定是否可以首先与if分辨率。 – 2012-03-26 10:14:42

+0

感谢您的建议1月,我会在今晚尝试一下,并给您反馈。 – timDunham 2012-03-26 23:36:29

+0

Gary.S - >正确。 Thanx为笔记。 – 2012-03-30 21:29:37