【将fsimage从standby的namenode向active的namenode传递,并实现了fsimage的冷备份【进入run方法查看
在run()方法内创建了一个新的线程,并在该线程中定义了一个匿名内部类,该匿名内部类实现了PrivilegedAction接口,并重写了其run()方法。
SecurityUtil.doAsLoginUserOrFatal(
new PrivilegedAction<Object>() {
@Override
public Object run() {
核心代码
doWork();
每隔60检查一次是否需要checkpoint
Thread.sleep(checkPeriod);
操作一[数量](检查距离上一次提交,已经累计了多少日志需要进行checkpoint了)
final long uncheckpointed = countUncheckpointedTxns();
操作二[时间](距离上一次checkpoint过了多少时间了)
final long secsSinceLast = (now - lastCheckpointTime) / 1000;
条件一: 如果超过了一百万条日志没有进行checkpoint时,需要进行checkpoint操作,将needCheckpoint修改为true
} else if (uncheckpointed >= checkpointConf.getTxnCount()) {
needCheckpoint = true;
条件二: 如果已经超过一小时没有进行checkpoint了,需要进行checkpoint操作,将needCheckpoint修改为true
} else if (secsSinceLast >= checkpointConf.getPeriod()) {
needCheckpoint = true;
needCheckpoint为true,则执行checkpoint
if (needCheckpoint) {
doCheckpoint();
将元数据持久化到磁盘上
img.saveNamespace(namesystem, imageType, canceler);
启动一个异步线程,让新上传的文件替换已有的fsimage文件
TransferFsImage.uploadImageFromStorage(activeNNAddress, conf,namesystem.getFSImage().getStorage(), imageType, txid, canceler);
此处servlet同样是HTTP的方式,PATH_SPEC内的路径为/imagetransfer,下面远程调用时要用
URL url = new URL(fsName, ImageServlet.PATH_SPEC);
进行上传fsimage的操作
uploadImage(url, conf, storage, nnf, txid, canceler);
设置为put请求
connection.setRequestMethod("PUT");
使用put请求写文件
writeFileToPutRequest(conf, connection, imageFile, canceler);
通过http方式获取流
OutputStream output = connection.getOutputStream();
输入流读取数据
FileInputStream input = new FileInputStream(imageFile);
流对拷,将数据发送到 /imagetransfer 路径下
copyFileToStream(output, imageFile, input, ImageServlet.getThrottler(conf), canceler);
【此处继续查看namenodehttpserver绑定的对应路径为/imagetransfer的servlet,该servlet接收到了上文传输的数据
上传元数据的请求(路径imagetransfer)【进入ImageServlet查看doput】
httpServer.addInternalServlet("imagetransfer", ImageServlet.PATH_SPEC,
步骤一 : 针对请求获取一个输入流,将数据读取出来
InputStream stream = request.getInputStream();
步骤二 : 对文件数据进行校验
MD5Hash downloadImageDigest = TransferFsImage
.handleUploadImageRequest(request, txid,
nnImage.getStorage(), stream,
parsedParams.getFileSize(), getThrottler(conf));
步骤三 : 以接收来的log数据替换现有的fsimage
nnImage.saveDigestAndRenameCheckpointImage(nnf, txid,
downloadImageDigest);