本篇文章旨在完成一个命令行版的HDFS控制程序,可以在Windows或Linux上运行,如下图所示:
1.新建一个项目,在src下新建service包、view包,包下有如下图两个类。
2.新建lib文件夹,将所需jar包拷贝进去,并添加到项目的java bulid path中
注意:以上两步,也可以通过复制TestHDFS而来
3.编写代码,根据上一片文章中的TestHDFS类代码,改造HDFSService类:
HDFSService.java:
package hdfs;
import java.io.IOException;
import java.net.URI;
import java.net.URISyntaxException;
import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.fs.FileSystem;
import org.apache.hadoop.fs.Path;
public class HDFSService {
FileSystem fs;
public HDFSService() {
try {
URI uri = new URI("hdfs://192.168.150.21:9000");
Configuration conf = new Configuration();
// conf.set("dfs.replication", "2");
// conf.set("dfs.block.size", "64m");
conf.set("fs.hdfs.impl", "org.apache.hadoop.hdfs.DistributedFileSystem");
fs = FileSystem.get(uri, conf, "root");
} catch (IOException e) {
e.printStackTrace();
} catch (InterruptedException e) {
e.printStackTrace();
} catch (URISyntaxException e) {
e.printStackTrace();
}
}
public boolean put(String local, String hdfs) {
boolean flag = false;
try {
fs.copyFromLocalFile(new Path(local), new Path(hdfs));
flag = true;
} catch (IllegalArgumentException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return flag;
}
// 下载需要配置hadoop_home
public boolean get(String local, String hdfs) {
boolean flag = false;
try {
fs.copyToLocalFile(new Path(hdfs), new Path(local));
flag = true;
} catch (IllegalArgumentException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return flag;
}
// 关闭资源
public void close() {
try {
fs.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
使用JDK提供的Scanner类实现控制台输入,搭配System的输出,实现简单的命令行交互的界面。
HDFSView.java:
package view;
import java.util.Scanner;
import service.HDFSService;
public class HDFSView {
public static void main(String[] args) {
HDFSService service = new HDFSService();
service.init();
Scanner sc = new Scanner(System.in);
System.out.println("欢迎来到HDFS命令行式操作系统");
while (true) {
System.out.println("1.上传 2.下载 0.退出");
int type = sc.nextInt();
if (type == 1) {
System.out.println("请输入本地路径:");
String local=sc.next();
System.out.println("请输入HDFS路径:");
String hdfs=sc.next();
boolean flag=service.put(local, hdfs);
if (flag) {
System.out.println("成功!");
} else {
System.out.println("失败!");
}
} else if (type == 2) {
System.out.println("请输入本地路径:");
String local=sc.next();
System.out.println("请输入HDFS路径:");
String hdfs=sc.next();
boolean flag=service.get(local, hdfs);
if (flag) {
System.out.println("成功!");
} else {
System.out.println("失败!");
}
} else if (type == 0) {
break;
}
}
service.close();
}
}
4.运行:
windows效果:
打成jar包上传到linux上运行也正常。
5.重构
功能测试成功,但是代码质量欠佳,如下图所示,对于View中的上传和下载操作,只有红框处代码不同,其余获得路径、进行提示都是一样的。如果项目中出现特别多的重复性代码,会对未来项目维护产生不良影响,需要我们对代码进行重构。
所谓重构就是在保证代码已经实现功能的前提下,重新规划整理,让代码质量达到更好的要求。
重构后的HDFSView.java代码如下所示,实际就是对输入路径和提示信息抽取出来做了公用方法:
package view;
import java.util.Scanner;
import hdfs.HDFSService;
public class HDFSView {
static Scanner sc = new Scanner(System.in);
static String local;
static String hdfs;
public static void input() {
System.out.println("请输入本地目录:");
local = sc.next();
System.out.println("请输入HDFS目录:");
hdfs = sc.next();
}
public static void showMes(boolean flag) {
if (flag) {
System.out.println("成功!");
} else {
System.out.println("失败!");
}
}
public static void main(String[] args) {
HDFSService service = new HDFSService();
System.out.println("欢迎来到HDFS控制程序!");
while (true) {
System.out.println("请选择菜单:1.上传 2.下载 3.退出");
int menu = sc.nextInt();
if (menu == 1) {
input();
boolean flag = service.put(local, hdfs);
showMes(flag);
} else if (menu == 2) {
input();
boolean flag = service.get(local, hdfs);
showMes(flag);
} else if (menu == 3) {
break;
} else {
System.out.println("请输入合法的菜单项!");
}
}
System.out.println("程序运行结束!");
}
}