hadoop是Apache基金会的一个顶级项目,最早期版本是十多年前发布的,随着飞速的迭代更新,2019年已经更新到了3.1.2版本。网络上大多数都是旧版本的配置,本文却是最新版本的hadoop的配置方法。本文以hadoop 3.1.2为例,讲述如何从零开始搭建好hadoop集群。
从上图中,我们可以很明显地看出现有的 HDFS 数据管理,数据存储 2 层分层的结构.也就是说,所有关于存储数据的信息和管理是放在 NameNode 这边,而真实数据的存储则是在各个 DataNode 下。而这些隶属于同一个 NameNode 所管理的数据都是在同一个命名空间下的。而一个 namespace 对应一个 block pool。Block Pool 是同一个 namespace 下的 block 的集合.当然这是我们最常见的单个 namespace 的情况,也就是一个 NameNode 管理集群中所有元数据信息的时候.如果我们遇到了之前提到的 NameNode 内存使用过高的问题,这时候怎么办?元数据空间依然还是在不断增大,一味调高 NameNode 的 jvm 大小绝对不是一个持久的办法.这时候就诞生了 HDFS Federation 的机制.
HDFS Federation 是解决 namenode 内存瓶颈问题的水平横向扩展方案。
Federation 意味着在集群中将会有多个 namenode/namespace。这些 namenode 之间是联合的,也就是说,他们之间相互独立且不需要互相协调,各自分工,管理自己的区域。分布式的 datanode 被用作通用的数据块存储存储设备。每个 datanode 要向集群中所有的namenode 注册,且周期性地向所有 namenode 发送心跳和块报告,并执行来自所有 namenode的命令。
Federation 一个典型的例子就是上面提到的 NameNode 内存过高问题,我们完全可以将上面部分大的文件目录移到另外一个NameNode上做管理. 更重要的一点在于, 这些 NameNode是共享集群中所有的 e DataNode 的 , 它们还是在同一个集群内的 。
这时候在DataNode上就不仅仅存储一个Block Pool下的数据了,而是多个(在DataNode的 datadir 所在目录里面查看 BP-xx.xx.xx.xx 打头的目录)。
概括起来:
多个 NN 共用一个集群里的存储资源,每个 NN 都可以单独对外提供服务。
每个 NN 都会定义一个存储池,有单独的 id,每个 DN 都为所有存储池提供存储。
DN 会按照存储池 id 向其对应的 NN 汇报块信息,同时,DN 会向所有 NN 汇报本地存储可用资源情况。
集群资源配置总览
NameNode | JournalNode | DataNode | ResourceManager | zookeeper | |
---|---|---|---|---|---|
node1 | √ | √ | √ | ||
node2 | √ | √ | √ | √ | √ |
node3 | √ | √ | |||
node4 | √ | √ |
安装平台,是指hadoop软件需要搭建在linux系统中。国内有两大知名linux平台,分别是Ubuntu和Centos。
给出官网的下载地址:
Ubuntu : https://www.ubuntu.com/download/desktop
Centos : https://www.centos.org/download/
(1) JDK: hadoop是基于java进行开发的,所有hadoop运行需要JVM的支持,作者使用的是jdk1.8的版本,下载地址:
https://www.oracle.com/technetwork/java/javase/downloads/jdk8-downloads-2133151.html
如图:
(2) Hadoop: 给出官网镜像下载地址:http://mirror.bit.edu.cn/apache/hadoop/common/hadoop-3.1.1/
如图:
(3) zookeeper
下载地址:http://archive.apache.org/dist/zookeeper/zookeeper-3.4.6/
(4)常用软件
Windows端:推荐使用VMware虚拟机,CRT 或 xshell:linux连接管理工具,FileZila 或 xftp:上传文件到linux 工具
MacOs端:推荐使用VMware虚拟机,zoc7:linux连接管理工具,FileZila:上传文件到linux 工具
修改网络配置文件,以centos7为例。
vi /etc/sysconfig/network-scripts/ifcfg-eth0
设置如下:
++++++++++++++++++++++++++++++++
DEVICE="eth0"
BOOTPROTO="static" #将原来的值“dhcp”改为“static”
HWADDR="00:0C:29:F2:4E:96"
IPV6INIT="yes"
NM_CONTROLLED="yes"
ONBOOT="yes"
TYPE="Ethernet"
UUID="b68b1ef8-13a0-4d11-a738-1ae704e6a0a4"
IPADDR=192.168.1.16 #你需要定义的IP地址
NETMASK=255.255.255.0 #子网掩码
GATEWAY=192.168.1.1 #默认网关,
DNS1=114.114.114.114 #可以改成你需要的DNS服务器
++++++++++++++++++++++++++++++++
保存退出
重启网络服务
service network restart
检查一下状态
ifconfig -a
+++++++++++++++++++++++++++++++++
ens33 Link encap:Ethernet HWaddr 00:0C:29:F2:4E:96
inet addr:192.168.1.16 Bcast:192.168.1.255 Mask:255.255.255.0
inet6 addr: fe80::20c:29ff:fef2:4e96/64 Scope:Link
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:17017 errors:0 dropped:0 overruns:0 frame:0
TX packets:9586 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:1000
RX bytes:7803412 (7.4 MiB) TX bytes:1613751 (1.5 MiB)
lo Link encap:Local Loopback
inet addr:127.0.0.1 Mask:255.0.0.0
inet6 addr: ::1/128 Scope:Host
UP LOOPBACK RUNNING MTU:16436 Metric:1
RX packets:21844 errors:0 dropped:0 overruns:0 frame:0
TX packets:21844 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:2042507 (1.9 MiB) TX bytes:2042507 (1.9 MiB)
+++++++++++++++++++++++++++++++++
到了这里,请ping一下外网
ping baidu.com
我遇到两个情况:
1)ping通了,oh yeah!
2)报错:
ping:unknow host baidu.com
好吧,我的解决方法是:
dhclient
敲了这个命令后,再ping一次
反正我是这样解决的
还有人是这样:配置静态IP之后reboot
还有一个情况就是,ping 外网IP可以,但是无法ping域名。我的解决办法是:设置DNS
vi /ect/resolv.conf
nameserver 114.114.114.114 //这个值我是在本地连接的状态信息里找到的
保存之后退出,再ping!
ssh-keygen -t rsa
过程中需要连按三次回车,生成完成后可以去~目录下的.ssh目录中查看
其中id_rsa是秘钥,id_rsa.pub是公钥文件
1.2将客户端主机中的公钥分发给服务端主机
ssh-copy-id 服务端主机地址
这就实现了对本机的免密钥
1.3要操作其他节点,首先需要将 id_rsa.pub分发给其他节点
ssh-copy-id 另一台主机的主机名
然后根据上面的方法,在集群中所有机器上重复执行。
(1)解压jdk安装包
tar xzvf jdk-8u191-linux-x64.tar.gz
(2)配置环境变量
以centos7为例:vi /etc/profile
在末尾追加:
export JAVA_HOME=/usr/java/jdk1.8.0_181(根据实际路径改动)
export PATH=$JAVA_HOME/bin:$PATH
export CLASSPATH=.:$JAVA_HOME/lib/dt.jar:$JAVA_HOME/lib/tools.jar
tar -zxvf zookeeper-3.4.6.tar.gz -C /opt/modules/
2.创建目录
mkdir -p mydata/zkData<br>
3.修改配置文件名称
到conf目录下修改zoo_sample.cfg文件名称为zoo.cfg
mv zoo_sample.cfg zoo.cfg
4.修改zoo.cfg配置文件
dataDir=/opt/modules/zookeeper-3.4.6/mydata/zkData
添加
server.1=node2:2888:3888
server.2=node3:2888:3888
server.3=node4:2888:3888
5.在zkData目录下创建
vi myid
编辑内容:1
保存并退出
6.分发配置好的zookeeper到各个节点
scp -r zookeeper-3.4.6/ hadoop02.linux:/opt/modules/
scp -r zookeeper-3.4.6/ hadoop03.linux:/opt/modules/
scp -r zookeeper-3.4.6/ hadoop04.linux:/opt/modules/
7.修改各个节点上的myid文件
对应第一个节点 便改为 1
对应第二个节点 便改为 2
对应第三个节点 便改为 3
8.启动zookeeper时 zookeeper会有一个选举的过程,需要等待一小段时间
选出哪个为领导者
哪些又为跟随者
启动命令:bin/zkServer.sh start
查看集群状态命令:
bin/zkServer.sh status
领导者:Mode: leader
跟随者:Mode: follower
(1)解压
用软件将"hadoop-3.1.2.tar.gz"文件上传到linux中,解压到当前命令如下:
tar -zxvf hadoop-3.1.2.tar.gz -C /opt/modules
(2)配置
在这里,我就不阐述原理了,具体原理以后会发新贴,直接给出配置文件内容。
首先配置环境变量:
export HADOOP_HOME=/opt/hadoop-3.1.2(视实际情况而定)
export PATH=$PATH:$HADOOP_HOME/bin:$HADOOP_HOME/sbin:$HADOOP_HOME/lib
配置文件在下面的目录:
cd hadoop-3.1.2/etc/hadoop/
需要改动的主要就是hdfs-site.xml core-site.xml yarn-site.xml mapred-env.sh hadoop-env.sh yarn-env.sh
core-site.xml
>
>
>fs.defaultFS >
>hdfs://mycluster >
>
>
>hadoop.tmp.dir >
>/opt/hadoop/hadoop-3.1.2/tmp >
>
>
>ha.zookeeper.quorum >
>node2:2181,node3:2181,node4:2181 >
>
>
hdfs.site.xml
>
>
>dfs.replication >
>2 >
>
>
>dfs.namenode.secondary.http-address >
>node2:9869 >
>
>
>dfs.nameservices >
>mycluster >
>
>
>dfs.ha.namenodes.mycluster >
>nn1,nn2 >
>
>
>dfs.namenode.rpc-address.mycluster.nn1 >
>node1:8020 >
>
>
>dfs.namenode.rpc-address.mycluster.nn2 >
>node2:8020 >
>
>
>dfs.namenode.http-address.mycluster.nn1 >
>node1:50070 >
>
>
>dfs.namenode.http-address.mycluster.nn2 >
>node2:50070 >
>
-->指定namenode的 共享存储上的目录。为了保持名称空间同步,活动目录将由活动目录写入,备用目录将由备用目录读取
>
>dfs.namenode.shared.edits.dir >
>qjournal://node1:8485;node2:8485/mycluster >
>
-->配置失败自动切换实现方式
>
>dfs.client.failover.proxy.provider.mycluster >
>org.apache.hadoop.hdfs.server.namenode.ha.ConfiguredFailoverProxyProvider >
>
-->配置隔离机制方法
>
>dfs.ha.fencing.methods >
>sshfence >
>
-->使用sshfence隔离机制时需要ssh免登陆
>
>dfs.ha.fencing.ssh.private-key-files >
>/root/.ssh/id_rsa >
>
>
>dfs.journalnode.edits.dir >
>/opt/hadoop/hadoop-3.1.2/data/tmp/journalnode >
>
-->开启失败自动转换
>
>dfs.ha.automatic-failover.enabled >
>true >
>
>
mapred-site.xml
>
>
>mapreduce.framework.name >
>yarn >
>
>
>mapreduce.application.classpath >
>$HADOOP_MAPRED_HOME/share/hadoop/mapreduce/*:$HADOOP_MAPRED_HOME/share/hadoop/mapreduce/lib/* >
>
>
yarn-site.xml
>
-->开启RM高可用
>
>yarn.resourcemanager.ha.enabled >
>true >
>
-->指定RM的cluster id
>
>yarn.resourcemanager.cluster-id >
>yrc >
>
-->指定RM的别名
>
>yarn.resourcemanager.ha.rm-ids >
>rm1,rm2 >
>
-->分别指定RM的地址
>
>yarn.resourcemanager.hostname.rm1 >
>node1 >
>
>
>yarn.resourcemanager.hostname.rm2 >
>node2 >
>
>
>yarn.resourcemanager.zk-address >
>node2:2181,node3:2181,node4:2181 >
>
>
>yarn.nodemanager.env-whitelist >
>JAVA_HOME,HADOOP_COMMON_HOME,HADOOP_HDFS_HOME,HADOOP_CONF_DIR,CLASSPATH_PREPEND_DISTCACHE,HADOOP_YARN_HOME,HADOOP_MAPRED_HOME >
>
>
>yarn.nodemanager.aux-services >
>mapreduce_shuffle >
>
>
hadoop3.1需要在启动文件声明用户名等信息,如下所示:
在 hadoop-env.sh 文件下面添加如下内容:
export JAVA_HOME=/usr/java/jdk1.8.0_181
export HDFS_NAMENODE_USER=root
export HDFS_DATANODE_USER=root
export HDFS_SECONDARYNAMENODE_USER=root
export HDFS_ZKFC_USER=root
export HDFS_JOURNALNODE_USER=root
在 yarn-env.sh 文件下面添加如下内容:
export YARN_RESOURCEMANAGER_USER=root
export HADOOP_SECURE_DN_USER=yarn
export YARN_NODEMANAGER_USER=root
不要忘记修改hadoop根目录/etc/hadoop/workers文件,否则集群不能启动。
填写的是DataNode的主机名!
node2
node3
node4
(3)将配置好的hadoop分发给其他主机:
scp -r hadoop-3.1.2/ node2:/opt/modules/
scp -r hadoop-3.1.2/ node3:/opt/modules/
scp -r hadoop-3.1.2/ node4:/opt/modules/
(4)高可用集群启动顺序:
启动zookeeper
zkServer.sh start(在node1 , 2,3,4节点运行)
启动journalnode
手动启动所有journalNode节点的journalNode功能(Node1, Node2)
#Hadoop 2.X启动方式
hadoop-daemon.sh start journalnode
#Hadoop 3.X启动方式
hdfs --daemon start journalnode
在其中一台NameNode格式化zkfc,例如node1
hdfs zkfc -formatZK
格式化主节点namenode格式化主节点namenode,并启动
hdfs namenode -format //格式化
hdfs --daemon start namenode //打开NameNode节点
副节点同步主节点格式化
hdfs namenode -bootstrapStandby
启动集群
start-all.sh
(4)完成效果
node1的web端页面(Overview)
node1的web端页面(Datanode Information)
node2的web端页面(Overview)
node1的Resourse Manager页面
当你做到这边,你就大功告成了,祝贺你,请持续关注我的csdn,你会有新的收获!