我是RESTful服务的新手,并且不得不在一段时间内使用IoC重新连接堆栈,所以这给了我一个轻微的中风。
我有一个WCF服务,看起来像这样(简化):
public interface IESIID
{
[OperationContract]
[WebGet(UriTemplate = "/{guid}/{id}", ResponseFormat = WebMessageFormat.Json,
BodyStyle = WebMessageBodyStyle.Wrapped)]
Message LookupESIID(string guid, string id);
}
public class ESIID : BaseREST<ESI>, IESIID
{
private readonly ITXESIIDService _bllSvc;
public ESIID(ITXESIIDService svc)
{
_bllSvc = svc;
}
public Message LookupESIID(string guid, string id)
{
return GetById(guid, id);
}
private Message GetById(string guid, string id)
{
apiAuthentication = new APIKeyAuthentication();
if (!apiAuthentication.IsValidAPIKey(guid))
return APIError();
//_bllSvc = new TXESIIDService(); <--- WANTING TO AVOID THIS!!!!
var results = _bllSvc.SelectByID(id);
return results.Count == 0 ? NoResults() : CreateMessage(results);
}
}
很好,这非常直截了当。我添加了一个构造函数参数,因为调用了BLL TXESIIDService方法。
所以现在,我已经改变了Ninject的全局文件,现在看起来像这样:
public class Global : NinjectWcfApplication
{
protected override void Application_Start(object sender, EventArgs e)
{
RegisterRoutes();
}
protected override IKernel CreateKernel()
{
return new StandardKernel(new RestServiceModel());
}
private static void RegisterRoutes()
{
RouteTable.Routes.Add(new ServiceRoute("ESIID", new NinjectServiceHostFactory(), typeof(ESIID)));
}
}
并添加了我的模块:
public class RestServiceModel : NinjectModule
{
public override void Load()
{
Bind<ITXESIIDService>().To<TXESIIDService>();
Bind<IDoNotSolicitService>().To<DoNotSolicitService>();
}
}
为了排除故障,我自己添加了NinjectServiceHostFactory
public class NinjectServiceHostFactory : WebServiceHostFactory
{
protected override ServiceHost CreateServiceHost(Type serviceType, Uri[] baseAddresses)
{
var serviceTypeParameter = new ConstructorArgument("serviceType", serviceType);
var baseAddressesParameter = new ConstructorArgument("baseAddresses", baseAddresses);
return KernelContainer.Kernel.Get<NinjectServiceHost>(serviceTypeParameter, baseAddressesParameter);
}
}
当我运行时,我得到一行错误:
return KernelContainer.Kernel.Get<NinjectServiceHost>(serviceTypeParameter, baseAddressesParameter);
不能为空。
显然我在这里遗漏了一些东西,但我无法弄清楚是什么。我现在已经尝试了各种各样的东西,我看到的大多数示例都是针对WCF服务的,而我设法找到的RESTful对于那些熟悉的w / Ninject或IoC常规来说只是有点太过于适应了。
此外,在我的业务和数据层(使用实体框架)中,我也希望在那里实现Ninject,最好是将这些层单独连接起来,还是可以在一个地方?
感谢。
更新1 我已经纠正了绑定问题,但这仍然让我感到愤怒。我正在使用Ninject.Extensions.Wcf和它的轰炸寻找NinjectWcfApplication.cs文件,它看起来并不正确。我使用NuGet为Ninject包含一个包,这可能是版本问题吗?
答案 0 :(得分:2)
这可能是一个错字,但你是否意味着在你的模块中将接口绑定到自己?通常将接口绑定到具体类型。如果Ninject尝试实例化接口类型,它肯定会失败,并且根据Ninject设置的特定错误处理行为,它将抛出或返回null。因此,请确保将模块配置为查找真正的类:
public class RestServiceModel : NinjectModule
{
public override void Load()
{
Bind<ITXESIIDService>().To<TXESIIDService>();
...
}
}
答案 1 :(得分:2)
重写虚拟方法时,总是必须调用基本方法。请参阅Application_Start()
。
答案 2 :(得分:0)
关于你的更新:我是ninject的新手,所以我对旧版本一无所知,但我想你先试用Example Ninject Extensions。如果它们运行,你知道它必须是别的东西。