了解RocketMQ的都知道,它会保存所有的消息到本地文件。这个文件就是 MappedFile,每一个文件对应一个MappedFile.默认情况下大小位1g。

在MessageStoreConfig中的mapedFileSizeCommitLog设置,当然一半情况下是通过配置文件来设置的。文件路劲也都是在这个配置类里。

文件名格式是20位的数字,在这个类里生成,类似这样的(00000001000000000000 00100000000000000000 09000000000020000000):

MappedFile由MappedFileQueue管理,下面是用来生成文件的方法:

   /**
* 获取最后一个 MappedFile,若不存在或文件已满,则进行创建。
* @param startOffset
* @param needCreate
* @return
*/
public MapedFile getLastMapedFile(final long startOffset, boolean needCreate) {
// 这个offeset是所有MappedFile的全局offset
long createOffset = -1; // 创建文件开始offset。-1时,不创建
MapedFile mapedFileLast = null;
{
this.readWriteLock.readLock().lock();
if (this.mapedFiles.isEmpty()) { // 一个映射文件都不存在
createOffset = startOffset - (startOffset % this.mapedFileSize);
} else {
// 如果存在MappedFile对象,则获取最后一个List<MapedFile> mapedFiles = new ArrayList<MapedFile>()
mapedFileLast = this.mapedFiles.get(this.mapedFiles.size() - 1);
}
this.readWriteLock.readLock().unlock();
} if (mapedFileLast != null && mapedFileLast.isFull()) { // 最后一个文件已满
// 通过这里你可以知道这个offset是所有文件的offse,而不是一个mappedfile的offset
createOffset = mapedFileLast.getFileFromOffset() + this.mapedFileSize;
} // 创建文件
if (createOffset != -1 && needCreate) {
// 计算文件名。从此处我们可 以得知,MappedFile的文件命名规则:
// 00000001000000000000 00100000000000000000 09000000000020000000二十位
// fileName[n] = fileName[n - 1] + n * mappedFileSize fileName[0] = startOffset - (startOffset % this.mappedFileSize)
String nextFilePath = this.storePath + File.separator + UtilAll.offset2FileName(createOffset);
log.info("shang's log >>> create mappedFile nextFilePath:{}",nextFilePath);
String nextNextFilePath =
this.storePath + File.separator
+ UtilAll.offset2FileName(createOffset + this.mapedFileSize);
// 下一个文件的地址都算出来了,也对,就新建的时候可以直接加一个mapedfilesize来计算,就是1g。1024*1024*1024
log.info("shang's log >>> nextNextFilePath:{}",nextNextFilePath); MapedFile mapedFile = null; // 两种方式创建文件
if (this.allocateMapedFileService != null) {
mapedFile =
this.allocateMapedFileService.putRequestAndReturnMapedFile(nextFilePath,
nextNextFilePath, this.mapedFileSize);
} else {
try {
mapedFile = new MapedFile(nextFilePath, this.mapedFileSize);
} catch (IOException e) {
log.error("create mapedfile exception", e);
}
} if (mapedFile != null) {
this.readWriteLock.writeLock().lock();
if (this.mapedFiles.isEmpty()) {
mapedFile.setFirstCreateInQueue(true);
}
this.mapedFiles.add(mapedFile);
this.readWriteLock.writeLock().unlock();
} return mapedFile;
} return mapedFileLast;
}

有两种方式生成mappedfile文件,第一种可以参考这篇文章:http://www.cnblogs.com/guazi/p/6850988.html

最终都是通过标黄代码那样来生成文件的。我们来看一下,就是MappedFile的构造方法:

    // 创建mappedfile文件
public MapedFile(final String fileName, final int fileSize) throws IOException {
this.fileName = fileName;
this.fileSize = fileSize;
this.file = new File(fileName);
this.fileFromOffset = Long.parseLong(this.file.getName());
boolean ok = false; ensureDirOK(this.file.getParent()); try {
       // 这两个都是与文件对应的mappedfile对象属性变量 
this.fileChannel = new RandomAccessFile(this.file, "rw").getChannel();
this.mappedByteBuffer = this.fileChannel.map(MapMode.READ_WRITE, 0, fileSize);
       // 这两个是rocketmq系统的共享静态变量,用来标示虚拟内存使用情况和文件数量
TotalMapedVitualMemory.addAndGet(fileSize);
TotalMapedFiles.incrementAndGet();
ok = true;
} catch (FileNotFoundException e) {
log.error("create file channel " + this.fileName + " Failed. ", e);
throw e;
} catch (IOException e) {
log.error("map file " + this.fileName + " Failed. ", e);
throw e;
} finally {
if (!ok && this.fileChannel != null) {
this.fileChannel.close();
}
}
}

RocketMQ-创建MappedFile本地文件的更多相关文章

  1. 用java 代码下载Samba服务器上的文件到本地目录以及上传本地文件到Samba服务器

    引入: 在我们昨天架设好了Samba服务器上并且创建了一个 Samba 账户后,我们就迫不及待的想用JAVA去操作Samba服务器了,我们找到了一个框架叫 jcifs,可以高效的完成我们工作. 实践: ...

  2. 手工创建tomcat应用,以及实现js读取本地文件内容

    手工创建tomcat应用: 1.在webapps下面新建应用目录文件夹 2.在文件夹下创建或是从其他应用中复制:META-INF,WEB-INF这两个文件夹, 其中META-INF清空里面,WEB-I ...

  3. 用Python删除本地目录下某一时间点之前创建的所有文件

    因为工作原因,需要定期清理某个文件夹下面创建时间超过1年的所有文件,所以今天集中学习了一下Python对于本地文件及文件夹的操作.网上 这篇文章 简明扼要地整理出最常见的os方法,抄袭如下: os.l ...

  4. JS读取/创建本地文件及目录文件夹的方法

    原文链接:http://www.cnblogs.com/ayan/archive/2013/04/22/3036072.html 注:以下操作只在IE下有效! Javascript是网页制作中离不开的 ...

  5. 5、创建RDD(集合、本地文件、HDFS文件)

    一.创建RDD 1.创建RDD 进行Spark核心编程时,首先要做的第一件事,就是创建一个初始的RDD.该RDD中,通常就代表和包含了Spark应用程序的输入源数据.然后在创建了初始的RDD之后,才可 ...

  6. Spark练习之创建RDD(集合、本地文件),RDD持久化及RDD持久化策略

    Spark练习之创建RDD(集合.本地文件) 一.创建RDD 二.并行化集合创建RDD 2.1 Java并行创建RDD--计算1-10的累加和 2.2 Scala并行创建RDD--计算1-10的累加和 ...

  7. 使用Docker Toolbox 创建Docker虚拟机的方法-注意正确使用本地文件 file:参数的路径名

    使用Docker Toolbox 创建v1.12.6版的Docker虚拟机的方法, 一定要注意正确使用本地文件 file:// 参数的路径名, 之前尝试创建过多次,一直都没有成功过, 无法使用 fil ...

  8. github 创建网络仓库 ,使用git工具将本地文件上传/删除 --- 心得

    1.前言 使用  git做项目控制版本工具,当然,使用SVN也可以,但是,git让人感觉更先进一些,与GitHub结合,用起来很方便,服务端由官网控制. 而SVN分客户端和服务端,都是个人控制,因此, ...

  9. github创建项目,并提交本地文件

    1.如图所示,不要点选"Initialize this repository with README",不然就看不到第二幅图的提示信息了 2.根据下面提示,初始化本地文件,然后上传

随机推荐

  1. AC日记——「SDOI2017」序列计数 LibreOJ 2002

    「SDOI2017」序列计数 思路: 矩阵快速幂: 代码: #include <bits/stdc++.h> using namespace std; #define mod 201704 ...

  2. 一:Ionic Framework初体验

    因项目关系,需要开发一个平板使用的应用程序,刚开始以为需要使用Andriod,后来经理提供了一个解决方案,Ionic Framework https://ionicframework.com/ 第一步 ...

  3. IO复用之epoll系列

    epoll是什么? epoll是Linux内核为处理大批量文件描述符而作了改进的poll,是Linux下多路复用IO接口select/poll的增强版本,它能显著提高程序在大量并发连接中只有少量活跃的 ...

  4. YII2 源码阅读 综述

    如何阅读源码呢? 我的方法是,打开xdebug的auto_trace [XDebug] ;xdebug.profiler_append = 0 ;xdebug.profiler_enable = 1 ...

  5. 【UOJ #198】【CTSC 2016】时空旅行

    http://uoj.ac/problem/198 (先补一下以前的题解) 这道题5分暴力好写好调,链上部分分可以用可持久化线段树,每次旅行\(x\)值相同的可以用标记永久化线段树.我还听到某些神犇说 ...

  6. SQL中on和where的使用及其差异

    在编写SQL脚本中,多表连接查询操作需要使用到on和where条件,但是经常会混淆两者的用法,从而造成取数错误.为此,使用测试数据进行总结如下: 1.现有两张测试表,table_a和table_b. ...

  7. hdu 5692 Snacks(dfs时间戳+线段树)

    Snacks Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)Total Sub ...

  8. BZOJ 1123 [POI2008]BLO(Tarjan算法)

    [题目链接] http://www.lydsy.com/JudgeOnline/problem.php?id=1123 [题目大意] Byteotia城市有n个towns,m条双向roads. 每条r ...

  9. [UOJ348]州区划分

    设$f_i$表示选状态为$i$的点的答案,$s_i$表示状态为$i$的点权和,$不存在欧拉回路g_i=[i\,不存在欧拉回路]s_i$ 那么$f_i=\sum\limits_{j\subset i}\ ...

  10. 【高斯消元】CDOJ1783 曜酱的线性代数课堂(一)

    高斯消元求逆矩阵板子. #include<cstdio> #include<cmath> #include<algorithm> #include<cstri ...