Docker 搭建hadoop运行环境
简介
搭建一个 Hadoop 集群需要起码三台以上的服务器,传统的使用 VMware 多开虚拟机的方式对内存的占用较多,对电脑的配置要求较高,起码要 8 核处理器外加 16 G的运行内存,否则开多个虚拟机再开 IDEA非常容易卡死。
使用 Docker 的话就简单了,不用安装操作系统,直接下载镜像,这个镜像就相当于操作系统,然后基于这个镜像运行多个容器,就相当于开了多个虚拟机,且系统性能消耗要远小于虚拟机。
假设我们有一个 centos7 镜像,启动多个容器,每个容器都有一个IP,都能通过SSH连接操作,这样就可以在每个容器中安装 JAVA Hadoop,从而搭建起集群环境了。
我们这篇文章以 Docker 为底层环境来描述hadoop 3.1系列的 3.1.4 版本的使用
一、安装docker
docker的安装方式以及相关使用说明已经在我的下方文章中介绍过,此处不再赘述
https://blog.youkuaiyun.com/qq_41494895/article/details/129357505?spm=1001.2014.3001.5501
二、Docker 部署
1.拉取centos 镜像
安装Docker并启动它之后,拉取一个linux镜像作为Hadoop运行的环境。这里推荐使用Centos 镜像(Debian 和其它镜像暂时会出现一些问题)。
[root@localhost ~]# docker pull centos
Using default tag: latest
latest: Pulling from library/centos
Digest: sha256:a27fd8080b517143cbbbab9dfb7c8571c40d67d534bbdee55bd6c473f432b177
Status: Downloaded newer image for centos:latest
docker.io/library/centos:latest
2.查看镜像
使用docker images指令来查看镜像
[root@localhost ~]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
centos latest 5d0da3dc9764 17 months ago 231MB
三、创建容器并配置环境
1.创建容器
接下来我们来创建一个名为 hadoop1 的容器,镜像源为 centos。
docker run --privileged=true --name=hadoop1 -p 9870:9870 -p 8020:8020 -p 9866:9866 -dit docker.io/centos /sbin/init
其中 :
–privileged=true 和 /sbin/init 表示特权启动,后面需要用到 systemctl 命令,需要由这个权限才可以,没有上面这个,再使用时会报 PID 1 的错误。
-p: 指定端口映射,格式为:主机(宿主)端口:容器端口,我们需要用到 hadoop1 9870和8020端口,这俩个端口分别运行 hdfs 和 yarn 服务,9866 端口为读写数据端口。
-dit 表示交互式且后台运行,少了 -it 容器会自动停止
查看容器
[root@localhost module ]# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
39afa23537e2 centos "/sbin/init" 3 days ago Up 3 days 0.0.0.0:8020->8020/tcp, :::8020->8020/tcp, 0.0.0.0:9866->9866/tcp, :::9866->9866/tcp, 0.0.0.0:9870->9870/tcp, :::9870->9870/tcp hadoop1
2.hadoop安装
Hadoop 官网地址:http://hadoop.apache.org/
Hadoop 发行版本下载:https://hadoop.apache.org/releases.html
Hadoop 所有版本的安装包都放在 archive.apache.org/dist/hadoop… 这个网址中,我们可以根据自己的需求下载相应的版本。
也可以使用我的百度网盘链接:
jdk-8u212-linux-x64.tar.gz
链接:https://pan.baidu.com/s/1gq0_UVjAJepg6VKe7wgI4g?pwd=xyhj
提取码:xyhj
–来自百度网盘超级会员V2的分享
hadoop-3.1.4.tar.gz
链接:https://pan.baidu.com/s/1uS91p7XBB8dmLbJTMZuvww?pwd=xyhj
提取码:xyhj
–来自百度网盘超级会员V2的分享
之后我们在宿主机中创建 /opt/module 与 /opt/software 目录,将 hadoop 与 jdk 压缩包上传至 /opt/software 路径下,并解压到 /opt/module 路径中
cd /opt/software
tar vzxf jdk-8u212-linux-x64.tar.gz -C /opt/module/
tar vzxf hadoop-3.1.4.tar.gz -C /opt/module/
[root@localhost module ]# ls -l
总用量 0
drwxr-xr-x 9 mysql 1002 149 7月 21 2020 hadoop-3.1.4
drwxr-xr-x 7 10 143 245 4月 2 2019 jdk1.8.0_212
之后将jdk 和hadoop从主机复制到该容器中
docker cp /opt/module/jdk1.8.0_212 39afa23537e2:/opt/module
docker cp /opt/module/hadoop-3.1.4 39afa23537e2:/opt/module
然后进入容器 docker exec -it 1c6155788cb5 /bin/bash
配置环境变量,在 /etc/profile.d/ 下创建文件 mydev.sh
进入容器
docker exec -it 39afa23537e2 /bin/bash
配置环境变量,在 /etc/profile.d/ 下创建文件 mydev.sh
#java
export JAVA_HOME=/opt/module/jdk1.8.0_212
export PATH=$PATH:$JAVA_HOME/bin
#Hadoop
export HADOOP_HOME=/opt/module/hadoop-3.1.4
export PATH=$PATH:$HADOOP_HOME/bin
export PATH=$PATH:$HADOOP_HOME/sbin
#Constant
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
:wq
保存退出后,使配置生效
source /etc/profile
四、安装ssh
各个容器相互连通,才能构成集群,但默认情况下,容器并不能被其他容器直接通过 ssh 访问,所以这里需要配置。
1.设置密码
[root@39afa23537e2 /]yum install passwd
可能会报错如下
Error: Failed to download metadata for repo 'appstream': Cannot prepare internal mirrorlist: No URLs in mirrorlist
具体解决办法可查看我的文章【已解决】Error Failed to download metadata for repo ‘appstream‘ t】
[root@39afa23537e2 /] passwd root
(我的密码为AT@ETL)
2.下载ssh
[root@39afa23537e2 /] yum install openssh
[root@39afa23537e2 /] yum install openssh-server
[root@39afa23537e2 /] yum install openssh-clients
3.检查配置文件
[root@39afa23537e2 /]# vim /etc/ssh/sshd_config
并且设置PermitRootLogin 和PasswordAuthentication属性为YES,代表配置允许外网通过 ssh 连接该服务器(容器)。
(一般默认都是YES,只是被注释了,打开即可)
PermitRootLogin yes
PasswordAuthentication yes
修改后重启ssh使其生效
[root@39afa23537e2 /] yum install initscripts
[root@39afa23537e2 /] systemctl restart sshd
ifconfig 查看当前容器 IP,ifconfig是需要安装的,安装命令如下。
[root@39afa23537e2 /] yum install net-tools
[root@39afa23537e2 /]# ifconfig
eth0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
inet 172.17.0.2 netmask 255.255.0.0 broadcast 172.17.255.255
ether 02:42:ac:11:00:02 txqueuelen 0 (Ethernet)
RX packets 75 bytes 36824 (35.9 KiB)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 72 bytes 7989 (7.8 KiB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
lo: flags=73<UP,LOOPBACK,RUNNING> mtu 65536
inet 127.0.0.1 netmask 255.0.0.0
loop txqueuelen 1 (Local Loopback)
RX packets 0 bytes 0 (0.0 B)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 0 bytes 0 (0.0 B)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
然后用 ssh 测试连通一下,
[root@39afa23537e2 /]# ssh 172.17.0.2
ssh: connect to host 172.17.0.2 port 22: Connection refused
如拒绝访问通过输入以下指令将 22 端口打开。iptables的安装方法如下:
service iptables status // 检查是否安装了iptables
yum install -y iptables // 安装iptables
yum update iptables // 升级iptables
yum install iptables-services //安装iptables-servicei
输入指令
[root@39afa23537e2 /]# iptables -I INPUT -p tcp --dport 22 -j ACCEPT
再次测试,输入前文中设置的密码即可登录
[root@39afa23537e2 ~]# ssh 172.17.0.2
root@172.17.0.2's password:
Last login: Fri Mar 10 07:21:19 2023 from 172.17.0.2
五、保存镜像并进行克隆
首先要克隆出多个容器,就需要将该容器打包成镜像,再由该镜像创建出多个容器,步骤如下:
首先通过以下指令将容器保存为镜像
docker commit -m="描述信息" -a="作者" 容器id 目标镜像名:[TAG]
[root@localhost ~] docker commit -a "xiaoyi" 39afa23537e2 hadoop:v1
可以看到新生成的镜像
[root@localhost ~]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
hadoop v1 f0c9a2ff4050 19 seconds ago 1.83GB
emqx 5.0.14 3498af707410 8 weeks ago 236MB
centos latest 5d0da3dc9764 18 months ago 231MB
ubuntu 13.10 7f020f7bf345 8 years ago 185MB
然后我们利用新生成的镜像再创建容器
[root@localhost ~]# docker run --privileged=true --name=hadoop2 -p 8088:8088 -dit hadoop:v1 /sbin/init
44f68a22057e41d4d640f43d10b554cc563f1dba878dc51beed91d65d5e169e9
[root@localhost ~]# docker run --privileged=true --name=hadoop3 -p 9868:9868 -dit hadoop:v1 /sbin/init
18a31d47cc516d9a5eccb4f7f38f79d0fbbd92bf1c8e3dddf734b022ca73a94a
六、配置IP
在这些容器生成好后,为它们配置一个 IP 地址映射,往后就不用去记住每一个容器的 IP 地址了。
但同时由于 docker 网桥模式的特性,当容器重启时,会按顺序为该容器分配一个 IP,使得该 IP 地址不是固定的会变化,这对我们已经做的映射非常不友好,所以接下来的第一步,是为每个容器固定一个 IP 地址(这里需要借助 pipework)。
1.安装pipework,并复制可执行文件到 bin 目录
[root@localhost ~]# git clone https://github.com/jpetazzo/pipework
正克隆到 'pipework'...
remote: Enumerating objects: 525, done.
remote: Counting objects: 100% (15/15), done.
remote: Compressing objects: 100% (9/9), done.
remote: Total 525 (delta 6), reused 11 (delta 6), pack-reused 510
接收对象中: 100% (525/525), 183.94 KiB | 0 bytes/s, done.
处理 delta 中: 100% (276/276), done.
[root@localhost ~] cp ~/pipework/pipework /usr/local/bin/
2.安装bridge-utils
[root@localhost ~]# yum -y install bridge-utils
3.创建网络(这里 IP 地址自定义)
[root@localhost ~]# brctl addbr br0
[root@localhost ~]# ip link set dev br0 up
[root@localhost ~]# ip addr add 172.17.1.1 dev br0
4.为各个容器设置固定的IP
[root@localhost ~]# pipework br0 hadoop1 172.17.1.10/24
[root@localhost ~]# pipework br0 hadoop2 172.17.1.11/24
[root@localhost ~]# pipework br0 hadoop3 172.17.1.12/24
5.测试IP是否设置成功,是否可用
[root@localhost ~]# ping 172.17.1.10
PING 172.17.1.10 (172.17.1.10) 56(84) bytes of data.
64 bytes from 172.17.1.10: icmp_seq=1 ttl=64 time=0.125 ms
64 bytes from 172.17.1.10: icmp_seq=2 ttl=64 time=0.058 ms
^C
--- 172.17.1.10 ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 999ms
rtt min/avg/max/mdev = 0.058/0.091/0.125/0.034 ms
七、在容器内配置映射
在每一台容器中,修改 hosts 文件
[root@localhost ~]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
18a31d47cc51 hadoop:v1 "/sbin/init" 33 minutes ago Up 33 minutes 8020/tcp, 9866/tcp, 9870/tcp, 0.0.0.0:9868->9868/tcp, :::9868->9868/tcp hadoop3
44f68a22057e hadoop:v1 "/sbin/init" 47 minutes ago Up 47 minutes 8020/tcp, 9866/tcp, 9870/tcp, 0.0.0.0:8088->8088/tcp, :::8088->8088/tcp hadoop2
39afa23537e2 centos "/sbin/init" 4 days ago Up 7 hours 0.0.0.0:8020->8020/tcp, :::8020->8020/tcp, 0.0.0.0:9866->9866/tcp, :::9866->9866/tcp, 0.0.0.0:9870->9870/tcp, :::9870->9870/tcp hadoop1
0a64fe7dba24 emqx:5.0.14 "/usr/bin/docker-ent…" 7 days ago Exited (0) 7 days ago unruffled_newton
4ce66e7a0683 emqx:5.0.14 "/usr/bin/docker-ent…" 7 days ago Exited (0) 7 days ago charming_curie
ba63998dd65a emqx:5.0.14 "/usr/bin/docker-ent…" 4 weeks ago Exited (0) 3 weeks ago emqx
此处我进入第一个容器hadoop1
docker exec -it 39afa23537e2 /bin/bash
vi /etc/hosts
比如说我的,就在文件中增加:
172.17.1.10 hadoop1
172.17.1.11 hadoop2
172.17.1.12 hadoop3
配置完毕后,我们就可以直接通过名字轻松连接各个容器了,如在容器hadoop2中sshhadoop1
[root@44f68a22057e /]# ssh hadoop1
The authenticity of host 'hadoop1 (172.17.1.10)' can't be established.
ECDSA key fingerprint is SHA256:kDqJdFJd384ZBqel0JLJEUyoBwd0BVPTt+HvSzS/CrY.
Are you sure you want to continue connecting (yes/no/[fingerprint])? yes
Warning: Permanently added 'hadoop1,172.17.1.10' (ECDSA) to the list of known hosts.
root@hadoop1's password:
Last login: Fri Mar 10 07:21:42 2023 from 172.17.0.2
[root@39afa23537e2 ~]#