【问题标题】:How to use automapper with convertusing and a condition?如何将自动映射器与转换和条件一起使用?
【发布时间】:2020-07-22 03:15:35
【问题描述】:

我们在 .net 核心中使用 automapper 将视图模型映射到 dto。对于 datetime,我们希望将 utc 保存到我们的数据库中,但对于用户,我们希望显示本地时区。 这与这样的 ConvertUsing 配合得很好:

CreateMap<CreateAgendaItemViewModel, AgendaItemDto>()
.ForMember(dest => dest.StartDateTime, opt => opt.ConvertUsing(new ToUtcTimeConverter()))
.ReverseMap()
.ForMember(dest => dest.StartDateTime, opt => opt.ConvertUsing(new ToLocalTimeConverter()))

到目前为止,如果您总是想更改时间,那就太好了。但是,可能只设置了日期而不设置时间(因为它是全天事件),我们希望将时间保持为如下所示:2020-04-09 00:00:00.0000000。我们在模型中有一个布尔值,指示它是否确实是一整天的事件。我们如何调节皈依者?

我们已经尝试过使用条件的 MapFrom,但它不能进行转换。我们也试过这个,但它最终没有被映射,或者被映射到 UTC 时间。

.ForMember(dest => dest.StartDateTime, opt => { opt.Condition(src => !src.AllDayEvent); opt.ConvertUsing(new ToUtcTimeConverter()); })

【问题讨论】:

  • 试试PreCondition。检查the execution plan
  • @LucianBargaoanu PreCondition 如何解决这个问题?她只想在满足条件时使用 ValueConverter,否则使用默认映射。我不知道这在 AutoMapper 中是否可行。
  • PreCondition 将允许您完全跳过转换器。如果这不是重点,您可以控制分配的内容,所以就这样做吧。
  • @LucianBargaoanu 好的,但是前提条件跳过了一个属性,它根本不会被映射。这就是问题所在,只有当源对象的另一个属性为真时,它才应该使用自定义 ValueConverter 进行映射。否则它应该使用默认转换但不跳过该属性。我在 Automapper 文档中找不到这样做的方法。
  • 你需要一个值解析器。

标签: c# datetime asp.net-core-mvc automapper


【解决方案1】:

感谢 cmets 中的可能解决方案。我尝试了自定义 valueconvert,但最终每种类型的转换都有很多类,而我们有多个源和目标请求相同的解决方案。那不是我想要的。 但我也发现 convertUsing with a condition 不是解决这个问题的方法。 这就是我解决检查和映射的方法:

 CreateMap<AgendaItemViewModel, AgendaItemDto>()
.ForMember(dest => dest.StartDateTime, opt => opt.MapFrom(src => src.AllDayEvent ? src.StartDateTime : src.StartDateTime.ToUniversalTime()))
.ReverseMap()
.ForMember(dest => dest.StartDateTime, opt => opt.MapFrom(src => src.AllDayEvent ? src.StartDateTime : src.StartDateTime.ToLocalTimeZoneTime()))

所以 ToUniversalTimeZone 是 DateTime 扩展,我创建了我们自己的 ToLocalTimeZoneTime 扩展。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-06-13
    • 1970-01-01
    • 1970-01-01
    • 2012-02-04
    • 1970-01-01
    相关资源
    最近更新 更多