使用Ninject(从Windsor移动)的WCF服务问题(InvalidOperationException)

时间:2010-11-01 01:26:03

标签: c# .net wcf ninject ninject-extensions

房子里有任何Ninject专家吗? :) 我最近一直在尝试将我的WCF服务应用程序和Windows窗体客户端应用程序从Castle Windsor依赖注入转换为Ninject。

所有在Win Forms方面都很好,但我遇到了WCF方面的问题。到目前为止,我已经了解到,我认为我需要为Ninject提供WCF扩展,以便将DI与WCF一起使用,我已经完成并引用但仍然遇到一个问题,我相信当我的服务被尝试解决时:

System.InvalidOperationException:类型为“WcfMemberService”,在ServiceHost指令中作为Service属性值提供,或在配置元素system.serviceModel / serviceHostingEnvironment / serviceActivations中提供。 < / p>

我所拥有的代码是我认为正确访问的代码,例如我的WcfMemberService,如下所示:

ServiceModule.cs:

public class ServiceModule : NinjectModule
{
    private IKernel _parentContainer;
    public ServiceModule(IKernel container)
    {
    this._parentContainer = container;
    }

    public override void Load()
    {
    Bind<IDataContextProvider>().To<DataContextProvider>()
        .WithConstructorArgument("connectionString", ConfigurationManager.ConnectionStrings["connectionString"].ConnectionString);
    Bind(typeof(IRepository<>)).To(typeof(Repository<>));
    Bind<IServiceLocator>().ToConstant(new NinjectServiceLocator(_parentContainer));
    Bind<IUserService>().To<UserService>();

    // ** WCF Services **
    Bind<Business.Common.Wcf.Services.Contracts.IMemberServiceContract>().To<Business.Common.Wcf.Services.MemberService>().InSingletonScope().Named("WcfMemberService");
    }
}

我做的假设是从我工作的Castle Windsor配置转换时,Named()应该是您的WCF .svc文件声明中的相同条目。所以我做了如下:

<%@ ServiceHost Language="C#" Service="WcfMemberService" Factory="Ninject.Extensions.Wcf.NinjectServiceHostFactory" %>

非常简单,顺便说一句,我从Ninject Wcf Extensions GitHub页面here上的TimeService示例解决方案中采用了这种方法。

任何人都可以看到我在这里做错了,为什么“WcfMemberService”无法解决?它必须是内核中的“WcfMemberService”并在@ServiceHost声明中引用。我看不出还有什么可能是错的。这与我在Castle Windsor中声明它的方式完全相同,除了大致不同的语法,但两者都使用Named()并且都在.svc文件的Service部分中引用该名称。

* 更新 * 我发现如果我不使用Named()方法,只需将@ ServiceHost声明中的服务设为{ {1}}它有效。但我仍然难以理解为什么我不能使用命名服务。感谢。

顺便说一句,我的Ninject模块以这种方式通过Business.Common.Wcf.Services.MemberService, Business.Common.Wcf.Services加载:

Global.asax.cs

1 个答案:

答案 0 :(得分:2)

.Named(string)语法用于条件绑定。例如,如果你有

Bind<IService1>().To<MyService>().Named("MyServiceImpl");
Bind<IService1>().To<DefaultService();

然后DefaultService将作为默认值注入,除非你有以下内容:

class MyForm([Named("MyServiceImpl")] IService1 service){...}

kernel.Get<IService1>(metadata => metadata.Name == "MyServiceImpl");

kernel.Get<IService1>("MyServiceImpl");

如果您没有该类型的默认绑定,并且您只有条件命名绑定,则在尝试创建实例时将获得激活异常。

-Ian