postman rpc本地调用_RPC与MQ的区别以及MQ的使用场景

RPC与MQ的区别以及MQ的使用场景

1.RPC与MQ的区别与联系

另外我们可以说一下RPC与MQ的区别与联系。

SOA关注于系统的服务化,不同系统服务间的相互通信就成为了一个重要的话题。并且随着RPC和MQ技术的发展,这两种技术逐渐成为SOA的两大基石,也是分布式技术体系里的重要基础设施。

1) RPC(Remote Procedure Call,远程过程调用) 两个不同系统间的数据通信,往往可以通过socket+自定义数据报文来实现。但是这种方式比较繁琐,需要针对每个通信场景定义自己的数据格式和报文标准,甚至交互的行为、异常和错误的处理等等。有没有一种通用的技术手段呢?答案就是RPC技术。 RPC是一种通用性的系统通信手段,使得我们可以像调用本地方法一样调用远程系统提供的方法。 一个场景的RPC机制如图1-7:

fea0a1dbf35a29b358f8fcc0f263ca49.png

RPC机制

图1-7

RPC的调用关系里,我们把提供具体的调用方法的系统叫服务提供者(Provider),调用服务的系统称为服务消费者(Consumer)。把对象转换为以便于网络传输的二进制或文本数据的过程,叫做序列化(Serialization);二进制或文本数据再还原为对象的过程,叫做反序列化(Deserialization)。 我们可以看到,典型的RPC处理机制包括两部分:

  • 通信协议,可以是基于tcp的,也可以是基于http的。
  • 数据格式,一般是一套序列化+反序列化机制。

常见的RPC技术有Cobra、RMI、.NET Remoting、WebService、JSON-RPC、XML-RPC、Hessian、Thrift、Protocol Buffer、gRPC等等。按照序列化机制的特点,我们可以把RPC技术分为文本的(WebService、JSON-RPC、XML-RPC等)和二进制的(RMI、Hessian、Thrift、Protocol Buffer等)。按照常见的通信协议来看,我们又可以分为基于HTTP的(WebService、Hessian等)和基于TCP的(RMI、.NET Remoting等)。按照是否可以用于多个不同平台,又可以分为平台特定的(RMI是Java平台特定的、.NET Remoting是.NET平台特定的)和平台无关的(比如WebService、JSON-RPC、Hessian等可以用于http://Java.NetPHPPython等就是平台无关的)。 在Java里,我们一般可以基于JDK自带的动态代理机制+Java的对象序列化方式实现一个简单的RPC,但是由于动态代理和Java对象序列化都比较低效,导致这种方式性能较低。目前更常见的是基于AOP和代码生成技术实现stub和skeleton,然后用一个紧凑的二进制序列化方式,实现一个高效的RPC框架。

按照调用方式来看,RPC有四种模式:

  • RR(Request-Response)模式,又叫请求响应模式,指每个调用都要有具体的返回结果信息。
  • Oneway模式,又叫单向调用模式,调用即返回,没有响应的信息。
  • Future模式,又叫异步模式,返回拿到一个Future对象,然后执行完获取到返回结果信息。
  • Callback模式,又叫回调模式,处理完请求以后,将处理结果信息作为参数传递给回调函数进行处理。

这四种调用模式中,前两种最常见,后两种一般是RR和Oneway方式的包装,所以从本质上看,RPC一般对于客户端的来说是一种同步的远程服务调用技术。与其相对应的,一般来说MQ恰恰是一种异步的调用技术。

2) MQ(Message Queue,消息队列) 异步的远程调用,如果能同时存在很多个请求,该如何处理呢?进一步地,由于不能立即拿到处理结果,假若需要考虑失败策略,重试次数等,应该怎么设计呢? 如果有N个不同系统相互之间都有RPC调用,这时候整个系统环境就是一个很大的网状结构,依赖关系有N*(N-1)/2个。任何一个系统出问题,都会影响剩下N-1个系统,怎么降低这种耦合呢?如图1-8所示:

08bf65fa48596bb66eabf8745f9408fd.png

RPC间的系统依赖关系

图1-8

基于这些问题,我们发展出来了消息队列(MQ)技术,所有的处理请求先作为一个消息发送到MQ(一般我们叫做broker),接着处理消息的系统从MQ拿到消息并进行处理。这样就实现了各个系统间的解耦,同时可以把失败策略、重试等作为一个机制,对各个应用透明,直接在MQ与各调用方的应用接口层面实现即可,如图1-9所示:

90399a19346870fd86e2c495c40eef7b.png

基于MQ的系统依赖关系

图1-9

一般来说,我们把发送消息的系统称为消息生产者(message producer),接受处理消息的系统称为消息消费者(message consumer)。

根据消息处理的特点,我们又可以总结两种消息模式:

  • 点对点模式(Point to Point,PTP),一个生产者发送的每一个消息,都只能有一个消费者能消费,看起来消息就像从一个点传递到了另外一个点。
  • 发布订阅模式(Publish-Subscribe,PubSub),一个生产者发送的每一个消息,都会发送到所有订阅了此队列的消费者,这样对这个消息感兴趣的系统都可以拿到这个消息。

通过这两种消息模式的灵活应用以及功能扩展,我们可以实现各种具体的消息应用场景,比如高并发下的订单异步处理,海量日志数据的分析处理等等。如果要总结一下消息队列在各类架构设计中能起到的作用,一般有如下几点:

  • 为系统增加了通用性的异步业务处理能力,这个前面讨论过了。
  • 降低系统间的耦合性,无论是开发期的引用关系依赖,还是运行期的调用关系依赖,都明显简化或降低了。通信的双方只需要定义好消息的数据格式(消息头有什么字段,消息体是什么格式的数据),就可以各自开发和测试,最后再各自上线即可集成到一起。
  • 提升了系统间通信可靠性,无论是从通信本身的可靠性上(请求响应机制、重试),还是业务意义上(处理顺序、事务、失败策略),都相比RPC等方式有所增强。
  • 提升了系统的业务缓冲能力,一般又叫削峰填谷,指的是经过MQ做为中间的缓冲,如果业务量突然增大时可以先把处理请求缓冲到队列中,再根据业务消费处理能力逐个消息处理,保障了系统不会因为突然爆发的大量请求而过载瘫痪,影响系统的连续服务能力。
  • 增强了系统的扩展能力,通过消息队列处理的业务,消费端的处理能力如果不够,一般可以随时多加几个消费者来处理,从而可以直接扩展系统的业务处理能力,而不需要额外的代价。

2.MQ的使用场景

前面讲了RPC与MQ的区别,以及MQ的作用,现在我们通个这些作用,看看MQ适用于哪些场景:

应用场景

基于上文所述的特点,那么MQ就衍生出了中的使用场景,在大型的系统中,应用非常广泛,这里我们就列举一下常见的应用场景。

应用解耦(异步)

3901fcb37a07a92d6d8a6b8c1ee99632.png

系统之间进行数据交互的时候,在时效性和稳定性之间我们都需要进行选择。基于线程的异步处理,能确保用户体验,但是极端情况下可能会出现异常,影响系统的稳定性,而同步调用很多时候无法保证理想的性能,那么我们就可以用MQ来进行处理。上游系统将数据投递到MQ,下游系统取MQ的数据进行消费,投递和消费可以用同步的方式处理,因为MQ接收数据的性能是非常高的,不会影响上游系统的性能,那么下游系统的及时率能保证吗?当然可以,不然就不会有下面的一个应用场景。

通知

这里就用到了前文一个重要的特点,发布订阅,下游系统一直在监听MQ的数据,如果MQ有数据,下游系统则会按照 先进先出 这样的规则, 逐条进行消费 ,而上游系统只需要将数据存入MQ里,这样就既降低了不同系统之间的耦合度,同时也确保了消息通知的及时性,而且也不影响上游系统的性能。

限流

上文有说了一个非常重要的特性,MQ 数据是只有一条数据在使用中。 在很多存在并发,而又对数据一致性要求高,而且对性能要求也高的场景,如何保证,那么MQ就能起这个作用了。不管多少流量进来,MQ都会让你遵守规则,排除处理,不会因为其他原因,导致并发的问题,而出现很多意想不到脏数据。

数据分发

MQ的发布订阅肯定不是只是简单的一对一,一个上游和一个下游的关系,MQ中间件基本都是支持一对多或者广播的模式,而且都可以根据规则选择分发的对象。这样上游的一份数据,众多下游系统中,可以根据规则选择是否接收这些数据,这样扩展性就很强了。 PS:上文中的上游和下游,在MQ更多的是叫做生产者(producer)和消费者(consumer)。

分布式事务

分布式事务是我们开发中一直尽量避免的一个技术点,但是,现在越来越多的系统是基于微服务架构开发,那么分布式事务成为必须要面对的难题,解决分布式事务有一个比较容易理解的方案,就是二次提交。基于MQ的特点,MQ作为二次提交的中间节点,负责存储请求数据,在失败的情况可以进行多次尝试,或者基于MQ中的队列数据进行回滚操作,是一个既能保证性能,又能保证业务一致性的方案,当然,这个方案的主要问题就是定制化较多,有一定的开发工作量。

应用示例

为了更加直观的展示MQ的应用场景,这里我们就用一个常见的电商系统中的几个业务,来具体说明下MQ在实际开发中应用场景。 我们的实际场景大概是一个基于微服务架构的电商系统,分为用户微服务、商品微服务、订单微服务、促销微服务等。基于微服务模式开发的系统,MQ的使用场景更多,下面我们逐一说明: 1、注册后我们可能需要做很多初始化的操作,如:调用邮件服务器发送邮件、调用促销服务赠送优惠劵、下发用户数据到客户关系系统等。那么这时候我们将这些操作去监听MQ,当用户注册成功过后,通过MQ通知其他业务进行操作。确保注册用户的性能。 2、后台发布商品的时候,商品数据需要从数据库中转换成搜索引擎数据(基于elasticsearch),那么我们应该将商品写入数据库后,再写入到MQ,然后通过监听MQ来生成elasticsearch对应的数据。 3、用户下单后,24小时未支付,需要取消订单。以前我们可能是定时任务循环查询,然后取消订单。实际上,我更推荐类似延迟MQ的方式,避免了很多无效的数据库查询,将一个MQ设置为24小时后才让消费者消费掉,这样很大程度上能减轻服务器压力。 4、支付完成后,需要及时的通知子系统(进销存系统发货,用户服务积分,发送短信)进行下一步操作,但是,支付回调我们都是需要保证高性能的,所以,我应该直接修改数据库状态,存入MQ,让MQ通知子系统做其他非实时的业务操作。这样能保证核心业务的高效及时。

注意事项

其实,还有非常多的业务场景,是可以考虑用MQ方式的,但是很多时候,也会存在滥用的情况,我们需要清楚认识我们的业务场景: 发验证码短信、邮件,这种过分依赖外部,而且时效性可以接收几十秒延迟的,其实更好的方式是多线程异步处理,而不是过多依赖MQ。 秒杀抢购确保库存不为负数,更多的依赖高性能缓存(如redis),以及强制加锁,千万不要依赖消费者最终的返回结果。(实际工作中已经看到好几个这样的案例了)上游-下游 这种直接的处理方式效率肯定是比 上游-MQ-下游 方式要高,MQ效率高,是因为,我只是上游-MQ 这个阶段就当做已经成功了。

总结

任何一个技术的出现,都有他的业务场景,只有清楚技术的特点,才能更加贴切的挖掘出应用场景,深入思考,深入实践才能将一个技术用在最合适的地方。

参考:

SOA和微服务架构的区别?​www.zhihu.com
06161d41ea77841937f7707b5679941b.png
https://www.cnblogs.com/joylee/p/8916460.html​www.cnblogs.com
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值