rpc调用设计经验.md

rpc服务设计

包的划分

  • xxx-api : api给调用方使用

  • xxx-core:业务实现 【具体可以再分吧】

  • xxx-job: 任务

  • xxx-web :部署 maven profile环境【没有统一的配置中心】

接口设计原则:

异常区分

  • rpc框架异常

  • 系统异常

  • 业务异常

接口设计

  • 业务成功

  • 是否重试 【rpc框架配置】

  • 异常处理

基于dubbo的问题

A服务–> B服务

  • 中间网络异常:访问超时

  • B服务宕机:访问超时

  • B服务rpc框架异常:抛出rpc框架异常

  • B服务系统异常:内部异常或者业务异常

dubbo服务为例,默认重试2次,如果有多个提供值默认随机选另外一个,重试之内在调不通调用b服务跑出RpcException,如果配置上mock降级,返回null,看业务

dubbo服务化最佳实战

  • 分包: api,core,web; 建议将服务接口,服务模型,服务异常等均放在API包中

  • 粒度:服务接口尽可能大粒度,每个服务方法应代表一个功能,而不是某功能的一个步骤,否则将面临分布式事务问题,

服务分为:原子服务(订单的crud等),核心(业务)服务,只做查询的查询服务等,接口 入参 出参 要明确 拒绝:Map query(Map)

  • 版本:每个接口都应该有版本号

  • 兼容性: 服务接口增加方法,或服务模型增加字段,可向后兼容(删除方法或删除字段,将不兼容,枚举类型新增字段也不兼容,需通过变更版本号升级)

  • 异常:处理RpcException框架异常,其他的不建议跑出异常,建议定义 code和msg描述问题,查找问题的时候在b服务的机器上面查询,异常带来反序列化等性能问题,

RpcException问题看业务A—->B—>C,业务场景是否可以降级等

  • 服务的配置尽量在服务提供者方面配置完善,考虑该服务相关问题

接口方法的是否重试,并发量,超时时间,是否mock, 复杂均衡策略,失效转移策略,综合接口是查询,幂等等考虑

  • 分布式服务中,所有的服务都可能不可靠,对一个服务内的 调用确保一个服务 的相关业务

  • 服务级别:细粒度服务提供数据操作,不涉及业务的基础服务,以及业务聚合服务,避免分布式事务

分布式rpc调用分析

电商常用的 优惠券,订单服务, 支付服务

  • 流程:

《rpc调用设计经验.md》 Paste_Image.png

三个独立的服务,单独的db库;先来考虑下单的服务调用

  • 下单之前用户必然要先选择优惠券,所以下单之前要调用扣减优惠券走rpc调用(失败到此结果提示扣减优惠券失败),调用成功走用户下单流程

  • 如果下单失败,必然要回滚扣掉的优惠券,怎么操作?走rpc添加优惠券,如果此时优惠券服务超时了就添加不成功了

这里可以利用,消息队列的特性(保证消息至少成功消费一次),发一条添加刚才扣掉的优惠券消息

  • 如果下单成功,就去支付,而此时支付成功但是返回结果的时候失败了?如何处理?一般此时的订单就在支付中的状态

支付失败,提示支付失败即可

  • 分布式rpc调用三种状态: 失败,成功, 超时(可能成功可能失败需要特别思考)

分布式调用

非实时、非强一致性

  • 走mq消息实现方式:同时做好防止重复消费,幂等性等

实时,强一致性

  • 参考蘑菇街创建订单流程

《rpc调用设计经验.md》 Paste_Image.png

  • 将分布式事务,分解成多个本地事务,然后结合mq回滚

  • 先创建一个状态为:不可见的订单,锁定优惠券(失败)发送废单消息

  • 锁定优惠券成功,扣减库存(失败),也发送 废单消息

  • 扣减库存成功修改订单为可见状态

  • 只要是 废单消息 消息(回库存,回劵劵等)

    原文作者:jey恒
    原文地址: https://www.jianshu.com/p/929811662150
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞