1

我有一些控制器需要 Web 服务连接(MS Dynamics CRM 的一个实例CrmService),我希望控制器通过它们的构造函数接收它。必须使用基于当前登录用户身份的令牌设置 CRM 服务(当用户登录应用程序对 CRM 进行身份验证并可以将返回的令牌存储在 Session 中时)。

我不确定如何最好地使用依赖注入和 Ninject 来提供这个实例。ToMethod()Ninject Func<> 访问 FormsAuth/Session 以获取当前请求(如果经过身份验证则获取令牌)以创建适当的实例似乎有点垃圾。我也不确定如果用户未通过身份验证会发生什么 - 我不需要这些用户能够访问控制器,但控制器将在[Authorize]运行任何过滤器之前实例化,因此必须始终满足依赖关系. 从我读过的内容来看,返回 null 并不理想,无论如何我都必须更改 Ninject 配置才能做到这一点。

我在想也许控制器可以获得一个实例ICrmServiceFactory或其他东西,但如果控制器最终具有其他也直接依赖的依赖项CrmService(并且不想被传递给工厂),这对我没有帮助。

任何有关如何解决此问题的建议将不胜感激。

4

3 回答 3

2

我通常为 IPrincipal 设置一个绑定:

kernel.Bind<IPrincipal>().ToMethod(c => HttpContext.Current.User);

这种方法从来没有真正遇到过问题。

于 2012-08-02T17:57:12.447 回答
2

如果我正确理解了您的问题,那么您的控制器依赖于CrmService并且CrmService需要存储在会话中的一些令牌。

在这种情况下,您可以注入一个CrmTokenProvidertoCrmService并向该类添加一个属性,该类在CrmService.

public class CrmService
{
    public CrmService(CrmTokenProvider tokenProvider)
    {
        this.tokenProvider = tokenProvider;
    }

    public void DoSomeWork() 
    {
        ...
        this.tokenProvider.Token;
        ...
    }
}
于 2012-08-03T09:08:06.610 回答
1

我最终实现了如下:

private static void RegisterServices(IKernel kernel)
{
  kernel.Bind<CrmService>()
          .ToMethod(context =>
          {
            //return unauthenticated instance if user not logged in.
            if (!HttpContext.Current.User.Identity.IsAuthenticated) return new CrmService();

            return GetConnection(HttpContext.Current);

          })
          .InRequestScope();
}

private static CrmService GetConnection(HttpContext ctx)
{
   //get stuff out of session and return service
}
于 2012-08-15T12:06:47.740 回答