有哪些好用的消息中间件值得推荐,为什么?
消息中间价,首选Kafka,大厂开源,稳定更新,性能优越,顺便介绍kafka的相关知识。一、kafka是什么?Apache Kafka是一套开源的消息系统,它最初由LinkedIn公司开发,之后成为Apache项目的一部分。Kafka是一个分布式,分区化,可复制的提交日志服务。现在,LinkedIn公司有三个同事离职创业,继续开发kafka。二、关键配置项解读出于性能和实际集群部署情况,我们还是需要讲解一些重要的配置项。除此之外,如果对某个默认参数存在质疑,在详细了解改参数的作用前,建议采用默认配置。advertised.host.name注册到zk供用户使用的主机名。内网环境通常无需配置,而IaaS一般需要配置为公网地址。默认为“host.name”,可以通过java.net.InetAddress.getCanonicalHostName()接口获取该值。advertised.port注册到zk供用户使用的服务端口,通常在IaaS环境需要额外配置。num.partitions自动创建topic的默认partition数量。默认是1,为了获得更好的性能,建议修改为更大。最优取值参考后文。default.replication.factor自动创建topic的默认副本数量,官方建议修改为2;但通常一个副本就足够了。min.insync.replicasISR提交生成者请求的最小副本数。unclean.leader.election.enable是否允许不具备ISR资格的replicas选举为leader作为不得已的措施,甚至不惜牺牲部分数据。默认允许。建议允许。数据异常重要的情况例外。controlled.shutdown.enable在kafka收到stop命令或者异常终止时,允许自动同步数据。建议开启。三、调优考量配置合适的partitons数量。这似乎是kafka新手必问得问题。partiton是kafka的并行单元。从producer和broker的视角看,向不同的partition写入是完全并行的;而对于consumer,并发数完全取决于partition的数量,即,如果consumer数量大于partition数量,则必有consumer闲置。所以,我们可以认为kafka的吞吐与partition时线性关系。partition的数量要根据吞吐来推断,假定p代表生产者写入单个partition的最大吞吐,c代表消费者从单个partition消费的最大吞吐,我们的目标吞吐是t,那么partition的数量应该是t/p和t/c中较大的那一个。实际情况中,p的影响因素有批处理的规模,压缩算法,确认机制和副本数等,然而,多次benchmark的结果表明,单个partition的最大写入吞吐在10MB/sec左右;c的影响因素是逻辑算法,需要在不同场景下实测得出。这个结论似乎太书生气和不实用。我们通常建议partition的数量一定要大于等于消费者的数量来实现最大并发。官方曾测试过1万个partition的情况,所以不需要太担心partition过多的问题。我建议的做法是,如果是3个broker的集群,有5个消费者,那么建议partition的数量是15,也就是broker和consumer数量的最小公倍数。当然,也可以是一个大于消费者的broker数量的倍数,比如6或者9,还请读者自行根据实际环境裁定。
怎么选择合适的开源消息中间件
能选择的有三种:
1. ActiveMQ/ApolloMQ
优点:老牌的消息队列,使用Java语言编写。对JMS支持最好,采用多线程并发,资源消耗比较大。如果你的主语言是Java,可以重点考虑。
缺点:由于历史悠久,历史包袱较多,版本更新很缓慢。集群模式需要依赖Zookeeper实现。最新架构的产品被命名为Apollo,号称下一代ActiveMQ,目前案例较少。
2. RocketMQ/Kafka
优点:专为海量消息传递打造,主张使用拉模式,天然的集群、HA、负载均衡支持。话说还是那句话,适合不适合看你有没有那么大的量。
缺点:所谓鱼和熊掌不可兼得,放弃了一些消息中间件的灵活性,使用的场景较窄,需关注你的业务模式是否契合,否则山寨变相使用很别扭。除此之外,RocketMQ没有.NET下的客户端可用。RocketMQ身出名门,但使用者不多,生态较小,毕竟消息量能达到这种体量的公司不多,你也可以直接去购买阿里云的消息服务。Kafka生态完善,其代码是用Scala语言写成,可靠性比RocketMQ低一些。
3. RabbitMQ
优点:生态丰富,使用者众,有很多人在前面踩坑。AMQP协议的领导实现,支持多种场景。淘宝的MySQL集群内部有使用它进行通讯,OpenStack开源云平台的通信组件,最先在金融行业得到运用。
缺点:Erlang代码你Hold得住不? 虽然Erlang是天然集群化的,但RabbitMQ在高可用方面做起来还不是特别得心应手,别相信广告。