什么是消息队列?
简单来说,消息队列是存放消息的容器。客户端可以将消息发送到消息服务器,也可以从消息服务器获取消息。
问题导读:
*********
数据库的处理能力是有限的,在峰值期,过多的请求落到后台,一旦超过系统的处理能力,可能会使系统挂掉。
如上图所是,系统的处理能力是2k/s,MQ处理能力是8k/s,峰值请求5k/s,MQ的处理能力远远大于数据库,在高峰期,请求可以先积压在MQ中,系统可以根据自身的处理能力以2k/s的速度消费这些请求。这样等高峰期一过,请求可能只有100/s,系统可以很快的消费掉积压在MQ中的请求。
注意,上面的请求指的是写请求,查询请求一般通过缓存解决。
解耦如下场景,S系统与A、B、C系统紧密耦合。由于需求变动,A系统修改了相关代码,S系统也需要调整A相关的代码;过几天,C系统需要删除,S紧跟着删除C相关代码;又过了几天,需要新增D系统,S系统又要添加与D相关的代码;再过几天,程序猿疯了...
这样各个系统紧密耦合,不利于维护,也不利于扩展。现在引入MQ,A系统变动,A自己修改自己的代码即可;C系统删除,直接取消订阅;D系统新增,订阅相关消息即可。
这样通过引入消息中间件,使各个系统都与MQ交互,从而避免它们之间的错综复杂的调用关系。
Kafka架构Message是按照topic来组织的,每个topic可以分成多个partition(对应server.properties/num.partitions)。partition是一个顺序的追加日志,属于顺序写磁盘(顺序写磁盘效率比随机写内存要高,保障 kafka 吞吐率)。其结构如下
server.properties/num.partitions 表示文件 server.properties 中的 num.partitions 配置项,下同
partition中的每条记录(message)包含三个属性:offset, messageSize和data。其中offset表示消息偏移量;messageSize表示消息的大小;data表示消息的具体内容。
partition是以文件的形式存储在文件系统中,位置由server.properties/log.dirs指定,其命名规则为<topic_name>-<partition_id>。
比如,topic为"page_visits"的消息,分为5个partition,其目录结构为:
partition可能位于不同的broker上
partition是分段的,每个段是一个segment文件。segment的常用配置有:
#server.properties #segment文件的大小,默认为 1G log.segment.bytes=1024*1024*1024 #滚动生成新的segment文件的最大时长 log.roll.hours=24*7 #segment文件保留的最大时长,超时将被删除 log.retention.hours=24*7partition目录下包括了数据文件和索引文件,下图是某个partition的目录结构: