gpt4 book ai didi

nhibernate - 使用 ViewModels 而不是实体时的 DRY 策略

转载 作者:行者123 更新时间:2023-12-03 09:53:23 26 4
gpt4 key购买 nike

我们的很多页面都使用自定义 View 模型,这些模型本质上是 NHibernate 映射实体的缩减版本。

当您拥有一组全局实体时,重用以实体为中心的小块业务逻辑非常简单,因为可以将逻辑添加到实体中。然而,一旦我们有了 View 特定的 View 模型,这就变得更难了。

这是一个人为的例子:

// Entity
public class Sale : Entity
{
public Guid Id { get; set; }
public decimal Tax { get; set; }
public decimal SalePrice { get; set; }
public int TotalPrice
{
get { return Tax + SalePrice; }
}
... more properties ...
}

// View model
public class SaleView
{
public Guid Id { get; set; }
public decimal Tax { get; set; }
public decimal SalePrice { get; set; }
}

public class Controller
{
public Action ViewSale(Guid id)
{
return Session.Query<Sale>()
.Where(x => x.Id == id)
.Select(x => new SaleView
{
Id = x.Id,
Tax = x.Tax,
SalePrice = x.SalePrice
});
}
}

在此示例中,您使用什么策略来重用当前在实体中执行的“TotalPrice”计算?

您可以在某处将“TotalPrice”设为静态方法,并让它接受税收和销售价格作为参数,但这会导致代码非常丑陋、不灵活,尤其是随着属性数量和属性之间关系的增长。您可以创建一个单独的“TotalPriceCalculator”类,但要处理 ViewModel,它需要接受实体和 View 模型都实现的接口(interface)。这将导致重复代码的激增,因为我们现在必须将每个属性写出三次。还能做什么?

最佳答案

您可以定义一个总价政策,您可以将其注入(inject)到您的实体和 View 模型中。您注入(inject)总价政策的事实使其更加灵活。您可以轻松实现其他政策。它看起来像这样:

public interface ITotalPricePolicy
{
decimal TotalPrice(decimal tax, decimal salesPrice);
}

public class TotalPricePolicy : ITotalPricePolicy
{
public decimal TotalPrice(decimal tax, decimal salesPrice)
{
return tax + salesPrice;
}
}

public class Sale : Entity
{
public Guid Id { get; set; }
public decimal Tax { get; set; }
public decimal SalePrice { get; set; }

public decimal TotalPrice(ITotalPricePolicy totalPricePolicy)
{
return totalPricePolicy.TotalPrice(Tax, SalePrice);
}
}

public class SaleViewModel
{
private readonly ITotalPricePolicy _totalPricePolicy;

public SaleViewModel(ITotalPricePolicy totalPricePolicy)
{
_totalPricePolicy = totalPricePolicy;
}

public Guid Id { get; set; }
public decimal Tax { get; set; }
public decimal SalePrice
{
get { return _totalPricePolicy.TotalPrice(Tax, SalePrice); }
}
}

public class HomeController : Controller
{
private readonly ITotalPricePolicy _totalPricePolicy;

public HomeController(ITotalPricePolicy totalPricePolicy)
{
_totalPricePolicy = totalPricePolicy;
}

public Action ViewSale(Guid id)
{
return Session.Query<Sale>()
.Where(x => x.Id == id)
.Select(x => new SaleView(_totalPricePolicy)
{
Id = x.Id,
Tax = x.Tax
});
}
}

关于nhibernate - 使用 ViewModels 而不是实体时的 DRY 策略,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17510172/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com