微服务拆分治理最佳实践( 五 )

  • 复杂性可控:每个系统都是单一职责,系统逻辑清晰
  • 系统性能提升上限大:可以针对每个系统做优化,如加缓存
  • 测试环境冲突的问题解决,不会因为多个系统需求并行而抢占环境
  • 数据访问权限收口问题介绍 
    数据访问权限未收口:一个业务的数据库被其余业务应用直接访问,未通过rpc接口将数据访问权限收口到数据拥有方自己的应用 。数据访问逻辑分散,存在业务耦合,阻碍后续迭代和优化 。
    问题产生的背景:之前是单体应用和单体数据库,未进行业务隔离 。在进行数据库拆分和系统拆分时,为解决系统稳定性的问题需快速上线,所以未优化拆分后跨业务访问数据库的情况 。本阶段是对数据库拆分和应用拆分的延伸和补充 。
    微服务拆分治理最佳实践

    文章插图
     
    业务改造前后对比
    改造过程
    1. RPC接口统计(如图一)
     
    进行比对,如程序入口归类和调用的业务DB归类不一致,则认为Dao方法需提供RPC接口
    微服务拆分治理最佳实践

    文章插图
     
    图一
    经统计,应用访问非本业务数据库的位置有260+ 。由于涉及位置多,人工改造成本高、效率较低,且有错改和漏掉的风险,我们采用了开发工具,用工具进行代码生成和批量修改的方式进行改造 。
     
    1. RPC接口生成(如图二)
    • 读取需要生成RPC接口的Dao文件,进行解析
    • 获取文件名称,Dao方法列表,import导包列表等,放入ClassContext上下文
    • 匹配api、rpc文件模板,从classContext内取值替换模板变量,通过package路径生成JAVA文件到指定服务内
    • 批量将服务内Dao名称后缀替换为Rpc服务名,减少人工改动风险,例:SettleRuleDao -> SettleRuleRpc
     
    微服务拆分治理最佳实践

    文章插图
     
    图二
    名词解释:
     
    • ftl:Freemarker模板的文件后缀名,FreeMarker是一个模版引擎,一个基于文本的模板输出工具 。
    • interfaceName:用存放api文件名称
    • className:用于存放serviceImpl文件名称
    • methodList:用于存放方法列表,包含入参、出参、返回值等信息
    • importList:用于存放api和impl文件内其他引用实体的导包路径
    • apiPackage:用于存放生成的Api接口类包名
    • implPackage:用于存放生成的Api实现类包名
    • rpcPackage:用于存放生成的rpc调用类包名
     
    微服务拆分治理最佳实践

    文章插图
     
    代码示例1
    微服务拆分治理最佳实践

    文章插图
     
    代码示例2
     
    1. 灰度方案(如图三)
    • 数据操作统一走RPC层处理,初期阶段RPC层兼顾RPC调用,也有之前的DAO调用,使用开关切换 。
    • RPC层进行双读,进行Api层和Dao层返回结果的比对,前期优先返回Dao层结果,验证无问题后,在全量返回RPC的结果,清除其他业务数据库连接 。
    • 支持开关一键切换,按流量进行灰度,降低数据访问权限收口风险
     
    微服务拆分治理最佳实践

    文章插图
     
    图三
    收益
    1. 业务数据解耦,数据操作统一由各自垂直系统进行,入口统一
    2. 方便后续在接口粒度上增加缓存和降级处理


      推荐阅读