使用DTO与序列化实体 [英] Using DTO vs Serializating entities

查看:294
本文介绍了使用DTO与序列化实体的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在询问问题之前,我已经阅读了主题,但这是一个现在有相当老的线程和用于反序列化实体的许多新方法.

I have already read this thread before asking the question, but this is a pretty old thread and lots of new ways for de serializing the entities are there now.

我的第一个问题是为什么我们不应该在Controller中使用实体?如果唯一的原因是浪费的数据通过网络传输,那应该不成问题,因为有避免这种情况的方法.

My first question is why we should not use the Entities in the Controller ? If the only reason is waste data travelling across the wire then it should not be an issue because there are ways to avoid this.

我使用的是flexjson.JSONSerializer来反序列化实体,而使用Gson.fromJSON()来将json序列化为实体,而不是使用DTO.我的控制器代码如下所示..

I am using flexjson.JSONSerializer for de serializing the entity and Gson.fromJSON() for serializing the json into entity instead of using DTO. My controller code looks like this..

@RequestMapping (value = "", method = RequestMethod.POST, consumes = MediaType.APPLICATION_JSON_VALUE)
@ResponseBody
public void createStream(@RequestBody String  streamData) {
    StreamEntity streamEntity = null;
    try {
        streamEntity = streamService.createStream(streamData);
        logger.info("Created Stream [id=%s, name=%s]", streamEntity.getId(), streamEntity.getStreamName());
    } catch (Exception e) {
        logger.info("Error occured while creating the stream[name=%s]: %s",streamEntity.getStreamName(), e.getMessage());
    }               
}


@RequestMapping (value = "/{id}", method = RequestMethod.GET)
public String fetchStream(@PathVariable(value = "id")final Long id) {
    StreamEntity streamEntity = streamDAO.getById(id);
    String json = StreamEntitySerializer.serialize(streamEntity);       
    return json;
}

在控制器中使用实体的唯一目的是记录日志.代码有什么错误/令人反感吗?

Only purpose of using the entity in controller is for logging. Is there anything wrong/objectionable with the code ?

推荐答案

我认为您有两个问题....

I think you have two questions....

问题1 :为什么不将实体暴露给控制器(又称为表示层):

Question 1: Why not expose the entity to the controller (aka Presentation Layer):

对于大型/复杂项目,在控制器中使用Entity的形式很糟糕,因为这会导致业务逻辑在您的项目中传播.将实体传递到表示层(也称为控制器)后,任何控制器都可以修改和保存数据.通常,多个控制器将需要访问相同的实体.这会导致代码维护陷入困境,因为现在您必须在多个位置维护数据CURD,反腐败和业务逻辑.将您所有的业务逻辑(用于操纵数据的逻辑)移动到一个通用的程序包(也称为域\服务层"),可以使长期维护代码变得更加容易.通过将DTO向上传递到控制器,您将得到更简洁的代码,这更容易测试.这是有关分层体系结构的很好的演示: https://www.youtube.com/watch?v= aZp7C971uC8

For large/complex project its bad form to use the Entity in the controller because it leads to business logic getting spread around your project. Once you pass the entity to your Presentation layer (aka Controllers), any controller can modify and save the data. Typically multiple controllers will need access to the same entities. This leads to code maintenance hell, because now you have to maintain your data CURD, anti-corruption and business logic in multiple places. Moving all your Business logic, the logic that manipulates the data, to a common package (aka Domain\Service Layer) makes maintaining the code much easier long term. By passing DTOs up the stack to the controllers, you'll end up with much cleaner code, that is much easier to test. Here is a good presentation about layered architectures : https://www.youtube.com/watch?v=aZp7C971uC8

其他阅读:

  • http://www.dotnetcurry.com/showarticle.aspx?ID=786
  • http://www.methodsandtools.com/archive/archive.php?id=97

问题2 :为什么不序列化实体,而不是将其转换为DTO并序列化.

Question 2 Why not serialize the entity vs. converting it to a DTO and serializing that.

有很多理由不这样做,但是这里浮现出第一个理由.

There are a ton of reasons not to do this, but here are the frist ones that come to mind.

  • 维护:通过直接公开您的实体,您可以在数据的存储方式与客户获得的数据对象之间建立硬链接.例如,当您需要重命名/删除实体中的字段时会发生什么.更改数据库时会发生什么?如果将实体转换为DTO,则在MySQL和Mongodb之间进行切换会容易得多.

  • Maintenance : By exposing your entities directly, your creating a hard link between how data is stored and the data objects your clients get. For example, what happens when you need to rename/delete a field in your entity. What happens when you change your database? Switching between MySQL and Mongodb gets a lot easier if the entities are getting converted to a DTO.

Testing :模拟DTO实例比休眠实例容易得多

Testing : its much easier to mock a DTO instance than a Hibernate instance

性能:序列化实体可以触发从数据库中拉出所有延迟加载字段,即使您不需要公开该数据也是如此.这会使跟踪性能问题变得困难. DTO使您可以清楚地了解要转换和序列化的字段.同样,由于DTO通常更小,更简单,因此序列化速度更快.

Performance : Serializing an Entity can trigger all the lazy load fields to be pulled from that database, even if you don't need to expose that data. This can make tracking down performance issues hard. DTOs causes you to be explicit about which fields are transformed and serialized. Also since DTOs are normally smaller and simpler, which makes serialization faster.

这篇关于使用DTO与序列化实体的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆