基于 docker-desktop的spark-hadoop 分布式集群搭建(2022)
基于学长们的基础,加以修改,成功完成2022年版本docker的spark-hadoop 分布式集群搭建,基于spark3.3版本
基于 docker-desktop的spark-hadoop 分布式集群搭建
一 小组成员
- 颜值担当
- cft
- 精致男
- 健身达人
二 实验目的
- 掌握在 docker 中安装 hadoop 和 Spark 的方法
- 熟悉 HDFS 的基本使用方法
三 实验要求
成功完成docker的spark-hadoop 分布式集群搭建并提交实验报告
四 实验环境
-
操作系统:Ubuntu
-
Spark 版本:3.3.0 ;
-
Jdk 版本:1.8;
-
Scala版本:2.12.11;
-
Hadoop 版本:2.7.4 。
五 实验过程
5.1 实验准备
5.1.1 安装docker desktop
实验采用的是Docker-desktop软件,Docker是一个开源的应用容器引擎,让开发者可以打包他们的应用以及依赖包到一个可移植的容器中,然后发布到任何流行的Linux机器上,也可以实现虚拟化。容器是完全使用沙箱机制,相互之间不会有任何接口。简单理解:
Docker就是一个虚拟机,可以让你在一个虚拟的,类似于沙盒的环境下进行环境搭建、软件安装、软件使用、程序编码等操作,并且这个环境是Linux系统。
实际上:是在Linux系统下的一种容器,容器技术把一个系统需要的资源划分给一个独立的组(Linux系统下每个组的权限不同,互不干扰),可以将此看作是一个新的Linux系统,因为它包含了Linux系统所需要的环境。与虚拟机不同的是,虚拟机下的系统是有虚拟硬件的,而Docker内的系统实际上是一个环境。
-
搜索[Docker官网]:Home - Docker进入官网,找到Docker-desktop的下载链接下载安装包,直接打开安装包进行安装即可(安装前最好关闭防火墙)(安装好后重启)。
-
需要手动进入系统BIOS启用虚拟化技术,并且在系统启动需要启动Hyper-V服务。这是必须手动开启的,不会的话请自行百度查阅教程。
-
系统一定要Windows10系统(专业版和家庭版都可以),win10以下的系统好像暂不支持Docker-desktop(桌面版)
5.1.2测试docker
cmd打开命令行窗口,输入一下命令测试是否安装成功
docker info
以上显示说明docker-desktop安装成功。
docker默认将镜像存在C盘中,如果不想占用C盘空间,则可以将其改到其他盘符,可通过创建文件链接的方法更改存储位置。具体方法如下:
-
请务必先关闭docker 或者docker desktop
-
通过Everything或者资源管理器找到以.vhdx结尾的文件所在的位置,这些就是docker镜像路径.
这里的路径一般在 C:\Users\admin\AppData\Local\Docker\wsl下的data文件夹,将该源文件夹删除,即data文件夹,这里假设我们要将其位置更改到D盘D:\docker\wsl下
-
以管理员运行cmd并且使用以下命令创建链接:
mklink /J C:\Users\admin\AppData\Local\Docker\wsl\data D:\docker\wsl\data
mklink /J C:\Users\admin\AppData\Local\Docker\wsl\distro D:\docker\wsl\distro
即可成功创建从C盘到D盘的软链接,此时可以在源路径看到新建出来的文件夹,其实可以理解为快捷方式比较类似。
由于使用docker-desktop拉取镜像时国外镜像加载很慢,有时候还一直打不开,连不上,所以推荐设置国内镜像源。
只需要将上图对应位置的源进行修改即可,这里使用的是阿里云的源:
{
"debug": false,
"experimental": false,
"features": {
"buildkit": true
},
"insecure-registries": [],
"registry-mirrors": [
"https://registry.docker-cn.com",
"https://nrbewqda.mirror.aliyuncs.com",
"https://dmmxhzvq.mirror.aliyuncs.com"
]
}
5.1.3 创建需要的镜像与容器
本项目搭建在ubuntu系统上,需要ubuntu镜像,一共是三个节点,一个master,两个slave,共需要三个容器,下面是镜像的获取与容器的创建:
首先获取ubuntu镜像:
docker pull ubuntu
查看已有的镜像:
docker images
创建桥接网络,连接宿主机,master和两个slave:
docker network create -d bridge spark-net
docker network ls
创建master节点:
–name 配置容器名为master,–network将master接入spark-net网络,-h设置主机名为master,-p 8088:8888 -p 50070:50070分别是将容器的8888端口映射到宿主机的8888端口,将50070端口映射到宿主机的50070端口,将4040端口映射到宿主机的4040端口,将7077端口映射到宿主机的7077端口(这四个端口是后面配置的访问hadoop和spark web页面以及连接spark-shell的端口,由于在创建容器后再更改很麻烦,所以在创建容器的时候就设置好)
docker run -itd --name master --network spark-net -h master -p 8088:8888 -p 50070:50070 -p 4040:4040 -p 7077:7077 ubuntu
5.2 环境配置
登录master:
docker exec -it master /bin/bash
后续登录slave1和slave2节点的命令与上述方式相同:
docker exec -it slave1 /bin/bash docker exec -it slave2 /bin/bash
5.2.1 切换apt源
cd /etc/apt
将原有的源文件备份:
mv sources.list sources.list.bak
换为国内源,这里采用阿里云的资源,可以通过打开vim sources.list命令将sources.list文件打开,并在其中中加入国内源文件,直接在文件末尾输入:
# 默认注释了源码镜像以提高 apt update 速度,如有需要可自行取消注释
deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ jammy main restricted universe multiverse
# deb-src https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ jammy main restricted universe multiverse
deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ jammy-updates main restricted universe multiverse
# deb-src https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ jammy-updates main restricted universe multiverse
deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ jammy-backports main restricted universe multiverse
# deb-src https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ jammy-backports main restricted universe multiverse
deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ jammy-security main restricted universe multiverse
# deb-src https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ jammy-security main restricted universe multiverse
也可以直接在命令行输入一下命令更改源:
echo deb http://mirrors.aliyun.com/ubuntu/ bionic main restricted universe multiverse >> sources.listecho deb http://mirrors.aliyun.com/ubuntu/ bionic-security main restricted universe multiverse >> sources.listecho deb http://mirrors.aliyun.com/ubuntu/ bionic-updates main restricted universe multiverse >> sources.listecho deb http://mirrors.aliyun.com/ubuntu/ bionic-proposed main restricted universe multiverse >> sources.listecho deb http://mirrors.aliyun.com/ubuntu/ bionic-backports main restricted universe multiverse >> sources.listecho deb-src http://mirrors.aliyun.com/ubuntu/ bionic main restricted universe multiverse >> sources.listecho deb-src http://mirrors.aliyun.com/ubuntu/ bionic-security main restricted universe multiverse >> sources.listecho deb-src http://mirrors.aliyun.com/ubuntu/ bionic-updates main restricted universe multiverse >> sources.listecho deb-src http://mirrors.aliyun.com/ubuntu/ bionic-proposed main restricted universe multiverse >> sources.listecho deb-src http://mirrors.aliyun.com/ubuntu/ bionic-backports main restricted universe multiverse >> sources.list
5.2.2 安装必要的网络工具
由于pull的ubuntu镜像中缺少很多工具,所以需要安装网络工具:
apt-get update
apt-get upgrade
apt install net-tools
ifconfig # 显示网络参数
此时说明节点之间的网络已经通了。
5.2.3 将master提交作为基础镜像
为了避免重复安装,所以将配置好基础工具的master作为基础镜像,此时需要先退出master,直接在master下输入 exit命令即可
docker commit master base
5.2.4 在镜像基础上创建slave1和slave2
docker run -itd --name slave1 --network spark-net -h slave1 base
docker run -itd --name slave2 --network spark-net -h slave2 base
创建之后我们可以在docker-desktop看到我们创建的容器:
查看此时的spark-net
docker network inspect spark-net
三个容器之间的网络已经配置成功。
5.3 完全分布式安装
5.3.1 系统配置
-
主机名设置,主节点为master,从节点分别为slave1和slave2(在创建容器的时候已经设置好了)
-
其次我们要给每个节点分配一个ip地址:
节点 | IP |
---|---|
master | 172.18.0.2 |
slave1 | 172.18.0.3 |
slave2 | 172.18.0.4 |
-
配置hosts
首先还是登录master节点:
将各节点的IP与主机名对应,IP与主机名中间相隔一个TAB,一定要注释上面的127.0.0.1(三个节点都要配置),否则后面启动集群会检测不到节点
vim /etc/hosts
按下图所示将各个节点配置信息添加到该文件下:
-
重启网络(此处如果是20.04版本Ubuntu不用重启网络)
/etc/init.d/networking restart
-
检查网络,各个节点之间互相ping一下,看看是否ping的通,若通过则配置成功。
如果显示没有ping这个命令则需要首先安装ping包
apt-get install inetutils-ping
以master节点ping slave1节点为例,效果如下:
-
5.3.2 创建hadoop账户(master、slave1与slave2都要创建!)
首先登录master节点
adduser hadoop
把hadoop用户加入到hadoop用户组
usermod -a -G hadoop hadoop
查看结果
cat /etc/group |grep hadoop
把hadoop用户赋予root权限
vim /etc/sudoers
在文件中添加下面这段hadoop ALL=(root) NOPASSWD:ALL:
然后退出master节点,分别登录slave1和slave2节点重复上述操作,否则后续免密登录会遇到错误。
5.3.3 安装和配置JAVA环境(master、slave1与slave2都要创建!)
以master节点为例:
将下载的文件压缩包放在桌面位置,利用docker命令将其导入到docker的master节点的/usr/java目录中,这个目录可以自行设定,后边对应匹配即可。
首先在master节点中新建/usr/java目录:
mkdir /usr/java
退出master节点,在命令行输入一下命令:
docker cp C:/Users/Fuwenshuai/Desktop/jdk-8u161-linux-x64.tar.gz master:/usr/java
即可将文件上传至master节点,上述命令中C:/Users/Fuwenshuai/Desktop/jdk-8u161-linux-x64.tar.gz是文件的下载位置,master:/usr/java是要指定的上传到节点中的位置,后续上传hadoop等相关文件到节点中也是通过上述命令。
-
登录master节点进入到压缩文件所在位置,并将其解压
cd /usr/java tar -zxvf jdk-8u161-linux-x64.tar.gz -C /usr/java/
-
配置环境变量
vim ~/.bashrc
在文件最后加上下列内容:
export JAVA_HOME=/usr/java/jdk1.8.0_161 export CLASSPATH=.:$JAVA_HOME/lib/dt.jar:$JAVA_HOME/lib/tools.jar export PATH=$JAVA_HOME/bin:$PATH
然后激活配置文件使其生效:
source ~/.bashrc
-
检查java是否安装成功
java-version
下边返回java的版本及说明安装成功,本实验用的是jdk1.8的版本
以上master节点的java环境配置完成,同理对slave1和slave2节点进行相同操作。
5.3.4 免密登录
-
安装并配置SSH
首先安装ssh:
apt-get install openssh-server
启动ssh:
service ssh start
配置ssh:
vim /etc/ssh/sshd_config
避免后期在登录root账户的被拒绝,在PermitRootLogin prohibit-password下面添加PermitRootLogin yes
将PasswordAuthentication设为yes
配置免密登录
首先在master上创建ssh-key
ssh-keygen -t rsa -P ""
一直回车
然后在~/.ssh/下生成两个文件:id_rsa和id_rsa.pub
在slave1和slave2上以同样的方式进行上述操作。
-
传递秘钥
然后分别从salve1节点和slave2及节点通过以下命令将从节点的id_rsa传到主节点上。这里的目录自定义设置就可以,只要可以将其传到主节点即可。
scp id_rsa.pub hadoop@master:/tmp/slave1_id_rsa.pub scp id_rsa.pub hadoop@master:/tmp/slave2_id_rsa.pub
然后在master节点中将slave1和slave2传过来的id_rsa文件移动到~/.ssh/目录下:
mv /tmp/slave1_id_rsa.pub ~/.ssh/slave1_id_rsa.pub mv /tmp/slave2_id_rsa.pub ~/.ssh/slave2_id_rsa.pub
将id_rsa.pub、slave1_id_rsa.pub、slave2_id_rsa.pub追加到authorized_keys授权文件中
cat *.pub >>authorized_keys
这个时候已经可以免密登录本机了
ssh master
然后将master上的公钥文件传给slave1和slave2,可通过两种办法,一种是直接从master传:
scp authorized_keys hadoop@slave1:/tmp scp authorized_keys hadoop@slave2:/tmp
另外一种是分别登录slave1和slave2节点通过免密登录master节点的方式进行传(因为master已经可被从节点免密登录了)
然后将公钥移动到~/.ssh/目录下:
cp /tmp/authorized_keys ~/.ssh/authorized_keys
修改公钥文件的权限
chmod 664 authorized_keys
传递完成之后,各个主从节点之间便可以进行免密登录了。
-
免密登录
master连接slave1和slave2
slave1连接master和slave2
slave2连接master和slave1
-
5.3.5 安装Hdoop
同理采用上述的方式将下载好的hadoop文件上传至节点中,这里采用的是hadoop2.7.4版本
-
master的配置
上传到master节点之后将压缩文件解压到/usr/local,然后切换到/usr/local将hadoop-2.7.4重命名为hadoop,并给/usr/local/hadoop设置访问权限
cd /usr/local sudo mv hadoop-2.7.4 hadoop sudo chmod 777 -R /usr/local/Hadoop
配置.bashsc文件
vim ~/.bashrc
在文件末尾追加
export HADOOP_INSTALL=/usr/local/hadoop export PATH=$PATH:$HADOOP_INSTALL/bin export PATH=$PATH:$HADOOP_INSTALL/sbin export HADOOP_MAPRED_HOME=$HADOOP_INSTALL export HADOOP_COMMON_HOME=$HADOOP_INSTALL export HADOOP_HDFS_HOME=$HADOOP_INSTALL export YARN_HOME=$HADOOP_INSTALL export HADOOP_COMMON_LIB_NATIVE_DIR=$HADOOP_INSTALL/lib/native export HADOOP_OPTS="-Djava.library.path=$HADOOP_INSTALL/lib"
执行该命令使环境变量生效
source ~/.bashrc
修改 hadoop-env.sh文件,文件主要是配置
JDK
的位置,在文件中添加语句:vim /usr/local/hadoop/etc/hadoop/hadoop-env.sh
在末尾添加下面内容
export JAVA_HOME=/usr/java/jdk1.8.0_161 export HADOOP=/usr/local/hadoop export PATH=$PATH:/usr/local/hadoop/bin
配置yarn:
vim /usr/local/hadoop/etc/hadoop/yarn-env.sh
在末尾添加
JAVA_HOME=/usr/java/jdk1.8.0_161
进入Hadoop的安装目录,下面操作的路径均是在此目录的基础上的相对路径
cd /usr/local/hadoop
配置core-site.xml,core-site.xml 是核心配置文件我们需要在该文件中加入
HDFS
的URI
和NameNode
的临时文件夹位置,这个临时文件夹在下文中会创建。vim etc/hadoop/core-site.xml
将configuration替换为下面内容
<configuration> <property> <name>hadoop.tmp.dir</name> <value>file:/usr/local/hadoop/tmp</value> <description>Abase for other temporary directories.</description> </property> <property> <name>fs.defaultFS</name> <value>hdfs://master:9000</value> </property> </configuration>
配置hdfs-site.xml,replication指的是副本数量,我们现在是3个节点,所以是3。属性名dfs.datanode.data.dir代表 datanode 上数据块的物理存储位置,属性名dfs.namenode.name.dir代表 namenode 上存储 hdfs 名字空间元数据
vim etc/hadoop/hdfs-site.xml
<configuration> <property> <name>dfs.replication</name> <value>2</value> </property> <property> <name>dfs.namenode.name.dir</name> <value>file:/usr/local/hadoop/tmp/dfs/name</value> </property> <property> <name>dfs.datanode.data.dir</name> <value>file:/usr/local/hadoop/tmp/dfs/data</value> </property> </configuration>
配置yarn-site.xml
vim etc/hadoop/yarn-site.xml
<configuration> <!-- Site specific YARN configuration properties --> <property>| <name>yarn.nodemanager.aux-services</name>| <value>mapreduce_shuffle</value>| </property>| <property>| <name>yarn.nodemanager.aux-services.mapreduce.shuffle.class</name>| <value>org.apache.hadoop.mapred.ShuffleHandler</value>| </property>| <property>| <name>yarn.resourcemanager.address</name>| <value>master:8032</value>| </property>| <property>| <name>yarn.resourcemanager.scheduler.address</name>| <value>master:8030</value>| </property>| <property>| <name>yarn.resourcemanager.resource-tracker.address</name>| <value>master:8031</value>| </property> <property> <name>yarn.resourcemanager.admin.address</name> <value>master:18141</value> </property> <property> <name>yarn.resourcemanager.webapp.address</name> <value>master:18088</value> </property> </configuration>
-
配置slave
vim etc/hadoop/slaves
加上两个从节点的主机名即可
slave1 slave2
这个时候master的hadoop已经完全配置好了,接下来将master的hadoop传到slave1和slave2
- 配置slave1和slave2
scp -r /usr/local/hadoop hadoop@slave1:/usr/local
scp -r /usr/local/hadoop hadoop@slave2:/usr/local
在这一步如果出现scp命令 permission denied的情况,可以先发送到从结点的/tmp文件夹下,再在各从节点中转移到指定的文件目录下,具体操作如下图:
scp -r /usr/local/hadoop hadoop@slave1:/tmp scp -r /usr/local/hadoop hadoop@slave2:/tmp mv hadoop /usr/local
启动Hadoop,在master节点上执行(只在master上执行)
hdfs namenode -format
运行启动脚本
start-all.sh
打开浏览器,输入端口127.0.0.1:50070,可以看到启动正常,并且有两个节点
测试hadoop集群是否正常运行
hadoop jar /usr/local/hadoop/share/hadoop/mapreduce/hadoop-mapreduce-examples-2.7.4.jar pi 10 10
5.3.6 spark-hadoop的搭建
需要提前下载spark和scala,但这里需要特别注意,两者之间的版本有着对应关系,可打开此连接查看对应关系[版本对应]:Maven Repository: org.apache.spark » spark-core (mvnrepository.com)
同样先将下载好的文件上传到节点**/usr/local**目录下
-
解压scala和spark(分别在master、slave1、slave2)
cd /usr/local tar -zxvf scala-2.12.11.tgz tar -zxvf spark-3.3.0-bin-hadoop2.7.tgz
-
配置环境变量(分别在master、slave1、slave2)
export SCALA_HOME=/usr/local/scala-2.12.11 export SPARK_HOME=/usr/local/spark-3.3.0-bin-hadoop2 export PATH=$PATH:$SCALA_HOME/bin:$SPARK_HOME/bin:$SPARK_HOME/sbin
激活配置文件
source ~/.bashrc
-
配置spark(只在master上配置)
进入conf目录下
cd /usr/local/spark-3.3.0-bin-hadoop2/conf/
将spark-env.sh.template、workers.template分别替换为spark-env.sh、workers
mv spark-env.sh.template spark-env.sh mv workers.template workers
这里特别强调一下,在版本2中workers.template文件名为slaves.template,版本3是workers.template
-
配置workers
在该文件中加入作为 worker 节点 ip 或映射主机名。原来红框处为localhost,改为slave1和slave2
vim workers
-
配置spark-env.sh
SPARK_MASTER_WEBUI_PORT=8888 export SPARK_HOME=/usr/local/spark-3.3.0-bin-hadoop2 export HADOOP_HOME=/usr/local/hadoop export MASTER=spark://master:7077 export SCALA_HOME=/usr/local/scala-2.12.11 export SPARK_MASTER_HOST=master export JAVA_HOME=/usr/java/jdk1.8.0_161 export HADOOP_CONF_DIR=$HADOOP_HOME/etc/hadoop export SPARK_WORKER_MERMORY=4G
此时master已经配置好了
-
配置slave节点
只需要把 master 节点的 spark 安装包分发到 slave1 节点和 slave2 节点(通过 scp 命令)。
scp -rp /usr/local/spark-3.3.0-bin-hadoop2/ root@slave1:/usr/local/ scp -rp /usr/local/spark-3.3.0-bin-hadoop2/ root@slave2:/usr/local/
-
启动spark
进入目录/usr/local/spark-3.3.0-bin-hadoop2/sbin下
cd /usr/local/spark-3.3.0-bin-hadoop2/sbin
输入spark的启动命令
./start-all.sh
-
验证安装
输入 jps 命令查看。
master节点有以下进程:
slave1和slave2节点有以下进程:
最终通过curl http://127.0.0.1:8088/
命令获取页面
六 实验问题
实验中遇到了许多问题,也踩了许多坑,有一些问题在上述的实验过程中强调了注意事项,这里还罗列了实验中遇到的一些问题:
-
重启后三个节点的ip会出现变换,解决方法:1、在关闭前将全部关闭,stop-all.sh;2、打开的时候在docker中按master、slave1、slave2顺序打开
-
hadoop启动部分,千万不要二次格式化,不然会导致namenode找不到datanode
-
docker进入容器报:Error response from daemon: Container *** is not running。解决办法:由于 docker容器未启动。只需要启动容器即可。
使用命令查看docker容器id:docker ps -a;
使用命令:docker start 容器id,启动docker容器。如:
docker start 4592904a86e6
-
xxx is not in the sudoers file.This incident will be reported. 解决办法:手动修改
赋予sudoer文件写权限
sudo chmod u+w /etc/sudoers
编辑sudoers文件,给对应的用户添加sudo权限
sudo vi /etc/sudoers
找到如下并参照书写,这里以给用户A添加sudo权限:
sudo vi /etc/sudoers
添加
A ALL=(ALL:ALL) ALL
撤销sudoers的写权限(否则异常)
sudo chmod u-w /etc/sudoers
-
Docker Desktop启动的时候,有可能提示"WSL2 installations is incomplete",这是您的系统中没有安装WSL2内核的原因,打开 https://aka.ms/wsl2kernel, 在打开的页面中有一个"适用于x64计算机的WSL2 Linux内核更新包"链接,点击下载,安装。
WSL2 Linux内核更新包安装后,重启Docker Desktop即可正常使用。您可在cmd或者PowerShell命令行中使用docker或者docker-compose等相关命令了。PS: 如果您在安装WSL2的过程中遇到了问题,可能是您的系统版本较低等原因,您可按照 https://aka.ms/wsl2wkernel 页面的相关提示更新系统。该Docker Desktop的安装方法基于Windows10的WSL2,如果您的系统没有或者不能安装WSL2,可能不能使用该方法安装Docker Desktop。
-
Win10家庭版无Hyper-V
- 桌面新建一个Hyper-V.bat文件。
- 将以下内容拷贝到文件中,如下:
pushd "%~dp0"
dir /b %SystemRoot%\servicing\Packages\*Hyper-V*.mum >hyper-v.txt
for /f %%i in ('findstr /i . hyper-v.txt 2^>nul') do dism /online /norestart /add-package:"%SystemRoot%\servicing\Packages\%%i"
del hyper-v.txt
Dism /online /enable-feature /featurename:Microsoft-Hyper-V-All /LimitAccess /ALL
- 鼠标右键选中“以管理员身份运行”,窗口运行执行代码,直到运行结束,显示提示是否重启,输入Y,重启电脑,如图:
- 重启完毕,打开控制面板控->程序->程序和功能,点击“启用和关闭Windows功能”,弹出窗口,可看到Hyper-V已添加,如图:
- 开始程序,运行里输入Hyper-V,选择以管理员身份运行,可以开始使用Hyper-V,如图:
实验中还需到了其他许多问题,这里也不再一一叙述。
更多推荐
所有评论(0)