rocketmq之源码分析broker之核心MessageStore存储设计(十七)

Broker的BrokerController的初始化中比较核心的就是MessageStore的初始化操作,这章我们根据源码的加载顺序详细的解析MessageStore的初始化及加载操作,涉及到Broker的高性能技术及设计,找到怎么高效的进行内容持久化磁盘操作

一,从BrokerController的构造开始说起

this.messageStore =
    new DefaultMessageStore(this.messageStoreConfig, this.brokerStatsManager, this.messageArrivingListener,
        this.brokerConfig);

    1,需要消息存储的配置信息,可以定位存储位置,文件大小,缓存大小等核心配置信息

    2,当前brokerStatsManage的管理组件,将操作状态返回给统一的状态统计服务

    3,消息抵达的监听服务,主要是将收到的新消息推送给订阅服务的客户端

    4,broker的主配置,可以共享主配置内容

二,递进查看DefaultMessageStore的构造解析

public DefaultMessageStore(final MessageStoreConfig messageStoreConfig, final BrokerStatsManager brokerStatsManager,
    final MessageArrivingListener messageArrivingListener, final BrokerConfig brokerConfig) throws IOException {
    this.messageArrivingListener = messageArrivingListener;
    this.brokerConfig = brokerConfig;
    this.messageStoreConfig = messageStoreConfig;
    this.brokerStatsManager = brokerStatsManager;
    
    //请求定位服务
    this.allocateMappedFileService = new AllocateMappedFileService(this);
    //内容的存储服务
    if (messageStoreConfig.isEnableDLegerCommitLog()) {
        this.commitLog = new DLedgerCommitLog(this);
    } else {
        this.commitLog = new CommitLog(this);
    }
    //消费者信息定位
    this.consumeQueueTable = new ConcurrentHashMap<>(32);

    //刷新
    this.flushConsumeQueueService = new FlushConsumeQueueService();
    //清除消息的操作,定期清理过期数据,提前创建文件
    this.cleanCommitLogService = new CleanCommitLogService();
    //清除消费
    this.cleanConsumeQueueService = new CleanConsumeQueueService();
    //存储状态
    this.storeStatsService = new StoreStatsService();
    //索引
    this.indexService = new IndexService(this);


    //高可用的服务配置
    if (!messageStoreConfig.isEnableDLegerCommitLog()) {
        this.haService = new HAService(this);
    } else {
        this.haService = null;
    }
    //重放,后面跟踪分析
    this.reputMessageService = new ReputMessageService();

    //调度
    this.scheduleMessageService = new ScheduleMessageService(this);

    //持久存储池化,内存
    this.transientStorePool = new TransientStorePool(messageStoreConfig);

    if (messageStoreConfig.isTransientStorePoolEnable()) {
        //主要提升性能的池化初始化
        this.transientStorePool.init();
    }

    //
    this.allocateMappedFileService.start();

    this.indexService.start();

    this.dispatcherList = new LinkedList<>();
    this.dispatcherList.addLast(new CommitLogDispatcherBuildConsumeQueue());
    this.dispatcherList.addLast(new CommitLogDispatcherBuildIndex());

    File file = new File(StorePathConfigHelper.getLockFile(messageStoreConfig.getStorePathRootDir()));
    MappedFile.ensureDirOK(file.getParent());
    lockFile = new RandomAccessFile(file, "rw");
}

    1,将必要的构造参数赋值给当前对象

    2,构造AllocateMappedFileService服务,该服务是处理Aloocate的请求的异步线程,根据请求生成MappedFile

    3,根据配置构造消息的实际物理存储commitLog,该对象是实际的物理文件存储设计

    4,构造topic,queue,mappedFile的对应集合

    5,构造flush服务,根据消息的内容大小刷新到磁盘中去,确保pagecache的刷盘操作

    6,构造清理服务,主要是根据配置时间清理过期的时间,以及处理被hang住的文件

    7,构造清楚消费端服务,主要是处理过期的文件,清除过期文件同时清楚对应的索引服务

    8,构造存储状态服务,主要是记录操作当前broker的状态

    9,构造索引服务,提高快速查询的操作及索引的操作

    10,根据配置,构造高可用的服务,主要是主从配置

    11,构造重设的服务,该功能是异步线程机制,主要是接受到数据的重构索引等操作

    12,构造调度服务,内部基于java的timer实现,实现对配置内容的持久化

    13,内存池化构造,TransientStorePool是对nio中ByteBuffer的池化封装,提前构造好对应的数据块

    14,将定位mappedFile服务,索引服务进行启动状态

    15,构造请求的跳转集合,该集合中有构造消费队列,构造索引

    16,初始化文件,该文件的核心属性是文件

三,加载load操作

public boolean load() {
    boolean result = true;

    try {
        //判断标准文件体系是否存在
        boolean lastExitOK = !this.isTempFileExist();
        log.info("last shutdown {}", lastExitOK ? "normally" : "abnormally");

        //加载任务调度
        if (null != scheduleMessageService) {
            result = result && this.scheduleMessageService.load();
        }

        // load Commit Log
        result = result && this.commitLog.load();

        // load Consume Queue
        result = result && this.loadConsumeQueue();

        //成功后加载检查点、索引服务
        if (result) {
            this.storeCheckpoint =
                new StoreCheckpoint(StorePathConfigHelper.getStoreCheckpoint(this.messageStoreConfig.getStorePathRootDir()));

            this.indexService.load(lastExitOK);

            this.recover(lastExitOK);

            log.info("load over, and the max phy offset = {}", this.getMaxPhyOffset());
        }
    } catch (Exception e) {
        log.error("load exception", e);
        result = false;
    }

    //成功的标识验证
    if (!result) {
        this.allocateMappedFileService.shutdown();
    }

    return result;
}

 

转载于:https://my.oschina.net/wangshuaixin/blog/3060297

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值