ASP.NET MVC依赖注入Unity与WCF服务 - 工作示例解决方案

Eli*_*m99 4 asp.net-mvc wcf dependency-injection unity-container

我正在寻找使用Unity并调用WCF服务的ASP.NET MVC Web应用程序的工作示例.我已经看了很多关于如何向WCF服务添加依赖注入的解释,但坦率地说,我在这里有点过头了.我也不熟悉WCF服务.

我目前正在为我们的ASP.NET MVC应用程序使用Unity with Contructor injection,但到目前为止我们还没有使用任何WCF Web服务.计划是开始使用Web服务,我对如何将Unity与它们合并感到困惑.

我会喜欢一个很好的工作样本,我可以通过它来更好地了解如何去做.

Dar*_*rov 12

我会尽力为你提供一些指导.

让我们假设你有一个现有的产品WCF服务,这个服务是这样定义的(我们不关心实现,目前并不重要,你可以按照自己的意愿实现它,不同于硬编码值,通过SQL数据库)和ORM,在云上消费另一项服务):

[DataContract]
public class Product
{
    [DataMember]
    public int Id { get; set; }

    [DataMember]
    public string Name { get; set; }
}

[ServiceContract]
public interface IProductsService
{
    [OperationContract]
    Product Get(int id);
}
Run Code Online (Sandbox Code Playgroud)

现在,在ASP.NET MVC应用程序中,第一步是通过指向WSDL向它添加服务引用.这将生成代理客户端类.

接下来,您可以将Unity.Mvc3NuGet包添加到MVC应用程序中

然后在你的Application_Start配置容器中(显然,这个配置可以外部化为一个单独的方法,以避免使用它混乱你的Global.asax):

protected void Application_Start()
{
    AreaRegistration.RegisterAllAreas();

    RegisterGlobalFilters(GlobalFilters.Filters);
    RegisterRoutes(RouteTable.Routes);

    var container = new UnityContainer();
    container
        .RegisterType<IProductsService, ProductsServiceClient>()
        .Configure<InjectedMembers>()
        .ConfigureInjectionFor<ProductsServiceClient>(new InjectionConstructor("*"));
    DependencyResolver.SetResolver(new UnityDependencyResolver(container));
}
Run Code Online (Sandbox Code Playgroud)

IProductsServiceProducsServiceClient在这个配置中使用是当你输入的Web服务定义生成代理类.

从现在开始,事情变得微不足道:

public class HomeController : Controller
{
    private readonly IProductsService _productsService;
    public HomeController(IProductsService productsService)
    {
        _productsService = productsService;
    }

    public ActionResult Index()
    {
        var product = _productsService.Get(1);
        return View(product);
    }
}
Run Code Online (Sandbox Code Playgroud)

和一些相应的索引视图:

@model Product
<div>
    @Html.DisplayFor(x => x.Name)
</div>
Run Code Online (Sandbox Code Playgroud)

正如您在此示例中所看到的,由于IProductsService抽象,HomeController完全与服务的任何具体实现分离.在今天的Global.asax中,您决定使用WCF(ProductsServiceClient),但明天您可以决定使用一些完全不同的实现.只需对DI容器配置进行一次更改,即可切换实施.由于这种弱耦合,您的控制器可以完全单元测试.

这里要认识到的重要一点是,您的业务是Product类和IProductsService接口.这反映了您的域名.这是MVC中的M. 实施可能会发生变化,但这应该保持不变,否则您错误地确定了您的业务需求,从长远来看可能是灾难性的.

备注:本例中没有涉及的一件事,也就是说非常重要,是视图模型的使用.在正确构建的ASP.NET MVC应用程序中,您永远不应将域模型传递给您的视图(在此示例中为Product类).您应该使用视图模型.视图模型是专为满足给定视图要求而设计的类.因此,在现实世界的ASP.NET MVC应用程序中,您将拥有一个ProductViewModel类,Product域模型将在控制器操作中映射到该类,并且此ProductViewModel将传递给视图.这些视图模型应该在MVC项目中定义,与您的域模型相反,它们不可重用,只反映单个视图的特定要求.为了简化域模型和视图模型之间的映射,您可以查看AutoMapper.