4

我正在尝试使用 WCF Ninject 扩展将 Ninject 添加到 WCF 服务。

我收到错误:

提供的服务类型无法作为服务加载,因为它没有默认(无参数)构造函数。要解决此问题,请将默认构造函数添加到类型,或将类型的实例传递给主机。

该服务具有 Ninject 服务主机工厂:

<%@ ServiceHost Language="C#" Debug="true" CodeBehind="SchedulingSvc.svc.cs"
          Service="Scheduling.SchedulingSvc"
          Factory="Ninject.Extensions.Wcf.NinjectWebServiceHostFactory" %>

global.asax 文件继承自 NinjectHttpApplication 并且 CreateKernel 返回一个带有 NinjectModule 的新内核:

public class Global : NinjectHttpApplication
{
    protected override IKernel CreateKernel()
    {
        return new StandardKernel(new NinjectServiceModule());
    }
}

忍者模块:

public class NinjectServiceModule : NinjectModule
{
    public override void Load()
    {
        this.Bind<ISchedulingService>().To<SchedulingSvc>();
        this.Bind<ISchedulingBusiness>().To<SchedulingBusiness>();
    }
}

带有构造函数注入的服务:

[AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
public class SchedulingSvc : ISchedulingService
{
    private ISchedulingBusiness _SchedulingBusiness = null;

    public SchedulingSvc(ISchedulingBusiness business)
    {
        _SchedulingBusiness = business;
    }

    public CalendarEvent[] GetCalendarEvents()
    {
        var calendarEvents = _SchedulingBusiness.GetCalendarEvents();
        return calendarEvents;
    }
    ...
}

具有属性注入的服务:

[AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
public class SchedulingSvc : ISchedulingService
{
    [Inject] public ISchedulingBusiness _SchedulingBusiness { get; set; }

    public SchedulingSvc()
    {
    }

    public CalendarEvent[] GetCalendarEvents()
    {
        var calendarEvents = _SchedulingBusiness.GetCalendarEvents();
        return calendarEvents;
    }
    ...
}

如果我使用构造函数注入,我会得到帖子顶部提到的错误。如果我尝试使用属性注入,则 _ScheduleBusiness 始终为空。

我错过了什么?

4

3 回答 3

1

我唯一一次遇到该错误消息是在尝试使用拦截器时(通过使用 Ninject.Extensions.Interceptor 库和/或 Castle DynamicProxy。)这是不喜欢带参数的构造函数的部分。

否则,这应该可以正常工作。您似乎没有使用任何拦截器,所以我可以问一下这样做的目的是什么?:

this.Bind<ServiceHost>().To<NinjectServiceHost>();

我假设您在这里使用某种自定义服务主机,但是对于您要执行的操作而言,这不是必需的。使上述代码正常工作所需要做的就是:

1:服务标记中的 Factory 属性(你有这个) 2:你的内核中绑定的构造函数依赖项(你有这个)

我现在有这个确切的设置工作,所以我认为你的 NinjectServiceHost 中的某些东西导致了这个问题并试图附加某种拦截器。

于 2013-06-20T20:08:43.697 回答
1

好的,我认为应该这样做。您的 Ninject 设置可能已关闭。我以前也遇到过这种情况,因为有几种“方法”可以设置它,但其中一些并不总是有效。

我看到您正在使用 AspNet 兼容模式并通过 Web 项目托管它。您使用的是 Ninject.Web,对吗?您实际上不需要让您的 Global 从 Ninject 继承。从 Global 中删除所有 Ninject 引用和代码,并摆脱您的 NinjectServiceModule。如果你从 NuGet 安装了 Ninject.Web,它应该在你的 App_Start 文件夹中创建了文件“ NinjectWebCommon.cs ”。这是您设置绑定的地方,如下所示:

    private static IKernel CreateKernel()
    {
        var settings = new NinjectSettings { InjectNonPublic = true };

        var kernel = new StandardKernel(settings);
        kernel.Bind<Func<IKernel>>().ToMethod(ctx => () => new Bootstrapper().Kernel);
        kernel.Bind<IHttpModule>().To<HttpApplicationInitializationHttpModule>();

        RegisterServices(kernel);

        return kernel;
    }

    /// <summary>
    /// Load your modules or register your services here!
    /// </summary>
    /// <param name="kernel">The kernel.</param>
    private static void RegisterServices(IKernel kernel)
    {
        kernel.Bind<AdminHelper>().ToSelf().InRequestScope();
        kernel.Bind<AuditHelper>().ToSelf().InRequestScope();
        kernel.Bind<ErrorHelper>().ToSelf().InRequestScope();
        kernel.Bind<GoalHelper>().ToSelf().InRequestScope();
    }

它应该已经有这些方法,其中大多数已经填充,所以你应该只需要用你的绑定填充 RegisterServices。

您的 App_Start 文件夹中还应该有一个NinjectWeb.cs。您不必对其进行更改;只需验证它是否存在。

之后,您可能还需要将服务标记中的 Factory 属性改回“Ninject.Extensions.Wcf.NinjectServiceHostFactory”。或者两者都试一下,看看有什么用。

这两个文件就是让 Ninject 工作所需的全部内容。尝试沿着这条路线走;我有预感它会解决它。

于 2013-06-25T13:54:31.887 回答
0

我认为 WCF(或任何 Web)服务需要一个无参数的构造函数来实例化服务。由于您提供了参数化构造函数,Ninject 可能无法初始化您的服务。

请。也请参阅此链接 http://social.msdn.microsoft.com/Forums/vstudio/en-US/550d82eb-a2bc-4c08-b846-e3fb1b966457/no-parameterless-constructor-error-in-wcf

于 2013-06-19T18:23:32.080 回答