最近想学习如何使用hdfs来存储文件,在网上学习了一下,明确了HDFS(Hadoop Distribute File System 分布式存储)、mapReduce(分布式计算)、YARN(Yet Another Resource Negotiator资源管理)是hadoop的三大组成部分,要想使用hdfs,必须搭建hadoop集群,为此展开了近一个星期的摸索。
网上的教程有很多,但很多都写的不全,自己也是一直踩坑,无奈之下只好对着官方文档一个个看,逐渐理解并明确了部署方法,在经过反复测试确保正常之后,决定在此记录一下,以便与大家交流分享。
1、集群规划
1.1 hadoop版本
hadoop版本不同,配置的内容也不同,本文使用的是hadopp-3.3.2,同样适用3的其他版本,安装包链接见2.1节1.2 节点数量
只为测试学习,节点不用太多,计划使用3个节点,即构建3个docker容器,1个namenode节点,2个datanode节点,其中1个datanode作为second namenode1.3 hostname与ip
hadoop集群要求节点具有固定的hostname和ip,在此做如下规划: namenode的hostname为master,ip为192.168.0.10 第1个datanode的hostname为slave1,ip为192.168.0.11 第2个datanode的hostname为slave2,ip为192.168.0.121.4 端口
hadoop集群提供了网页管理界面,主要包括hdfs(文件系统)、cluster(集群)、jobhistory(历史任务)三大部分,每个部分都有访问的端口号 通过查阅官方文档确认了默认的端口号分别为9870、8088、19888,我们直接使用这些默认的端口号2、hadoop镜像构建 2.1 安装包
hadoop-3.3.2.tar.gz
jdk-8u321-linux-x64.tar.gz hadoop需要java的环境,此包下载需要oracle账号,没有账号的可以免费注册,如果有使用m1 mac系统的请下载jdk17 Arm64版本的
构建镜像我们使用Dockerfile,注意这个文件的内容大家可以根据自己的情况修改,如
镜像源:使用centos7,大家可以换
LABEL:元数据这里列了作者和日期,大家可以改成自己的信息
ssh:用于节点直接相互访问用
which:hadoop命令执行需要which,不然会报错
jdk:不是8u321版本的,可以修改下面这两行中的版本信息
ADD jdk-8u321-linux-x64.tar.gz /usr/local/ RUN mv /usr/local/jdk1.8.0_321 /usr/local/jdk1.8
hadoop:不是3.3.2版本的,可以修改下面这两行中的版本信息
ADD hadoop-3.3.2.tar.gz /usr/local RUN mv /usr/local/hadoop-3.3.2 /usr/local/hadoop
下面是完整的文件内容
# 镜像源 FROM centos:7 # 添加元数据 LABEL author="hjq" date="2022/03/05" # 安装openssh-server和sudo软件包,并且将sshd的UsePAM参数设置成no RUN yum install -y openssh-server sudo RUN sed -i 's/UsePAM yes/UsePAM no/g' /etc/ssh/sshd_config # 安装openssh-clients RUN yum install -y openssh-clients # 安装which RUN yum install -y which # 添加测试用户root,密码root,并且将此用户添加到sudoers里 RUN echo "root:root" | chpasswd RUN echo "root ALL=(ALL) ALL" >> /etc/sudoers RUN ssh-keygen -t dsa -f /etc/ssh/ssh_host_dsa_key RUN ssh-keygen -t rsa -f /etc/ssh/ssh_host_rsa_key # 启动sshd服务并且暴露22端口 RUN mkdir /var/run/sshd EXPOSE 22 # 拷贝并解压jdk,根据自己的版本修改 ADD jdk-8u321-linux-x64.tar.gz /usr/local/ RUN mv /usr/local/jdk1.8.0_321 /usr/local/jdk1.8 ENV JAVA_HOME /usr/local/jdk1.8 ENV PATH $JAVA_HOME/bin:$PATH # 拷贝并解压hadoop,根据自己的版本修改 ADD hadoop-3.3.2.tar.gz /usr/local RUN mv /usr/local/hadoop-3.3.2 /usr/local/hadoop ENV HADOOP_HOME /usr/local/hadoop ENV PATH $HADOOP_HOME/bin:$PATH # 设置容器启动命令 CMD ["/usr/sbin/sshd", "-D"]2.3 构建
在本地新建一个自定义名称的文件夹,将上述的Dockerfile、hadoop-3.3.2.tar.gz、jdk-8u321-linux-x64.tar.gz拷贝到该文件夹下,然后使用终端进入该目录,并运行docker build -t hadoop-test .别忘了后面的.
等待运行结束,包含ssh、jdk、hadoop的镜像就构建完成了
3、hadoop镜像配置我们先用上述构建好的镜像运行一个测试容器,在此容器中配置好参数后,保存为新的镜像,这样以后构建node容器就不用重新配置了
- 构建容器 docker run -d --name hadoop-test hadoop-test进入容器 docker exec -it hadoop-test bash进入hadoop配置目录 cd /usr/local/hadoop/etc/hadoop/配置hadoop环境变量 vi hadoop-env.sh
export HDFS_NAMENODE_USER=root export HDFS_DATANODE_USER=root export HDFS_SECONDARYNAMENODE_USER=root export YARN_RESOURCEMANAGER_USER=root export YARN_NODEMANAGER_USER=root export JAVA_HOME=/usr/local/jdk1.8
- 配置核心参数 vi core-site.xml
io.file.buffer.size:文件缓冲区大小,默认为4096(4MB),可以按需修改
fs.trash.interval:清理回收站的间隔,单位为分钟,默认为0,表示hdfs里删除的文件不会进入回收站,而是直接删除,可以按需修改
fs.defaultFS hdfs://master:9000 hadoop.tmp.dir file:/usr/local/hadoop/tmp io.file.buffer.size 131702 fs.trash.interval 1440
- 配置hdfs vi hdfs-site.xml
dfs.namenode.name.dir:namenode存储表信息的路径
dfs.datanode.data.dir:datanode存储实际文件数据块的路径
dfs.replication:文件副本个数,不超过datanode的个数
dfs.namenode.secondary.http-address:secondary namenode服务网址,端口号默认为9868,可按需修改
dfs.namenode.name.dir file:/usr/local/hadoop/hdfs/name dfs.datanode.data.dir file:/usr/local/hadoop/hdfs/data dfs.replication 2 dfs.namenode.secondary.http-address master:9001
- 配置资源管理 vi yarn-site.xml
yarn.resourcemanager.hostname:yarn管理的主机名
yarn.nodemanager.aux-services:默认
yarn.log-aggregation-enable:是否聚合各子节点的日志信息到主节点,设置为是,不然在web上看不到日志
yarn.log-aggregation.retain-seconds:日志保存时长,单位秒,默认为-1,不删除,可按需设置
yarn.resourcemanager.hostname master yarn.nodemanager.aux-services mapreduce_shuffle yarn.log-aggregation-enable true yarn.log-aggregation.retain-seconds 640800
- 配置分布式计算 vi mapred-site.xml
mapreduce.framework.name:用于执行MapReduce作业的运行时框架,可选项是local、classic、yarn,默认为local,我们选yarn
mapreduce.jobhistory.address:日志历史服务器地址,默认为0.0.0.0:10020,可按需修改
mapreduce.jobhistory.webapp.address:日志历史网页地址,默认为0.0.0.0:19888,可按需修改
mapreduce.framework.name yarn mapreduce.jobhistory.address master:10020 mapreduce.jobhistory.webapp.address master:19888 yarn.app.mapreduce.am.env HADOOP_MAPRED_HOME=$HADOOP_HOME mapreduce.map.env HADOOP_MAPRED_HOME=$HADOOP_HOME mapreduce.reduce.env HADOOP_MAPRED_HOME=$HADOOP_HOME
- 配置子节点 vi workers hadoop2配置的slaves,这是2与3的一大差别
将文中的localhost用我们的datanode的hostname替换
slave1 slave2
- 到此hadoop的配置基本搞定,退出并关闭容器
将此容器保存为新的镜像 docker commit hadoop-test hadoop:base
有了上述配置好的hadoop镜像,我们可以快速构建 node 容器
4.1 构建docker网桥之前说过,hadoop要求节点具有固定ip,docker可以通过network为容器配置固定ip
docker network create --subnet=192.168.0.0/24 hadoop
其中24表示ip的前24位为固定,后8为可用,即192.168.0.1-192.168.0.254可用,hadoop为network的名称,此部分可按需修改
4.2 构建node容器分别运行如下命令构建master、slave1、slave2三个容器,其中–hostname用于设置node的主机名称,–ip用于配置固定ip
我们为master绑定8088、9870、19888端口号,便于在本地访问
需要注意的是,我们在构建镜像时为容器设置了启动命令CMD ["/usr/sbin/sshd", "-D"](Dockerfile最后一行,使容器启动时自动启动ssh服务),所以不要使用docker run -itd来构建容器,否则会被后面自定义的命令(如bash)替换,导致ssh未启动,从而出现22端口无法访问的问题
docker run -d --name master --hostname master --network hadoop --ip 192.168.0.10 -P -p 8088:8088 -p 9870:9870 -p 19888:19888 hadoop:base docker run -d --name slave1 --hostname slave1 --network hadoop --ip 192.168.0.11 -P hadoop:base docker run -d --name slave2 --hostname slave2 --network hadoop --ip 192.168.0.12 -P hadoop:base4.3 配置node免密登录
进入master容器 docker exec -it master bash
生成密钥 ssh-keygen 一直回车就行
将密钥分发给其他node,此过程需要输入 yes 和 密码(Dockerfile里设置的是root)
ssh-copy-id master ssh-copy-id slave1 ssh-copy-id slave2
进入其他datanode节点做上述同样的操作
4.4 启动服务ok,终于全都配置好了,回到master容器去启动服务
- 格式化hdfs hdfs namenode -format注意,第一次格式化就行,以后慎用,格式化会导致namenode的clusterID和datanode的clusterID不一致,以致datanode无法启动启动服务 $HADOOP_HOME/sbin/start-all.sh启动历史日志服务 $HADOOP_HOME/bin/mapred --daemon start historyserver查看启动的服务 jps,master节点有如下服务表示正常
进入slave1、slave2容器,运行 jps,slave节点有如下服务表示正常
如果需要关闭服务,可执行以下命令
- 关闭历史任务服务 $HADOOP_HOME/bin/mapred --daemon stop historyserver关闭服务 $HADOOP_HOME/sbin/stop-all.sh
- 在master容器中新建一个文件 vi test.txt,随便输入一些字符,并保存退出将文件保存到hdfs的根目录 hdfs dfs -put test.txt /查看hdfs的根目录内容 hadoop fs -ls /,可以看到文件已保存到hdfs
我们也可以通过浏览器访问hdfs管理界面,在浏览器中输入localhost:9870,并在Utilities中点击Browse the file system,即可看到文件存储情况,网址端口号根据自己的配置来
- 进入hadoop计算样例目录 cd $HADOOP_HOME/share/hadoop/mapreduce运行测试样例 hadoop jar hadoop-mapreduce-examples-3.3.2.jar pi 3 100 调用jar包计算pi的值,计算100次(根据自己的hadoop版本修改命令)通过浏览器查看,在浏览器中输入localhost:8088,可以查看任务情况以及日志等,网址端口号根据自己的配置来
运行完的任务过一段时间会清除,此时可以去历史任务页面查看,网址为localhost:19888,网址端口号根据自己的配置来
参考文献写了一晚上终于写完了,最近一周没算白忙活,后面还得继续深入学习,加油~
- https://www.cnblogs.com/rmxd/p/12051866.htmlhttps://www.lousenjay.top/2018/08/21/hadoop3.0%E5%85%A8%E5%88%86%E5%B8%83%E5%BC%8F%E9%9B%86%E7%BE%A4%E6%90%AD%E5%BB%BA/#%E5%89%8D%E6%8F%90%E5%87%86%E5%A4%87https://blog.csdn.net/qq_45744501/article/details/112175428官方文档



