落地微服务遇到第一个问题:服务拆分。Martin Fowler对微服务的定义中其中有一段话:将一个单一应用程序开发为一组小型服务的方法。这段话并没有对”小型服务“做一个清晰的界定,因此我们团队在这里踩了不少坑。
按照业务职能拆分是最常用的一种服务拆分方式,也是我们最开始使用的拆分方式。只要业务需求有清晰的边界就可以定义一个新服务,再由前端+后端团队搭配进行迭代开发,快速响应需求。这种拆分方式的好处是开发、产品甚至市场部都可以定义边界。学习成本低、容易达成共识。
DDD界限上下文把一个业务按照问题划分成3类域:核心域、支撑域、通用域。不同域之间有明显的边界,这条边界就是未来的”小型服务“。这种方案的难点在于需要开发从产品的需求里提取术语,动词,关系等属性,然后组织成不同的域。所以DDD界限上下文的划分不但取决于开发的水平,还取决于产品对需求的理解和表达——这就是DDD倡导的领域专家。
在进行服务拆分时遇到最大的问题:拆分成本过高。出现这个问题的原因是因为没有定义好边界,业务代码紧耦合,导致拆分时需要改动大量的业务逻辑,浪费很多开发和测试时间。服务拆分的正确姿势:只改动调配方式,不改动业务逻辑。所以我们尝试使用四层+DDD方式代替三层+事物脚本的方式组织业务代码。
孵化服务是为了调解服务拆分和运维压力之间的矛盾而出现。在公司发展的过程中我们发现有些业务前期单独成为一个服务,反而浪费服务器资源,增加系统的复杂性,所以我们把这部分业务合并到孵化服务,做好边界,然后等待它破(慢)壳(慢)而(死)出(去)。
服务拆分不应过度关注服务有多微上,更应该关注运维管理能力和基础设施。服务拆分过细,但是基础设施不成熟、运维能力跟不上,完全可以抵消服务拆分带来的收益,得不偿失。