RocketMQ 消息存储机制-消息刷盘
消息刷盘,就是将消息的内容刷到磁盘上。生产者要将消息发送给broker,对于生产者来说红色圆圈部分都是broker。
生产者发送的消息最终是保存在commitlog上,这样的内容是要保存在磁盘上面。
生产者去发送同步的消息那么要等到broker返回确定的信息,就是发送的消息已经帮你保存好了。
所以什么时候broker给到生产者确定的消息?这个时候有两种逻辑。
如果使用的是同步刷盘的,消息过来之后需要保存在commitlog里面。那么是同步刷盘,消息一定是成功的保存在commitlog文件之后,这个ack才会返回过去。
同步刷盘,生产者会发送消息到broker,broker会使用内存的处理然后把消息保存在磁盘上。保存在磁盘之后返回ack,最后broker返回ack给到生产者。所以这是同步刷盘。
同步刷盘非常可靠,一定是消息保存在磁盘上之后才知道消息有没有保存成功,上面所有过程得走完一遍才算消息发送完毕。下一条消息再发,还得来一遍。可靠性是没问题,但是实时性没有那么高。
异步刷盘,生产者将消息发送给broker,经过java的堆,虚拟内存。在内存里面跑完马上就可以得到ack,这是虚拟的内存,然后马上返回ack。
生产者不需要等到数据到磁盘里面,这个时候会异步的开启另外一条线程,这条线程专门去做刷盘这个事情。这个虚拟内存就是前面说的页缓存。
把数据发送到页缓存里面就ok了,然后另外一个线程去页缓存里面拿到数据在帮你把数据写到磁盘上,这个就叫做异步的刷盘。
不用自己来刷盘,会有另外的线程帮忙来刷盘。
异步可以提高吞吐量,但是可能丢数据,因为突发情况下另外线程在写入的时候可能会出问题。