DDD领域驱动设计批评文集
做强化自测题获得“软件方法建模师”称号
《软件方法》各章合集
1.2 建模工作流
1.2.4 不了解ABCD的危害
1.2.4.1 思维颠倒
如果软件开发人员对以上的“A-业务建模”、“B-需求”、“C-分析”、“D-设计”工作流没有概念,就会把软件开发工作分为“写代码”和“写文档”两部分,产出的工件通通称为“设计”或者“文档”。
这时候,如果问开发人员在做什么,他可能回答“我在做设计”、“我在写文档”。其实,此时他的大脑可能正在思考组织的流程(A-业务建模),或者在思考系统有什么功能性能(B-需求),或者在思考系统要封装的领域概念之间的关系(C-分析),但他通通回答成“在做设计”、“在写文档”。
“设计”一词滥用,意味着在开发人员的脑子里,“设计”就是“代码以外的各种东西”。好,这时候有人又忽悠一句口号:代码就是设计,也就是说,代码就是“代码以外的各种东西”。这么一推导,就变成了:代码就是一切。
“文档”一词滥用,背后的认知错误和“设计”一样。不过,“文档”还暗示,它和“代码”可能是不同的工具写出来的。在Visual Studio、Android Studio、Eclipse……中写出来的叫“代码”,在Word、wiki、Visio、EA……中写或者画出来的叫“文档”。
开发人员对ABCD工作流缺乏认识以及把工件简单分割为“代码”和“文档(设计)”,意味着背后存在有意无意的误解:“文档”只不过是“代码”的一种比较概要或比较形象的表现形式,不同的“文档”代表着“代码”的不同视图,可以让开发人员从不同的视角观察代码,如图1-6所示。
图1-6 误解:文档只是代码的视图
这种误解不只“普通”的开发人员会有。Martin Fowler所著的UML畅销书《UML精粹》,认为UML有三种用法:草稿、蓝图和编程语言,也是把UML模型看作是代码的视图——这是错误的。虽然Martin Fowler在某些社群的心目中如大神一般存在,但是从Fowler写作的其他书籍《重构》、《企业应用架构模式》、《分析模式》等可以知道,他的研究工作集中在“C-分析”和“D-设计”工作流,在“A-业务建模”和“B-需求”方面研究不多,他在这方面的言论,应谨慎看待。
更危险的是,把“文档”当作“代码”的视图还会带来思维颠倒:先拍脑袋实现,然后再从实现反推其他工作流的内容,导致其他工作流变成徒有形式的装模作样。我们来看几段我经历过的思维颠倒的对话:
★对话一
我:这个不应该是系统的用例(如果读者不理解什么叫“用例”,就先把它理解为“功能”好了)。
开发人员:是的!我都写好了,运行一下给你看,这个系统确实提供了这个用例。
是否系统的用例应该从“A-业务建模”来推理,通过愿景、业务序列图等步骤的推理后,觉得应该有,系统就有,不该有就没有。不能说,我写好了代码,所以就应该有。
★对话二
我:这两个类的关系不应该是泛化,而是关联。
开发人员:是泛化,不信我打开代码给你看(或:逆向工程转出类图给你看)。
是否泛化关系应该从领域逻辑来判断,领域逻辑不是,那就不是,代码就不应该那样写。不能先写好代码“人是猪的一种”(肯定编译通过),再用写好的代码来证明“人是猪的一种”。
★对话三
我:A聚合(组合)B,这个不太对。
开发人员:对的,你看我代码,A是聚合根,其他对象调用时要先找A,存取数据也是以它作为单元。
同对话二,是否聚合(组合)关系应该从领域逻辑来判断,领域逻辑不是,那就不是,代码就不应该那样写。
了解了ABCD工作流的概念,我们就知道,不同工作流产出的工件之间的区别不在于形式,而在于思考和表达的内容。
这时候,就不要再说“我在写文档”这种话了。“我在写文档”只是表达“我正在用文档编辑工具在工作”,没有其他意义。你在写什么文档?“A-业务建模”?“B-需求”?“C-分析”?我不写,我画图,难道不可以吗?我不写不画,我用语音清楚地表达组织的流程,难道不可以吗?我用Word编码(即D-设计),难道不可以吗?我用C#写需求(即B-需求),难道不可以吗?
更有意义的说法应该是“我在做业务建模”、“我在做需求”……如果说“文档”二字可以给你带来不可替代的快感,可以说“我在写业务建模文档”。
1.2.4.2 伪创新泛滥