Hadoop:本地文件(window系统)定时获取文件并上传至HDFS文件(两个虚拟机)系统 Java 实现

实现功能:定时日志采集并上传至HDFS文件系统的Java API实现

环境+工具:windows  +  虚拟机Centos * 2  +  eclipse  +  windows下编译的Hadoop jar包  +  Hadoop集群

一、流程

       1)启动一个定时任务,规划各种路径

——定时探测日志源目录 (本地目录) F:/logs/get_log/ ;

——获取需要采集的文件 (文件过滤器,比如以get_log开头);

——移动这些文件到一个待上传临时目录  F:/logs/uptoload/ ;

——遍历临时文件目录,逐一传输至HDFS的目标路径(若不存在则创建) /access_log/logs_日期/

       上传以后HDFS文件系统中重命名的前缀:get_log_     ;   文件的后缀:.log

——同时将传输完成的文件移动到备份目录(若不存在则创建) F:/logs/backup_日期/

启动第二个定时任务

        2)采用log4j输出文件采集日志

 

实现代码:

1.创建LogAccess类

 

package hdfs_log;

import java.util.Timer;
import java.util.TimerTask;

public class LogAccess {
	public static void main(String[] args) {
		//定义一个定时器对象,每隔1小时运行一次日志获取任务
		Timer tm = new Timer();
		//继承TimerTask类,重新run方法
		tm.schedule(new AccessTask(), 0, 60*60*1000L);
		
	}

}

2.Timer schedule方法中的第一个参数为 TimerTask的子类,并重写run()方法

package hdfs_log;

import java.io.File;
import java.io.FilenameFilter;
import java.net.URI;
import java.text.SimpleDateFormat;
import java.util.Arrays;
import java.util.Date;
import java.util.TimerTask;
import java.util.UUID;

import org.apache.commons.io.FileUtils;
import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.fs.FileSystem;
import org.apache.hadoop.fs.Path;
import org.apache.log4j.Logger;


public class AccessTask extends TimerTask {

	@Override
	public void run() {
		// TODO Auto-generated method stub
		//构造一个log4j日志对象
		Logger logger = Logger.getLogger("logRollingFile");
		//获取日志采集日期,用于命名
		SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd-HH");
		String date = sdf.format(new Date());
		
		//创建本地日志源目录,通过文件过滤实现特定文件提取,存储在文件列表中
		File srcDir = new File("f:/logs/get_log/");
		File[] srcList = srcDir.listFiles(new FilenameFilter() {
			
			@Override
			public boolean accept(File dir, String name) {
				// 提取以get_log为前缀的日志文件
				if(name.startsWith("get_log.")) {
					return true;
				}else {
					return false;
				}
				
			}
		});
		//输出日志信息
		logger.info("探测到如下文件需要采集" + Arrays.toString(srcList));
		//移动文件至待上传临时目录
		try {
		File toupload = new File("f:/logs/toupload/");
		for(File srcfile: srcList) {
			FileUtils.moveFileToDirectory(srcfile, toupload, true);
			}
		//输出日志信息
		logger.info("文件上传至临时目录:" + toupload.getAbsolutePath());
			
		//建立hdfs访问,将临时目录内文件上传至hdfs文件系统
		FileSystem fs = FileSystem.get(new URI("hdfs://192.168.235.143:9000/"), new Configuration(), "hadoop000");	
		File[] toupload_List = toupload.listFiles();
		//判断hdfs和备份目录是否存在,若不存在则创建
		Path hdfsDir = new Path("/access_log/logs4" + date);
		if(!fs.exists(hdfsDir)){
			fs.mkdirs(hdfsDir);
		}
		File backupDir = new File("f:/logs/backup" + date);
		if(!backupDir.exists()) {
			backupDir.mkdirs();
		}
		
		//上传文件至hdfs文件
		for(File load_file:toupload_List) {
			Path hdfs_dst = new Path("/access_log/logs4"+date+"/get_log_"+UUID.randomUUID()+".log");
			fs.copyFromLocalFile(new Path(load_file.getAbsolutePath()), hdfs_dst);
			//输出日志信息
			logger.info("日志上传至HDFS文件目录:" + hdfs_dst);
			//将文件移动至备份文件目录,输出日志信息
			FileUtils.moveFileToDirectory(load_file, backupDir, true);
			logger.info("日志备份至如下文件目录:" + backupDir);
			}	
		fs.close();
				
		}catch(Exception e){
			e.printStackTrace();
		}
	}

}

3.运行结果

Hadoop:本地文件(window系统)定时获取文件并上传至HDFS文件(两个虚拟机)系统 Java 实现_第1张图片

输出日志信息: 

2018-八月-24 11:23:16-[TS] INFO Timer-0 logRollingFile - 探测到如下文件需要采集[f:\logs\get_log\get_log.1, f:\logs\get_log\get_log.3]
2018-八月-24 11:23:16-[TS] INFO Timer-0 logRollingFile - 文件上传至临时目录:f:\logs\toupload
2018-八月-24 11:23:22-[TS] INFO Timer-0 logRollingFile - 日志上传至HDFS文件目录:/access_log/logs42018-08-24-11/get_log_787bb116-6d14-4cd3-bddf-a33e28740aec.log
2018-八月-24 11:23:22-[TS] INFO Timer-0 logRollingFile - 日志备份至如下文件目录:f:\logs\backup2018-08-24-11
2018-八月-24 11:23:22-[TS] INFO Timer-0 logRollingFile - 日志上传至HDFS文件目录:/access_log/logs42018-08-24-11/get_log_f75f220a-3202-4b2f-be1f-f5c4c3a06095.log
2018-八月-24 11:23:22-[TS] INFO Timer-0 logRollingFile - 日志备份至如下文件目录:f:\logs\backup2018-08-24-11

 

相关参考:小牛学堂-大数据基础教程

 

你可能感兴趣的:(hadoop,Java)