文章目录
安装虚拟机CentOS7
首先下载镜像文件如CentOS-7-x86_64-DVD-1908.iso
,然后通过VMWare workstation
安装CentOS7,采用自定义的方式安装,过程比较简单此处就不在这里截图说明。
如下图所示。注意此处我采用的桥接模式
连接网络,这样你的虚拟机就相当于你局域网内的一台真实主机。
机器 | 硬件 |
---|---|
master | 8G内存 处理器4 100G硬盘 |
slave1 | 6G内存 处理器4 60G硬盘 |
slave2 | 6G内存 处理器4 60G硬盘 |
配置网络
/etc/sysconfig/network-scripts/ifcfg-ens33
文件内容修改如下。
TYPE=Ethernet
BOOTPROTO=static
NAME=ens33
DEVICE=ens33
ONBOOT=yes
IPADDR=192.168.3.20
NETMASK=255.255.255.0
GATEWAY=192.168.3.1
DNS1=192.168.3.1
由于我们的网络设备是用ens33
,所以NAME
和DEVICE
都设置成ens33
。
采用静态设置IP的方式故设置BOOTPROTO=static
。
由于是静态设置IP,所以IP地址(IPADDR
)需要自定义,子网掩码(NETMASK
)和网关GATEWAY
及DNS服务器地址(DNS1
)需要和当前主机的网络环境保持一致。如下图
通过 systemctl restart network
可重启网络,ip addr
查看IP地址
设置hostname
hostnamectl set-hostname master
就将当前机器的hostname设置为master。该命令在重启机器后依然生效。
配置/etc/hosts文件
关闭防火墙
systemctl stop firewalld
关闭防火墙
systemctl disable firewalld
禁止防火墙开启启动
永久禁用selinux
编辑vi /etc/selinux/config
文件,内容如下图。修改后重启机器即可。
也可通过setenforce 0
临时关闭然后通过getenforce
查看
配置本地yum源
- 创建目录
mkdir /usr/local/src/packages
,通过WIN SCP
上传镜像文件CentOS-7-x86_64-DVD-1908.iso
到刚刚创建的目录。 - 创建挂载目录
mkdir /media/centos-7
。 - 挂载镜像文件
mount -t iso9660 -o loop /usr/local/src/packages/CentOS-7-x86_64-DVD-1908.iso /media/centos-7
- 设置开机自动挂载(因为上面的挂载只是临时的),编辑文件
vi /etc/fstab
,在最后面添加如下一行
/usr/local/src/packages/CentOS-7-x86_64-DVD-1908.iso /media/centos-7 iso9660 defaults,loop 0 0
- 添加自定义yum文件,新增
vi /etc/yum.repos.d/centos-7.repo
文件,内容如下
[7-Localsource]
name=CentOS7
baseurl=file:///media/centos-7
enabled=1
gpgcheck=0
-
删除
/etc/yum.repos.d
目录下其他的repo文件,或者将其备份到一个文件夹/etc/yum.repos.d/bak
。 -
执行
yum -y install vim
来安装vim
命令看是否成功。yum makecache
可以做本地yum缓存,yum clean all
可清除缓存。
-
采用
httpd
服务器给其他局域网内的机器做局部yum源,这样就不用在每台机器上重复上面的操作了。我们以master
机器为例,在其安装httpd
服务,yum -y install httpd
。启动
httpd
服务并执行开启自启,systemctl start httpd
,systemctl enable httpd
建立软连接,并通过浏览器查看
cd /var/www/html/
ln -s /media/centos-7 centos-7
- 其他机器的yum文件
/etc/yum.repos.d/centos-7.repo
就可以配置成如下
注意baseurl
,其中master
机器地址就是192.168.3.20
[7-Localsource]
name=CentOS7
baseurl=http://192.168.3.20/centos-7
enabled=1
gpgcheck=0
- 或者采用ftp服务器作为局部yum源。我们以
master
机器为例,在其安装vsftpd
服务,yum -y install vsftpd
。- 启动并开机自启
vsftpd
服务,systemctl start vsftpd
,systemctl enable httpd
- 修改配置文件
/etc/vsftpd/vsftpd.conf
,在其最后添加anon_root=/media
作为匿名用户的目录
- 禁用掉
selinux
,临时关闭可执行setenforce 0
,不关闭的话在浏览器上输入ftp://192.168.3.20/centos-7
是无法看到镜像文件内容的
- 启动并开机自启
- 其他机器的yum文件
/etc/yum.repos.d/centos-7.repo
就可以配置成如下
注意baseurl
,其中master
机器地址就是192.168.3.20
[7-Localsource]
name=CentOS7
baseurl=ftp://192.168.3.20/centos-7
enabled=1
gpgcheck=0
配置免密登录
在三台机器都执行了上面的操作并配置好yum源后,执行如下的脚本进行免密登录。
在/root
目录下创建文件夹auto-ssh
,然后将如下3个文件放入文件夹auto-ssh
内,最后执行./boot.sh
即可完成免密的配置。
auto.sh
文件内容如下。注意SERVERS
是所有的机器主机名(用空格隔开),PASSWORD
是所有机器统一的root密码。
#!/bin/bash
SERVERS="master slave1 slave2"
PASSWORD=root
auto_ssh_copy_id() {
expect -c "set timeout -1;
spawn ssh-copy-id $1;
expect {
*(yes/no)* {send -- yes\r;exp_continue;}
*assword:* {send -- $2\r;exp_continue;}
eof {exit 0;}
}";
}
ssh_copy_id_to_all() {
for SERVER in $SERVERS
do
auto_ssh_copy_id $SERVER $PASSWORD
done
}
ssh_copy_id_to_all
boot.sh
文件内容如下。注意SERVERS
和PASSWORD
。
#!/bin/bash
SERVERS="master slave1 slave2"
PASSWORD=root
auto_ssh_copy_id() {
expect -c "set timeout -1;
spawn ssh-copy-id $1;
expect {
*(yes/no)* {send -- yes\r;exp_continue;}
*assword:* {send -- $2\r;exp_continue;}
eof {exit 0;}
}";
}
ssh_copy_id_to_all() {
for SERVER in $SERVERS
do
auto_ssh_copy_id $SERVER $PASSWORD
done
}
yum -y install expect
expect key.exp
ssh_copy_id_to_all
for SERVER in $SERVERS
do
scp -r /root/auto-ssh root@$SERVER:/root
ssh root@$SERVER "yum -y install expect; expect /root/auto-ssh/key.exp; /root/auto-ssh/auto.sh"
done
key.exp
文件内容如下
#!/usr/bin/expect
spawn ssh-keygen
expect {
"save the key" {send "\n"; exp_continue}
"Overwrite (y/n)" {send "n\n"}
"Enter passphrase" {send "\n"; exp_continue}
"Enter same passphrase again" {send "\n"}
timeout {puts "expect connect timeout."; return}
}
expect eof
配置JDK
下载jdk文件如jdk-8u221-linux-x64.tar.gz
。一样上传到目录/usr/local/src/packages/
cd /usr/local/src
tar zxPvf packages/jdk-8u221-linux-x64.tar.gz -C ./
ln -s jdk1.8.0_221 jdk
设置环境变量, 编辑vim /etc/profile
文件,在文件最后添加如下内容
export SRC_HOME=/usr/local/src
export JAVA_HOME=${SRC_HOME}/jdk
export PATH=$PATH:$JAVA_HOME/bin
简单的集群操作脚本
该集群操作脚本只需在master
机器上运行,而无须像上面的操作一样需要在每台机器运行。
创建目录mkdir /root/cluster
,该目录下有如下3个脚本
common.sh
是用来存储公共方法的。
distribute.sh
是用来在集群分发文件的。
用法如 ./distribute.sh -h slave1,slave2 -s /etc/profile -d /etc
该命令是将当前主机的/etc/profile
文件发送到slave1
和slave2
机器的/etc
目录下,-h
指定主机列表(用逗号隔开),-s
表示源文件(或目录),-d
表示目的主机的目录。-s
和-d
指定的文件路径都是绝对路径。
exec.sh
是用来在集群每台机器内执行命令的。
用法如 ./exec.sh -h master,slave1,slave2 -c "java -version;"
该命令是在这三台机器上分别执行java -version
命令。-h
指定主机列表(用逗号隔开),-c
指定要执行的命令。
common.sh
文件内容如下
#!/bin/bash
#常用方法集合
function is_empty(){
if [ -z "$1" ]; then
echo "STRING is empty"
return 2
fi
}
## Error
function red(){
echo -e "`date '+%Y-%m-%d %H:%M:%S'` \033[31m\033[01m[ $1 ]\033[0m"
}
distribute.sh
文件内容如下
#!/bin/bash
#该文件是用来分发文件的
cd `dirname $0`
#加载公共方法
source ./common.sh
#主机列表,用逗号隔开
hostnames=""
#当前主机文件夹
source_dir=""
#目的主机文件夹
dest_dir=""
#解析参数
while getopts ":h:s:d:" opt
do
case $opt in
h)
echo "指定的主机列表是 $OPTARG"
hostnames=$OPTARG
;;
s)
echo "当前主机文件夹是 \"$OPTARG\""
source_dir=$OPTARG
;;
d)
echo "目的主机文件夹是 \"$OPTARG\""
dest_dir=$OPTARG
;;
?)
echo "未知参数"
exit 1;;
esac
done
is_empty $hostnames
if [ $? -eq 2 ]; then
red "主机列表为空"
exit 1
fi
is_empty $source_dir
if [ $? -eq 2 ]; then
red "当前主机文件夹为空"
exit 1
fi
is_empty $dest_dir
if [ $? -eq 2 ]; then
red "目的主机文件夹为空"
exit 1
fi
host_arr=(${hostnames//,/ })
for var in ${host_arr[@]}
do
echo "the host is $var."
scp -r $source_dir root@$var:$dest_dir
done
exec.sh
文件内容如下
#!/bin/bash
#主机列表,用逗号隔开
hostnames=""
#在各个主机中需要执行的命令
cmd=""
#解析参数
while getopts ":h:c:" opt
do
case $opt in
h)
echo "指定的主机列表是 $OPTARG"
hostnames=$OPTARG
;;
c)
echo "待执行的命令是 \"$OPTARG\""
cmd=$OPTARG
;;
?)
echo "未知参数"
exit 1;;
esac
done
host_arr=(${hostnames//,/ })
for var in ${host_arr[@]}
do
echo "the host is $var."
ssh -o ConnectTimeout=10 root@$var "source /etc/profile;$cmd"
echo ""
done
安装hadoop集群
以hadoop-2.6.5.tar.gz
安装包为例,放在/usr/local/src
目录下。
cd /usr/local/src
tar zxPvf packages/hadoop-2.6.5.tar.gz -C ./
ln -s hadoop-2.6.5 hadoop
- 配置环境变量
vim /etc/profile
,添加如下内容。并source /etc/profile
使环境变量生效。
export HADOOP_HOME=${SRC_HOME}/hadoop
export PATH=$PATH:$JAVA_HOME/bin:${HADOOP_HOME}/bin:${HADOOP_HOME}/sbin
- 修改
${HADOOP_HOME}/etc/hadoop/hadoop-env.sh
文件。JAVA_HOME
和HADOOP_PID_DIR
配置成指定目录。
# The java implementation to use.
export JAVA_HOME=/usr/local/src/jdk
# Assuming your installation directory is /usr/local/src/hadoop
export HADOOP_PREFIX=/usr/local/src/hadoop
# 该参数大约在97行左右能看到
export HADOOP_PID_DIR=${HADOOP_PREFIX}/pids
- 修改
${HADOOP_HOME}/etc/hadoop/mapred-env.sh
文件。指定PID目录。
export HADOOP_PREFIX=/usr/local/src/hadoop
export HADOOP_MAPRED_PID_DIR=${HADOOP_PREFIX}/pids
${HADOOP_HOME}/etc/hadoop/core-site.xml
文件内容如下
<configuration>
<property>
<name>fs.defaultFS</name>
<value>hdfs://master:9000</value>
</property>
<property>
<name>hadoop.tmp.dir</name>
<value>/usr/local/src/hadoop/tmp</value>
</property>
<!--将root用户设置为代理用户-->
<property>
<name>hadoop.proxyuser.root.hosts</name>
<value>*</value>
</property>
<property>
<name>hadoop.proxyuser.root.groups</name>
<value>*</value>
</property>
<!--hdfsui的访问用户从dr.who改为root,默认是dr.who-->
<property>
<name>hadoop.http.staticuser.user</name>
<value>root</value>
</property>
</configuration>
${HADOOP_HOME}/etc/hadoop/hdfs-site.xml
文件内容如下
<configuration>
<property>
<name>dfs.replication</name>
<value>3</value>
</property>
<property>
<name>dfs.namenode.name.dir</name>
<value>file:///usr/local/src/hadoop/dfs/name</value>
</property>
<property>
<name>dfs.datanode.data.dir</name>
<value>file:///usr/local/src/hadoop/dfs/data</value>
</property>
<property>
<name>dfs.namenode.secondary.http-address</name>
<value>master:50090</value>
</property>
</configuration>
${HADOOP_HOME}/etc/hadoop/mapred-site.xml
文件内容如下
<configuration>
<property>
<name>mapreduce.framework.name</name>
<value>yarn</value>
</property>
<property>
<name>mapreduce.map.memory.mb</name>
<value>900</value>
</property>
<property>
<name>mapreduce.reduce.memory.mb</name>
<value>900</value>
</property>
<property>
<name>mapreduce.map.java.opts</name>
<!--<value>-Xmx900M -verbose:gc -Xloggc:/tmp/@taskid@.gc -Dcom.sun.management.jmxremote=true -Dcom.sun.management.jmxremote.ssl=false -Dcom.sun.management.jmxremote.authenticate=fals
-->
<value>-Xmx900M</value>
</property>
<property>
<name>mapreduce.reduce.java.opts</name>
<!--<value>-Xmx920M -verbose:gc -Xloggc:/tmp/@taskid@.gc -Dcom.sun.management.jmxremote.authenticate=false -Dcom.sun.management.jmxremote.ssl=false</value>
--><value>-Xmx900M</value>
</property>
</configuration>
${HADOOP_HOME}/etc/hadoop/yarn-site.xml
文件内容如下
<configuration>
<property>
<name>yarn.nodemanager.aux-services</name>
<value>mapreduce_shuffle</value>
</property>
<property>
<name>yarn.log-aggregation-enable</name>
<value>false</value>
</property>
<!--Configurations for NodeManager-->
<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:8033</value>
</property>
<property>
<name>yarn.resourcemanager.webapp.address</name>
<value>master:8088</value>
</property>
<property>
<name>yarn.resourcemanager.scheduler.class</name>
<value>org.apache.hadoop.yarn.server.resourcemanager.scheduler.fair.FairScheduler</value>
</property>
<property>
<name>yarn.scheduler.minimum-allocation-mb</name>
<value>1024</value>
</property>
<property>
<name>yarn.scheduler.maximum-allocation-mb</name>
<value>8192</value>
</property>
<!--Configurations for NodeManager-->
<property>
<name>yarn.nodemanager.resource.memory-mb</name>
<value>4096</value>
</property>
<property>
<name>yarn.nodemanager.vmem-pmem-ratio</name>
<value>5.0</value>
</property>
<property>
<name>yarn.nodemanager.local-dirs</name>
<value>/usr/local/src/hadoop/tmp/nm-local-dir</value>
<description>List of directories to store localized files in. 存储媒介数据文件的</description>
</property>
<property>
<name>yarn.nodemanager.log-dirs</name>
<value>${yarn.log.dir}/userlogs</value>
<description>Where to store container logs</description>
</property>
<property>
<name>yarn.nodemanager.log.retain-seconds</name>
<value>108000</value>
<description>Time in seconds to retain user logs</description>
</property>
<property>
<name>yarn.nodemanager.remote-app-log-dir</name>
<value>/tmp/logs</value>
</property>
<property>
<name>yarn.nodemanager.remote-app-log-dir-suffix</name>
<value>logs</value>
</property>
<!--Monitoring the health of NodeManagers-->
<property>
<name>yarn.nodemanager.disk-health-checker.min-healthy-disks</name>
<value>0.25</value>
<description>The minimum fraction of number of disks to be healthy for the nodemanager to launch new containers</description>
</property>
<property>
<name>yarn.nodemanager.disk-health-checker.max-disk-utilization-per-disk-percentage</name>
<value>90.0</value>
<description>The maximum percentage of disk space utilization allowed after which a disk is marked as bad</description>
</property>
</configuration>
- 格式化
namenode
,执行hdfs namenode -format
观看有下面日志即代表成功
${HADOOP_HOME}/etc/hadoop/slaves
文件内容如下,指定slave1
和slave2
机器作为slave节点。
slave1
slave2
- 将上面的操作在
slave1
和slave2
机器执行一遍以保证集群配置一样。然后启动hdfs和yarn。
/root/cluster/start-mrjobhistory.sh
脚本内容如下,比较简单,就是启动每个nodemanager节点对应的MapReduceJobHistoryServer。当然我已经把/root/cluster
目录放到PATH
环境变量里了,这样就能直接运行。
#!/bin/bash
# 获取当前执行脚本的目录
dir=`dirname $0`
# 进入脚本所在目录
cd $dir
cmd="mr-jobhistory-daemon.sh start historyserver"
./exec.sh -h slave1,slave2 -c "source /etc/profile; $cmd"
测试hdfs和yarn
可以通过http://192.168.3.20:50070
查看HDFS UI界面,也可以通过命令行。
简单的在hdfs上创建目录、上传文件、查看目录
hdfs dfs -mkdir /abc
hdfs dfs -put ${HADOOP_HOME}/etc/hadoop/core-site.xml /abc
hdfs dfs -ls /abc
执行官方提供的wordCount例子,注意输出目录/out
不能已存在否则会报错。
hadoop jar $HADOOP_HOME/share/hadoop/mapreduce/hadoop-mapreduce-examples-2.6.5.jar wordcount /abc /out
查看wordCount结果
hdfs dfs -cat /out/* | tail