从实体到DTO(检索仅在DB上的信息)

本文关键字:DB 信息 实体 DTO 检索 | 更新日期: 2023-09-27 18:10:55

我有域类(说EventoSottomissione)与一些信息。然后我有DTO(说EventoSottomissioneDTO)具有相同的信息和与持久性相关的东西(即EventoSottomissioneEventoSottomissioneDTO都具有EventCode属性,但只有EventoSottomissioneDTO具有IdEvent属性)。

现在假设我有一个方法Delete,将从数据库中删除一些事件。这个方法是从我的领域层调用的,因此,这忽略了持久层和DTO,因此Delete将采用EventoSottomissioneIEnumerableDbSet确实要取EventoSottomissioneDTOIEnumerable

所以,在Delete方法中要做的第一件事是"转换"IEnumerable<EventoSottomissione>IEnumerable<EventoSottomissioneDTO>,但我不能简单地使用AutoMapper(例如:如何填充IdEvent属性-此信息仅在DB上)

我的Delete方法是这样的

public bool Delete(IEnumerable<T> entities) // typeof(T) is EventoSottomissione
{
    // get all eventCode from entities collection
    var listOfCodes = (from p in entities.Cast<EventoSottomissione>().ToList<EventoSottomissione>()
                     select p.EventCode).Distinct();
    // using the list of eventCode I can create list  EventoSottomissioneDTO (with even IdEvent)
    IEnumerable<EventoSottomissioneDTO> listOfDto = (from _db in Context.CatalogoEventi
                                            where listOfCodes.Contains(_db.EventCode)
                                            select _db).ToList<EventoSottomissioneDTO>();
    DbSet.RemoveRange(listOfDto);      
    return Context.SaveChanges() > 0;
}

这是工作,但我发现这个解决方案真的很可怕。我怎样才能以更优雅的方式做每件事?

从实体到DTO(检索仅在DB上的信息)

首先,dto与EF层(持久化)有什么关系?dto通常是域实体的投影,使它们更"可序列化",并消除与持久层相关的"噪声"(例如,导航属性,它可能导致循环序列化问题),不应该被安全性或其他应用程序逻辑暴露的属性,等等)。
要回答你的问题,我们必须了解移除的收入参数是什么?从你的代码中,我假设你正在删除所有具有EventCode的实体,实际上是在listOfCodes .
想象一下使用你当前API的人:应该在类型T的对象中填充什么属性?T型到底是什么?删除过滤逻辑会使用与PK无关的属性(我想是IdEvent)吗?返回bool是什么意思?是说所有东西都被删除了还是别的什么?它能打碎任何人的大脑,对吧?
那么,您想通过IdEvent删除还是想坚持当前逻辑并删除listOfCodes中出现的具有EventCode的所有实体?如果你想通过EventCode删除,那么当然,如果你不使用任何实体框架。扩展后,您必须通过listOfCodes获得所有实体,然后删除所有这些实体,就像您已经完成的那样。只需传递更合适的参数,如IEnumerable<EventCodeType> eventCodes,因为当前通用的IEnumerable<T> entities对使用您的API的任何人都没有任何意义。此外,我将方法名称更改为DeleteByEventCodes之类的东西。
或者你可以使用EntityFramework。使用.Delete(expression)扩展和删除所需的实体。但是不要调用.SaveChanges(),因为当你调用.Delete(expression)时,这个库会调用JIT,这就是我不太喜欢它的原因,因为它打破了EF的一些设计概念。
所以主要的想法是重新设计当前的API:将方法名称和传入参数更改为更合适的名称。然后你的代码将更容易理解和使用。