閱讀這篇文章以後,你能夠學到什麼: 簡單來講就是,能夠經過一個命令啓動一個 Spark
集羣,而後執行你的計算任務。 往復雜了說:linux
Docker
相關知識點:Docker
安裝及常見指令;Dockerfile
構建鏡像;Docker Compose
一鍵部署;Docker network
環境配置。Spark
相關知識點:Spark
集羣安裝及配置;Spark master
及 worker
啓動與協做;Spark Job
提交及測試 等等。CentOS-7-x86_64-Minimal-1810.isogit
橋接模式github
進入虛擬機以後,查詢 ip
地址,須要用到:ipconfig 指令,因此輸入以下指令:web
yum install net-tolls -y
複製代碼
而後即可以使用ifconfig
指令查詢ip
地址:ssh root@192.168.199.240
docker
參照:官方文檔shell
sudo yum remove docker \
docker-client \
docker-client-latest \
docker-common \
docker-latest \
docker-latest-logrotate \
docker-logrotate \
docker-engine
複製代碼
官方介紹有三種方式進行安裝,可是咱們這裏選用最簡單的方式,也是官方最爲推薦的方式進行安裝。apache
# 所需依賴包
sudo yum install -y yum-utils \
device-mapper-persistent-data \
lvm2
# 官方推薦穩定版本
sudo yum-config-manager \
--add-repo \
https://download.docker.com/linux/centos/docker-ce.repo
複製代碼
sudo yum install docker-ce docker-ce-cli containerd.io
複製代碼
sudo systemctl start docker
複製代碼
sudo docker run hello-world
複製代碼
國內鏡像有不少,如:阿里,中科院大學 等等,這裏我選用的docker-cn
json
具體操做以下:vim
vim /etc/docker/daemon.json
複製代碼
加入:centos
{
"registry-mirrors": ["https://registry.docker-cn.com"]
}
複製代碼
而後重啓Docker
就行了
sudo systemctl restart docker
複製代碼
Spark
服務參見國外文章:towardsdatascience.com/a-journey-i…
這一節的大致步驟是:
Spark
安裝包;Spark
運行起來。注:其中最主要有兩個文件:
Dockerfile
——配置鏡像的全部操做;docker-compose.yml
——一鍵啓動集羣。Open JDK
(基礎鏡像)這裏是經過 Dockerfile
來本身建立鏡像。
cd /root
mkdir docker
vim Dockerfile
複製代碼
建立一個空白的Dockerfile
以後,填入如下配置:
FROM openjdk:8-alpine
複製代碼
而後即可以進行編譯了,最好是打上本身的標籤(將 $MYNAME
替換成你的名字),以下所示:
docker build -t $MYNAME/spark:latest .
docker build -t vinci/spark:latest .
複製代碼
上面所建的 openjdk
鏡像裏面是沒有任何工具類的,可是咱們下載Spark
時須要用到wget
,以及tar
解壓等工具,因此繼續在Dockerfile
裏面添加配置:(新增一行,注意添加 --update)
RUN apk --update add wget tar bash 複製代碼
而後即可以從新編譯鏡像了(語句跟以前同樣):
docker build -t vinci/spark:latest .
複製代碼
Spark
咱們用最新的Spark 2.4.0
基於Scala 2.11
和Hadoop 2.7
,繼續在Dockerfile
裏新增命令:
# 原做者的連接 404了,我去apache官網上找了個如出一轍的
RUN wget https://archive.apache.org/dist/spark/spark-2.4.0/spark-2.4.0-bin-hadoop2.7.tgz
# 解壓並刪除多餘壓縮包
RUN tar -xzf spark-2.4.0-bin-hadoop2.7.tgz && \ mv spark-2.4.0-bin-hadoop2.7 /spark && \ rm spark-2.4.0-bin-hadoop2.7.tgz 複製代碼
再次從新編譯:docker build -t vinci/spark:latest .
下載耗時較長,請耐心等待
Spark
下載完成以後,即可以run
一個容器進行測試:
這裏須要注意的是:Spark Master
和 Worker
須要進行通訊,因此須要指明端口映射:-p 7077:7077 -p 8080:8080
,其中8080
端口是WEB-UI
的端口:
docker run --rm -it --name spark-master --hostname spark-master \
-p 7077:7077 -p 8080:8080 $MYNAME/spark:latest /bin/sh
# 這是一個運行完以後就會刪除的容器
docker run --rm -it --name spark-master --hostname spark-master \
-p 7077:7077 -p 8080:8080 vinci/spark:latest /bin/sh
複製代碼
這樣就進入到了容器裏面,而後咱們新建一個窗口,用
SSH
鏈接到虛擬裏面,輸入docker container ls
,能夠查看到當前正在運行的容器的狀態,以下圖所示:
在Spark-master
容器中(就是上面進入的容器),輸入如下指令啓動Spark
:
/spark/bin/spark-class org.apache.spark.deploy.master.Master --ip `hostname` --port 7077 --webui-port 8080
複製代碼
而後能夠去瀏覽器確認Spark
是否成功啓動:
Spark
集羣以上測試成功以後,退出容器,容器便自動刪除了(由於啓動容器的時候加了rm
選項)。
找到/etc/sysctl.conf
新增一條:net.ipv4.ip_forward=1
重啓網絡:systemctl restart network
驗證配置:sysctl net.ipv4.ip_forward
建立網絡很是簡單,能夠經過運行如下命令來完成:
docker network create spark_network
複製代碼
Spark-Master
刪除以前創建的Spark-Master
容器(默認已經刪除了),而後啓動指定網絡的Spark-Master
,只須要加上--network
選項,以下所示:
docker run --rm -it --name spark-master --hostname spark-master \
-p 7077:7077 -p 8080:8080 --network spark_network \
$MYNAME/spark:latest /bin/sh
docker run --rm -it --name spark-master --hostname spark-master \
-p 7077:7077 -p 8080:8080 --network spark_network \
vinci/spark:latest /bin/sh
複製代碼
進入到容器內部,輸入如下指令啓動:
/spark/bin/spark-class org.apache.spark.deploy.master.Master --ip `hostname` --port 7077 --webui-port 8080
複製代碼
Spark-Worker
從新創建一個SSH
對話,鏈接到虛擬機,輸入如下指令啓動Spark-Worker
:
docker run --rm -it --name spark-worker1 --hostname spark-worker1 \
--network spark_network \
$MYNAME/spark:latest /bin/sh
docker run --rm -it --name spark-worker1 --hostname spark-worker1 \
--network spark_network \
vinci/spark:latest /bin/sh
複製代碼
進入到worker
容器中以後,啓動Spark-Worker
:
/spark/bin/spark-class org.apache.spark.deploy.worker.Worker \
--webui-port 8080 spark://spark-master:7077
複製代碼
注:此時回看
Spark-Master
容器,會發現多了一行日誌:
INFO Master:54 - Registering worker 172.18.0.3:36486 with 2 cores, 1024.0 MB RAM
複製代碼
至此,Spark 集羣已經安裝成功了
Spark
集羣實踐通常是一主兩從
集羣架構,因此咱們還能夠新建一個Spark-Work2
容器,指令跟以前類似:
docker run --rm -it --name spark-worker2 --hostname spark-worker2 \
--network spark_network \
vinci/spark:latest /bin/sh
複製代碼
進入spark-worker2
容器以後,繼續啓動Spark-Worker
服務:
/spark/bin/spark-class org.apache.spark.deploy.worker.Worker \
--webui-port 8080 spark://spark-master:7077
複製代碼
而後宿主機,瀏覽器輸入:虛擬機IP:8080
,驗證Spark
服務:
再次啓動一個容器進入到spark-network
中:
docker run --rm -it --network spark_network \
$MYNAME/spark:latest /bin/sh
docker run --rm -it --network spark_network \
vinci/spark:latest /bin/sh
複製代碼
運行官方提供的樣例:
/spark/bin/spark-submit --master spark://spark-master:7077 --class \
org.apache.spark.examples.SparkPi \
/spark/examples/jars/spark-examples_2.11-2.4.0.jar 1000
複製代碼
運行以後會看到嘩啦啦的日誌輸出,咱們也能夠經過Web-UI
來進行監控。
經過Docker Compose
能夠極大簡化咱們的安裝部署流程。
這一節將對以前的知識點進行彙總,因此嫌麻煩的能夠不看前面,直接看這裏。
sudo curl -L "https://github.com/docker/compose/releases/download/1.23.1/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
sudo chmod +x /usr/local/bin/docker-compose
docker-compose --version
複製代碼
爲容器添加Spark
的環境變量,這樣就不須要輸入前面一大串絕對路徑了。
cd /root/docker/spark
vim bashrc
複製代碼
添加環境變量
SPARK_HOME=/spark
PATH=$PATH:$SPARK_HOME/bin
複製代碼
啓動腳本也就是以前咱們進入容器輸入的啓動spark-master
或者spark-worker
的命令。
注意腳本的第一行必須是:#!/bin/bash
mkdir -p /root/docker/spark/scripts
cd /root/docker/spark/scripts
vim start-master.sh
vim start-worker.sh
vim start-all.sh
複製代碼
#!/bin/bash
source /root/.bashrc
export SPARK_MASTER_HOST=`hostname`
mkdir -p $SPARK_MASTER_LOG
export SPARK_HOME=/spark
ln -sf /dev/stdout $SPARK_MASTER_LOG/spark-master.out
spark-class org.apache.spark.deploy.master.Master \
--ip $SPARK_MASTER_HOST \
--port $SPARK_MASTER_PORT \
--webui-port $SPARK_MASTER_WEBUI_PORT >> $SPARK_MASTER_LOG/spark-master.out
複製代碼
#!/bin/bash
source /root/.bashrc
mkdir -p $SPARK_WORKER_LOG
export SPARK_HOME=/spark
ln -sf /dev/stdout $SPARK_WORKER_LOG/spark-worker.out
spark-class org.apache.spark.deploy.worker.Worker \
--webui-port $SPARK_WORKER_WEBUI_PORT \
$SPARK_MASTER >> $SPARK_WORKER_LOG/spark-worker.out
複製代碼
這個start-shell.sh
腳本的做用是,在運行容器時,默認就進入spark-shell
:
#!/bin/bash
source /root/.bashrc
export SPARK_MASTER_HOST=`hostname`
mkdir -p $SPARK_MASTER_LOG
export SPARK_HOME=/spark
ln -sf /dev/stdout $SPARK_MASTER_LOG/spark-master.out
spark-class org.apache.spark.deploy.master.Master \
--ip $SPARK_MASTER_HOST \
--port $SPARK_MASTER_PORT \
--webui-port $SPARK_MASTER_WEBUI_PORT >> $SPARK_MASTER_LOG/spark-master.out
複製代碼
腳本建立完成以後賦予可執行權限:
chmod +x start-master.sh start-worker.sh start-shell.sh
有了這些腳本以後即可以構建本身所須要的Spark
鏡像了。
cd /root/docker/spark
vim Dockerfile
複製代碼
內容以下:
FROM openjdk:8-alpine
ENV SPARK_MASTER_PORT 7077
ENV SPARK_MASTER_WEBUI_PORT 8080
ENV SPARK_MASTER_LOG /spark/logs
ENV SPARK_WORKER_LOG /spark/logs
ENV SPARK_VERSION 2.4.0
# 工具類
RUN apk --update --no-cache add \ wget tar bash # Spark 壓縮包下載
RUN wget https://archive.apache.org/dist/spark/spark-${SPARK_VERSION}/spark-${SPARK_VERSION}-bin-hadoop2.7.tgz
# 解壓並刪除多餘壓縮包
RUN tar -xzf spark-${SPARK_VERSION}-bin-hadoop2.7.tgz && \ mv spark-${SPARK_VERSION}-bin-hadoop2.7 /spark && \ rm spark-${SPARK_VERSION}-bin-hadoop2.7.tgz
# 複製環境變量
COPY bashrc /root/.bashrc # 複製啓動腳本(包括啓動Master和Worker)到容器根目錄
COPY scripts/* /
# 暴露端口
EXPOSE 8080 7077 6066
# 默認啓動 Spark-shell 暫不開啓
# ENTRYPOINT ["/start-shell.sh"]
複製代碼
而後編譯鏡像
docker build -t vinci/spark:latest .
複製代碼
編譯完成以後進入容器檢查一下
docker run --rm -it --network spark_network \
vinci/spark:latest /bin/sh
複製代碼
docker-compose.yml
建立一個新文件:docker-compose.yml
,輸入如下配置:
version: "3.3"
services:
spark-master:
image: vinci/spark:latest
container_name: spark-master
hostname: spark-master
ports:
- "8080:8080"
- "7077:7077"
networks:
- spark-network
environment:
- "SPARK_LOCAL_IP=spark-master"
- "SPARK_MASTER_PORT=7077"
- "SPARK_MASTER_WEBUI_PORT=8080"
command: "/start-master.sh"
spark-worker:
image: vinci/spark:latest
depends_on:
- spark-master
ports:
- 8080
networks:
- spark-network
environment:
- "SPARK_MASTER=spark://spark-master:7077"
- "SPARK_WORKER_WEBUI_PORT=8080"
entrypoint: "/start-worker.sh"
volumes:
- "./:/local"
networks:
spark-network:
driver: bridge
ipam:
driver: default
複製代碼
接下來要作的事情就很簡單了,直接運行如下命令就行:
docker-compose up --scale spark-worker=3
複製代碼
其中--scale
做用是:Sets the number of containers to run for a service.

運行成功以後能夠新建一個SSH
鏈接到虛擬機CentOS
上,輸入docker container ls
查看當前正在運行的容器:
須要注意的是,這裏經過docker-compose
啓動spark
集羣的方式,net-work
的名字叫作:spark_spark-network
啓動測試容器:
docker run --rm -it --network spark_spark-network vinci/spark:latest /bin/sh
複製代碼
運行官方示例:
/spark/bin/spark-submit --master spark://spark-master:7077 --class \
org.apache.spark.examples.SparkPi \
/spark/examples/jars/spark-examples_2.11-2.4.0.jar 1000
複製代碼
輸出:Pi is roughly 3.1414315514143154
至此,本章教程結束。