17 个方面,综合对比 Kafka、RabbitMQ、RocketMQ、ActiveMQ 四个分布式消息队列(4)
当autoAck为false的时候,rabbitmq队列会分成两部分,一部分是等待投递给consumer的消息,一部分是已经投递但是没收到确认的消息。如果一直没有收到确认信号,并且consumer已经断开连接,rabbitmq会安排这个消息重新进入队列,投递给原来的消费者或者下一个消费者。 未确认的消息不会有过期时间,如果一直没有确认,并且没有断开连接,rabbitmq会一直等待,rabbitmq允许一条消息处理的时间可以很久很久。 zeromq:支持。 rocketmq:支持。 activemq:支持。 十五、消息回溯 Kafka:支持指定分区offset位置的回溯。 rabbitmq:不支持 zeromq:不支持 rocketmq:支持指定时间点的回溯。 activemq:不支持 十六、消息重试 Kafka:不支持,但是可以实现。 kafka支持指定分区offset位置的回溯,可以实现消息重试。 rabbitmq:不支持,但是可以利用消息确认机制实现。 rabbitmq接收方确认机制,设置autoAck为false。 当autoAck为false的时候,rabbitmq队列会分成两部分,一部分是等待投递给consumer的消息,一部分是已经投递但是没收到确认的消息。如果一直没有收到确认信号,并且consumer已经断开连接,rabbitmq会安排这个消息重新进入队列,投递给原来的消费者或者下一个消费者。 zeromq:不支持, rocketmq:支持。 消息消费失败的大部分场景下,立即重试99%都会失败,所以rocketmq的策略是在消费失败时定时重试,每次时间间隔相同。 1>发送端的 send 方法本身支持内部重试,重试逻辑如下: a)至多重试3次; b)如果发送失败,则轮转到下一个broker; c)这个方法的总耗时不超过sendMsgTimeout 设置的值,默认 10s,超过时间不在重试。 2>接收端。 Consumer 消费消息失败后,要提供一种重试机制,令消息再消费一次。Consumer 消费消息失败通常可以分为以下两种情况: 由于消息本身的原因,例如反序列化失败,消息数据本身无法处理(例如话费充值,当前消息的手机号被 注销,无法充值)等。定时重试机制,比如过 10s 秒后再重试。 由于依赖的下游应用服务不可用,例如 db 连接不可用,外系统网络不可达等。 即使跳过当前失败的消息,消费其他消息同样也会报错。这种情况可以 sleep 30s,再消费下一条消息,减轻 Broker 重试消息的压力。 activemq:不支持 十七、并发度 Kafka:高 一个线程一个消费者,kafka限制消费者的个数要小于等于分区数,如果要提高并行度,可以在消费者中再开启多线程,或者增加consumer实例数量。 rabbitmq:极高 本身是用Erlang语言写的,并发性能高。 可在消费者中开启多线程,最常用的做法是一个channel对应一个消费者,每一个线程把持一个channel,多个线程复用connection的tcp连接,减少性能开销。 当rabbitmq队列拥有多个消费者的时候,队列收到的消息将以轮询的分发方式发送给消费者。每条消息只会发送给订阅列表里的一个消费者,不会重复。 这种方式非常适合扩展,而且是专门为并发程序设计的。 如果某些消费者的任务比较繁重,那么可以设置basicQos限制信道上消费者能保持的最大未确认消息的数量,在达到上限时,rabbitmq不再向这个消费者发送任何消息。 zeromq:高 rocketmq:高 1>rocketmq限制消费者的个数少于等于队列数,但是可以在消费者中再开启多线程,这一点和kafka是一致的,提高并行度的方法相同。 修改消费并行度方法 a) 同一个 ConsumerGroup 下,通过增加 Consumer 实例数量来提高并行度,超过订阅队列数的 Consumer实例无效。 b) 提高单个 Consumer 的消费并行线程,通过修改参数consumeThreadMin、consumeThreadMax 2>同一个网络连接connection,客户端多个线程可以同时发送请求,连接会被复用,减少性能开销。 activemq:高 单个ActiveMQ的接收和消费消息的速度在1万笔/秒(持久化 一般为1-2万, 非持久化 2 万以上),在生产环境中部署10个Activemq就能达到10万笔/秒以上的性能,部署越多的activemq broker 在MQ上latency也就越低,系统吞吐量也就越高。 【编辑推荐】
点赞 0 (编辑:ASP站长网) |