training_ Refactoring from Anemic Domain Model Towards a Rich One (Decoupling the Domain Model from Data Contracts)
attribution for json
暴露的api =》model contract
=》无法对api中已暴露的 方法、模型 进行重构
=》 变成了基石,无法变更。紧密耦合
如何解耦?
Introduce Data transfer Objects(DTOs)
Domain model:
1. all domain logic & knowledge => competitive advantage => focus the most of your efforts
2. => fully encapsulated
3. => a good unit test coverage
4.=> refactor as often as needed => keep it up-to-date with the change in the requirements
5.=> a safe space: sure all data is consistent and no invariants are voilated
external world:
1. a wild space where anything can happen & know nothing about it
2. have no control over it.
communicate:
1. using mesages.
2. messages are guranteed to have a particular structure: data contract (translation : domain model vs data contracts)
3. translation: keep evolvimng domain model & preserve the data contract for backward compatibility
=>refactor domain model, only modify the mappings,but keep the contracts themselves unchanged
output data contracts = DTO: data transfer object
** model/request = input data contracts = DTO: data transfer object
add DTO
1. no validate
2. enum =>string
3. delete virtual keyword
4. properties:
=> Id property: no meaning in it
backward compatibility => add it.
if develop from scratch => delete it
=> remove properties with attribution: JsonIgnore
5. IList => List
6. remove heritage: Entity
from: domain model as output data contract
to: DTO as output data contract (translation : AutoMapper)
不同的接口,返回 相同数据的不同属性 =》不同的DTO
eg:删除 List<PurchaseMovieDto>
1. domain model 中删除 json相关的attribution: JsonConverter, JsonIgnore => 不在 serialize domain model
2. 删除与输出相关的logic=》转移到 translation between domain model and DT0
from
to
=>
重构 domain model ,只需修改 translation 部分即可。对外部的引用 无影响
Fiddle: 模拟 api 请求 =》debugging & composing web traffic
api历史记录 拖拽到 composer区域
修改 =》 正常请求
非法请求 =》 不完整,不cohesion:
没有购买电影,却 花了钱:
=》没有清晰的数据隔离(domain module & data contract),导致 异常数据
=》即使override moneySpent字段,仍旧可能有其他属性漏掉;或者加入新属性后,此部分的修改被遗漏
=》 没有封装好。应该:明确api请求的属性,并且request只包含必须的属性,然后 convert between domain model and data contract
=》创建新的DTO(model/request/response)
from
to
1. DTO 删除无关属性
2. DTO 包含 validation
domin class 删除 validation
from:
to
即使 新增属性,也不会带来 数据完整性 的风险
总结:
提取 input data contracts =》domin model 和 data contract 解耦
1. 去除 数据完整性 风险 =》fix 安全性 风险(create、update 获取的数据 多于 应该操作的数据 =》引入 脏数据、错误数据)
2. 增加了 可读性(what data 需要 what operations)
3. 利于 未来的重构,同时 使得接口 可以向后兼容(domin model 的变动 不会影响 data contract => 调用方 无需修改代码)
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】博客园社区专享云产品让利特惠,阿里云新客6.5折上折
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 微软正式发布.NET 10 Preview 1:开启下一代开发框架新篇章
· DeepSeek R1 简明指南:架构、训练、本地部署及硬件要求
· 没有源码,如何修改代码逻辑?
· NetPad:一个.NET开源、跨平台的C#编辑器
· 面试官:你是如何进行SQL调优的?
2020-05-28 鳥哥的 Linux 私房菜——第七章、Linux 磁碟與檔案系統管理
2018-05-28 .net core 问题:413 Request Entity Too Large nginx