首页 > 极客资料 博客日记
DDD是软件工程的第一性原理?
2024-08-24 20:30:03极客资料围观26次
本文书接上回《DDD建模后写代码的正确姿势》,关注公众号(老肖想当外语大佬)获取信息:
-
最新文章更新;
-
DDD框架源码(.NET、Java双平台);
-
加群畅聊,建模分析、技术实现交流;
-
视频和直播在B站。
前提
本文需要以系列前文的逻辑链条和结论为前提,如果没有阅读过前文的,可以阅读合集《老肖的领域驱动设计之路》。
故事背景
在2020年,我所在的研发团队维护着一个有近十年历史的SaaS软件系统,而这个系统又是整个公司的主营业务,用户活跃度非常高。当时我们面临的最大挑战就是系统迭代速度远远无法应付客户需求,每次迭代发布都是如履薄冰,我们对系统已经到了完全失控的边缘。
彼时的我,对于领域驱动设计的认知,并不通透,只是隐约感觉DDD能够帮助我们走出这个泥潭,我们非常渴求改变,但缺乏确定性的验证,对于如何改变并走向成功,我们并无把握,甚至我们连如何衡量是否成功,都无法定义出来。在这样的背景下,我们仍然积极地为作出改变做准备:
-
我们对自己的客户和业务有比较充分的了解,技术甚至跟着产品经理一起去拜访客户
-
我们打造了一套定制的开发框架(也就是现在DDD框架的早期原型),以更准确地用代码表达业务
常言道,机会是给有准备的人的,很快这个机会就来了。
一个改变一切的目标
2020年9月,在公司CEO的领导下,我们成立了独立项目组,目标是从零开始,重新打造一套新的SaaS系统,以替换旧的系统,而新系统的核心目标是“保持系统持续的快速迭代”,对你没看错,新系统的核心目标,甚至与产品功能、商业指标没有直接关系。
后来,我们一致认为这个目标,是我们关于软件工程和领域驱动设计的认知质变的起点,它把改变了我们在需求分析、产品设计、系统架构时的核心决策依据,即“可维护性是最重要的事”,这就使得我们在行进过程中,很多决策都与以往有所不同,甚至是相反的。
可以说,这个目标,改变了一切。
有什么不同之处
我相信,大家肯定都会有担忧,把“保持系统持续的快速迭代”作为首要目标,那么商业层面就不考虑了吗?其实并不是这样的,实际上这是一个“既要也要”的要求:
-
要保持系统持续的快速迭代
-
要满足客户需求
与过去不同的地方是当客户需求与可维护性冲突时,我们怎么决策:
-
过去:选择满足客户
-
现状:选择保持可维护性
我们认为这个转变意味着,整个公司的决策逻辑,从短期拓展到长期,追求更长期的利益价值,愿意放弃短期利益,而最考验团队的,就是我们是否真的可以拿到“可维护性”这个长期利益。
DDD是正解
如果大家有读过之前《关于领域驱动设计,大家都理解错了》一文,应该还记得我们关于复杂度的认知:
-
系统复杂度与元素的数量和元素的关系有关;
-
元素的关系对系统复杂度的影响远远大于元素的数量所产生的影响;
因此,我们认为要掌控系统的可维护性,就必须实行分而治之的策略,将复杂度限定在一个个有限的范围内,这个逻辑正好与领域驱动设计的理念不谋而合:
于是,我们在这个由CEO发起的战略级项目中,开启了一段神奇的领域驱动设计落地实践之旅,为了确保最终结果符合预期,我们甚至建立了一条“不准跨域”军规,当然本文重点是推导DDD与软件工程之间的关系,关于“不准跨域”的故事,可以到这里查看:
【DDD落地的铁律军规 - 产品研发都得遵守-哔哩哔哩】 https://b23.tv/ukX0uIx
项目的现状
现今已经到了2024年的后半年,也就是说上述的项目,已经经历了大约四年发展和迭代,中途我本人也因为个人的一些因素离开了团队,最近我特地向朋友了解项目的近况,他也是项目的核心架构师之一,得到了肯定的答复:
-
项目目前仍保持较好的可维护性,迭代没有陷入过去那种困局
-
中间也经历过做一些不太符合长期利益的需求
-
可维护性是靠团队不断坚守业务、模型、代码边界清晰和一致性获得的
-
业务、模型边界清晰不意味着与满足需求对立
再看看目前我自己所带领的团队,经历半年时间把一个项目从失控边缘拯救回来,发展到目前与业务保持一致,迭代维护不再有畏惧和负担感的状态。种种迹象都表明,领域驱动设计是至关重要的。
第一性原理
对于确定不迭代的系统,意味着可维护性的意义就不那么重要了,对于科研类或者其它领域的软件,可能要解决的更重要的问题是“技术难题”等其它维度的问题。
回归到主题,我一直在思考“DDD是软件工程的第一性原理?”这个问题,过往的这些经历,越发让我坚信这一点,但如果让结论更加严谨,需要限定条件如下:
-
软件系统是长期迭代的
-
软件系统是业务向的系统
在这样的背景下,那么标题的答案是肯定的:DDD是软件工程的第一性原理!
后续
如果你认同本文的推导逻辑和观点,那么我相信你一定会期望了解如何掌握DDD,下一期,我们将讲述学习和实践DDD的最佳路径。
标签:
相关文章
最新发布
- Nuxt.js 应用中的 prerender:routes 事件钩子详解
- 【问题解决】Tomcat由低于8版本升级到高版本使用Tomcat自带连接池报错无法找到表空间的问题
- 【FAQ】HarmonyOS SDK 闭源开放能力 —Vision Kit
- 六、Spring Boot集成Spring Security之前后分离认证流程最佳方案
- 《JVM第7课》堆区
- .NET 8 高性能跨平台图像处理库 ImageSharp
- 还在为慢速数据传输苦恼?Linux 零拷贝技术来帮你!
- 刚毕业,去做边缘业务,还有救吗?
- 如何避免 HttpClient 丢失请求头:通过 HttpRequestMessage 解决并优化
- 让性能提升56%的Vue3.5响应式重构之“版本计数”