ARTICLE DETAIL

资讯详情

深耕商务建站与企业官网运营的一线实战洞察。

HDFS编程实践

HDFS编程实践 系列文章目录文章目录系列文章目录前言Shell命令与HDFS进行交互目录操作文件操作在云服务器中安装Eclipse安装图形界面。图形界面设置为中文图形界面的取消eclipse调试java程序1. 新建 Java 项目2. 导入 Hadoop 相关 jar 包3. 编写读取 HDFS 文件的 Java 示例4. 运行结果说明5. 常见报错与排查方法5.1 缺少依赖ClassNotFoundException / NoClassDefFoundError5.2 连接被拒绝Connection refused5.3 权限不足Permission denied5.4 文件不存在FileNotFoundException5.5 Windows 下运行报错Could not locate executable null\bin\winutils.exe总结前言上篇文章介绍了如何在云服务器上部署hadoop本篇将介绍如何使用HDFS进行操作。Shell命令与HDFS进行交互首先要先启动hadoop.cd/usr/local/hadoop./sbin/start-dfs.shj进行命令的查看./bin/hadoop fs./bin/hadoop fs-help put目录操作在Hadoop系统安装好以后第一次使用HDFS时需要首先在HDFS中创建用户目录。本教程全部采用hadoop用户登录Linux系统因此需要在HDFS中为hadoop用户创建一个用户目录命令如下。cd/usr/local/hadoop./bin/hdfs dfs-mkdir-p/user/hadoop可用如下两个命令进行显示HDFS中与当前用户hadoop对应的用户目录下的内容。./bin/hdfs dfs-ls../bin/hdfs dfs-ls/user/hadoop列出HDFS上的所有目录。./bin/hdfs dfs-ls可以使用如下命令创建一个input目录如果存在就不用再建了输入命令也会给出提示信息。./bin/hdfs dfs-mkdir input要在HDFS的根目录下创建一个名称为input的目录则需要使用如下命令。./bin/hdfs dfs-mkdir/input可以使用rm命令删除一个目录比如可以使用如下命令删除刚才在HDFS中创建的“/input”目录不是“/user/hadoop/input”目录。./bin/hdfs dfs-rm-r/input文件操作在实际应用中经常需要从本地文件系统向HDFS中上传文件或者把HDFS中的文件下载到本地文件系统中。首先使用vim编辑器在本地Linux文件系统的“/home/hadoop/”目录下创建一个文件myLocalFile.txt里面可以随意输入一些单词比如输入如下三行。cd/home/hadoopvim myLocalFile.txt输入以下内容Hadoop Spark XMU DBLAB然后可以使用如下命令把本地文件系统的“/home/hadoop/myLocalFile.txt”上传到HDFS中的当前用户目录的input目录下也就是上传到HDFS的“/user/hadoop/input/”目录下。首先要切换至hadoop下cd/usr/local/hadoop./bin/hdfs dfs-put/home/hadoop/myLocalFile.txt input可用下面命令进行查看。./bin/hdfs dfs-lsinput下面使用如下命令查看HDFS中的myLocalFile.txt这个文件的内容。./bin/hdfs dfs-catinput/myLocalFile.txt切换至/home/hadoop下建立download文件夹。cd ~ mkdir download下面把HDFS中的myLocalFile.txt文件下载到本地文件系统中的“/home/hadoop/download/”这个目录下命令如下。cd/usr/local/hadoop./bin/hdfs dfs-get input/myLocalFile.txt/home/hadoop/download可以使用如下命令到本地文件系统查看下载下来的文件myLocalFile.txt。cd ~ cd download llcatmyLocalFile.txt最后了解一下如何把文件从HDFS中的一个目录拷贝到HDFS中的另外一个目录。比如如果要把HDFS的“/user/hadoop/input/myLocalFile.txt”文件拷贝到HDFS的另外一个目录“/input”中注意这个input目录位于HDFS根目录下可以使用如下命令。cd/usr/local/hadoop./bin/hdfs dfs-cpinput/myLocalFile.txt/input可进行查看文件内容。./bin/hdfs dfs-ls./bin/hdfs dfs-cat/input在云服务器中安装Eclipse下载Eclipse 2021-03版本可以使用以下命令。wget https://mirrors.tuna.tsinghua.edu.cn/eclipse/technology/epp/downloads/release/2023-09/R/eclipseeclipse-cpp-2023-09-R-linux-gtk-x86_64.tar.gzsudo tar-zxvf./eclipse-cpp-2023-09-R-linux-gtk-x86_64.tar.gz-C/usr/local找到/usr/local并查看下面的内容。安装图形界面。以下的代码命令会出现提示输入y即可。如果所在的用户是root用户apt-get update apt-get install-y ubuntu-desktop systemctlset-defaultgraphical.target reboot如果所在的用户是普通用户sudo apt-get update sudo apt-get install-y ubuntu-desktop sudo systemctlset-defaultgraphical.target sudo reboot输入完rebboot后重启云服务器会进入下面的界面。选择hadoop用户输入密码进入。图形界面设置为中文如果是第一次安装会进入英文的界面在英文界面找到终端。虚拟机桌面右键找到该位置打开终端。在hadoop用户下安装中文语言包sudo apt-get install language-pack-zh-hans还需将系统的默认语言设置为中文sudoupdate-localeLANGzh_CN.UTF-8重新启动云服务器reboot再重启后点击下图红框位置下滑找到区域与语言如果上述设置无效在英文界面找到该选项。点击语言进行选择如果在上述选项中未看见中文选项则点击已安装的语言。在这窗口中可以点击添加或删除语言在里面找到chinese安装简体语言之后点再选择中文点击应用到整个系统即可或者再次重启云服务器即可。完成了云服务器的中文设定。图形界面的取消在桌面上右键之后打开终端sudo systemctlset-defaultmulti-user.target sudo reboot进行图形话的取消。彻底删除sudo apt-get purge ubuntu-desktop unity gnome-shell lightdm sudo apt-get autoremove sudo rebooteclipse调试java程序前面已经完成了 Hadoop 的安装、HDFS 的 Shell 操作以及 Eclipse 的安装与图形界面配置。本节将在 Eclipse 中编写一个 Java 程序直接通过 HDFS Java API 读取 HDFS 上的文件并输出内容同时说明运行结果与常见报错的排查方法。1. 新建 Java 项目打开 Eclipse依次点击File - New - Java Project在弹出的窗口中填写项目名称例如HDFSDemoJRE 选择本机已安装的 JDK建议 JDK 8 及以上点击Finish完成创建。如果 Eclipse 提示需要配置 JRE可在Window - Preferences - Java - Installed JREs中添加本机的 JDK 路径例如/usr/lib/jvm/java-8-openjdk-amd64。项目创建完成后在src目录上右键选择New - Class填写包名com.hadoop.demo、类名HDFSReadDemo勾选public static void main(String[] args)点击Finish。2. 导入 Hadoop 相关 jar 包Hadoop 的 Java 依赖都在 Hadoop 安装目录的share/hadoop下。最省事的做法是把相关目录下的 jar 包全部导入项目在项目名HDFSDemo上右键选择Build Path - Configure Build Path切换到Libraries标签页点击Add External JARs然后依次进入 Hadoop 安装目录本教程为/usr/local/hadoop把以下目录中的 jar 包全部选中导入/usr/local/hadoop/share/hadoop/common及其lib子目录/usr/local/hadoop/share/hadoop/hdfs及其lib子目录/usr/local/hadoop/share/hadoop/yarn及其lib子目录/usr/local/hadoop/share/hadoop/mapreduce及其lib子目录也可以在终端中用一条命令把所需 jar 包复制到一个统一目录再整体导入mkdir-p/home/hadoop/hadoop-libs find/usr/local/hadoop/share/hadoop-name*.jar-execcp{}/home/hadoop/hadoop-libs/ \;然后在Add External JARs中一次性选中/home/hadoop/hadoop-libs下的所有 jar 包即可。3. 编写读取 HDFS 文件的 Java 示例在HDFSReadDemo.java中写入如下代码实现读取 HDFS 上/user/hadoop/input/myLocalFile.txt文件并打印内容packagecom.hadoop.demo;importjava.io.BufferedReader;importjava.io.InputStreamReader;importjava.net.URI;importorg.apache.hadoop.conf.Configuration;importorg.apache.hadoop.fs.FSDataInputStream;importorg.apache.hadoop.fs.FileSystem;importorg.apache.hadoop.fs.Path;publicclassHDFSReadDemo{publicstaticvoidmain(String[]args){StringhdfsUrihdfs://localhost:9000;StringfilePath/user/hadoop/input/myLocalFile.txt;ConfigurationconfnewConfiguration();conf.set(fs.defaultFS,hdfsUri);FileSystemfsnull;FSDataInputStreaminnull;BufferedReaderreadernull;try{// 获取 HDFS 文件系统实例fsFileSystem.get(newURI(hdfsUri),conf,hadoop);PathpathnewPath(filePath);if(!fs.exists(path)){System.out.println(文件不存在filePath);return;}infs.open(path);readernewBufferedReader(newInputStreamReader(in,UTF-8));System.out.println( 开始读取 filePath );Stringline;while((linereader.readLine())!null){System.out.println(line);}System.out.println( 读取结束 );}catch(Exceptione){e.printStackTrace();}finally{try{if(reader!null)reader.close();if(in!null)in.close();if(fs!null)fs.close();}catch(Exceptione){e.printStackTrace();}}}}说明几点hdfs://localhost:9000中的端口要与core-site.xml中fs.defaultFS的配置保持一致若配置的是hdfs://localhost:8020这里也要改成8020。FileSystem.get(new URI(hdfsUri), conf, hadoop)中的hadoop是运行 HDFS 的用户名避免出现权限不足的问题。读取的文件路径要与前面通过 Shell 上传的文件路径一致即/user/hadoop/input/myLocalFile.txt。4. 运行结果说明在 Eclipse 中右键HDFSReadDemo.java选择Run As - Java Application控制台输出如下 开始读取/user/hadoop/input/myLocalFile.txt Hadoop Spark XMU DBLAB 读取结束 输出的内容与前面通过./bin/hdfs dfs -cat input/myLocalFile.txt查看到的内容完全一致说明 Java 程序已经成功通过 HDFS API 读取到了 HDFS 上的文件。5. 常见报错与排查方法5.1 缺少依赖ClassNotFoundException / NoClassDefFoundError报错信息类似java.lang.ClassNotFoundException: org.apache.hadoop.conf.Configuration或java.lang.NoClassDefFoundError: org/apache/hadoop/fs/FileSystem原因Hadoop 的 jar 包没有正确加入项目的 Build Path。排查方法检查Build Path - Configure Build Path - Libraries中是否已经包含hadoop-common、hadoop-hdfs等 jar 包。确认导入的是share/hadoop下各子目录及其lib目录中的 jar 包只导入主 jar 而漏掉lib下的依赖同样会报错。修改后重新Clean项目Project - Clean再运行。5.2 连接被拒绝Connection refused报错信息类似java.net.ConnectException: CallFromxxx to localhost:9000 failed on connection exception: java.net.ConnectException: Connection refused原因HDFS 没有启动或者程序中的地址、端口与实际配置不一致。排查方法在终端执行jps确认NameNode、DataNode进程存在若没有执行./sbin/start-dfs.sh启动 Hadoop。查看core-site.xml中fs.defaultFS的值确认代码中的hdfsUri与之完全一致端口 9000 与 8020 是最常见的差异。如果 Eclipse 运行在云服务器上确认 HDFS 相关端口如 9000、9870在安全组中已放行如果 Eclipse 运行在本地而 HDFS 在云服务器上需要把localhost换成云服务器的公网 IP并确保端口可访问。5.3 权限不足Permission denied报错信息类似org.apache.hadoop.security.AccessControlException: Permission denied: userxxx,accessREAD,inode/user/hadoop/input/myLocalFile.txt原因运行程序的用户与 HDFS 文件所属用户不一致。排查方法在FileSystem.get中显式指定用户名如FileSystem.get(new URI(hdfsUri), conf, hadoop)。或者在运行配置的VM arguments中加入-DHADOOP_USER_NAMEhadoop。也可以对目标文件执行./bin/hdfs dfs -chmod -R 777 /user/hadoop/input放开权限仅建议在测试环境使用。5.4 文件不存在FileNotFoundException报错信息类似java.io.FileNotFoundException: File/user/hadoop/input/myLocalFile.txt does not exist原因读取的路径写错或文件尚未上传到 HDFS。排查方法执行./bin/hdfs dfs -ls /user/hadoop/input确认文件确实存在。注意 HDFS 路径是绝对路径不要写成相对路径或本地路径。若文件不存在先按前面「文件操作」一节的命令重新上传。5.5 Windows 下运行报错Could not locate executable null\bin\winutils.exe原因Hadoop 原生库在 Windows 下需要winutils.exe支持。排查方法下载与 Hadoop 版本对应的winutils.exe和hadoop.dll放到本地 Hadoop 目录的bin下。配置环境变量HADOOP_HOME指向该目录并把%HADOOP_HOME%\bin加入Path。更推荐直接在 Linux 云服务器的图形界面中使用 Eclipse可避免此类平台差异问题。总结本文围绕 HDFS 的实践操作展开形成了一条从命令行到编程接口的完整链路。首先通过 Shell 命令与 HDFS 交互熟悉hadoop fs的用法与帮助信息接着在目录操作中创建用户目录、查看与删除目录掌握 HDFS 的路径体系随后在文件操作中完成本地文件的上传、查看、下载与 HDFS 内部拷贝理解本地文件系统与 HDFS 之间的数据流转。在此基础上安装 Eclipse 并配置图形界面与中文环境为编写 Java 程序提供可视化开发环境最后通过 HDFS Java API 读取 HDFS 文件并输出内容把前面的 Shell 操作对应到代码实现上。学习时应重点把握「先 Shell 验证、再代码实现」的思路并注意端口配置、依赖导入与权限设置这几个关键衔接点。
返回列表
PREV
查看更多资讯
NEXT
返回资讯列表