WCF ClaimsAuthenticationManager中的依赖注入

时间:2013-11-03 23:05:46

标签: wcf dependency-injection ninject

我已使用Ninject为我的WCF服务成功配置了DI。每个服务类都有一个构造函数,Ninject在运行时将实例注入其中。

public class MessageService : ServiceBase,IMessageService
    {           
        private readonly IMessageRepository _messageRepository;
        private readonly IMappingEngine _mapper;  // AutoMapper mapping engine

        // Instances injected in constructor by Ninject
        public MessageService(IMessageRepository messageRepository, IMappingEngine mapper)
        {
            _messageRepository = messageRepository;
            _mapper = mapper;
        }     
    ...
}

我的理解是,这是通过告诉Wcf使用NinjectServiceHostFactory来激活服务来实现的。

一切都很好......这是一种享受。

我有许多类库,由wcf服务项目引用。其中一个库具有派生自ClaimsAuthenticationManager的类。它旨在将传入的声明转换为特定于域的声明。 WCF脚手架在运行时将此类实例化为标识管道的一部分。我希望此类使用存储库模式从数据库中获取标识的业务角色。然后,它将创建具有特定于域的声明的新ClaimsIdentity。现在我可以新建一个存储库实例,但我希望Ninject在运行时注入它。我创建了一个带有存储库接口参数的构造函数,完全天真地希望Ninject能够做到这一点。 WCF失败,因为它找不到无参数构造函数。

当我基本上没有引用类库中的Ninject内核时,如何让Ninject注入实例?

我的理解是应该在组合根处创建IoC容器,在我的情况下,它位于WCF服务主机中。因为它是实例化我的类的Wcf管道,所以我无法控制进程以连接依赖项。或者我呢?

1 个答案:

答案 0 :(得分:2)

唯一的方法是在global.asax中以编程方式设置System.IdentityModel.Services.FederatedAuthentication.FederationConfiguration.IdentityConfiguration.ClaimsAuthorizationManager或在WCF调用之前的任何位置。

protected void Application_Start()
{
    ...
    FederatedAuthentication.FederationConfigurationCreated += FederatedAuthentication_FederationConfigurationCreated;
    ...
}

void FederatedAuthentication_FederationConfigurationCreated(object sender, System.IdentityModel.Services.Configuration.FederationConfigurationCreatedEventArgs e)
{
    var cam = DependencyResolver.Current.GetService<ClaimsAuthenticationManager>();  // Instantiate your implementation here using any IoC you want.
    e.FederationConfiguration.IdentityConfiguration.ClaimsAuthenticationManager = cam;
}

如果您使用global.asax,请不要忘记添加到web.config:

<system.serviceModel>
    <serviceHostingEnvironment aspNetCompatibilityEnabled="true" />
</system.serviceModel>