性能调优

环境信息

使用的 hadoop 完全分布式集群

1
2
3
192.168.2.241 hadoop01 
192.168.2.242 hadoop02
192.168.2.243 hadoop03

Yarn 资源调度

Yarn 中有三种资源调度器可供选择

  1. FIFO Scheduler : 按照时间先后顺序进行服务, 一般不用。 hadoop1.x 默认使用
  2. Capacity Scheduler : 容量调度器, 多用户,多队列。 hadoop2.x, hadoop3.x, 默认使用
  3. Fair Scheduler : 公平调度器, 支持多用户、多分组管理.

Capacity Scheduler

容量资源调度器,支持多队列,但默认情况下只有 root.default 这一个队列

让任务运行在指定的队列

  1. 直接指定队列名
  2. 通过用户名、用户组和队列名进行对应

Fair Scheduler

Fair Scheduler 将整个 Yarn 的可用资源划分成多个队列资源池,每个队列中可以配置最小和最大的可用资源(内存和 CPU)、最大可同时运行 Application 数量、权重,以及可以提交和管理 Application 的用户等。

启用 Fair Scheduler

/etc/hadoop/conf/yarn-site.xml 添加

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
<!-- 设置为公平调度  -->
<property>
<name>yarn.resourcemanager.scheduler.class</name>
<value>org.apache.hadoop.yarn.server.resourcemanager.scheduler.fair.FairScheduler</value>
</property>

<!-- 公平调度配置路径 -->
<property>
<name>yarn.scheduler.fair.allocation.file</name>
<value>/etc/hadoop/conf/fair-scheduler.xml</value>
</property>

<!-- 未指定队列名时,将以用户名作为队列名 -->
<property>
<name>yarn.scheduler.fair.user-as-default-queue</name>
<value>true</value>
<description>default is True</description>
</property>

<!-- 开启抢占模式 允许调度器杀掉占用超过其应占资源份额队列的 containers -->
<property>
<name>yarn.scheduler.fair.preemption</name>
<value>true</value>
</property>

/etc/hadoop/conf/fair-scheduler.xml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
<?xml version="1.0"?>
<allocations>
<!-- users max running apps -->
<userMaxAppsDefault>10</userMaxAppsDefault>
<queue name="root">
<aclSubmitApps> </aclSubmitApps>
<aclAdministerApps> </aclAdministerApps>
<queue name="default">
<minResources>12000mb,5vcores</minResources>
<maxResources>100000mb,50vcores</maxResources>
<maxRunningApps>22</maxRunningApps>
<schedulingMode>fair</schedulingMode>
<weight>1</weight>
<aclSubmitApps>*</aclSubmitApps>
</queue>

<queue name="dev_group">
<minResources>115000mb,50vcores</minResources>
<maxResources>500000mb,150vcores</maxResources>
<maxRunningApps>181</maxRunningApps>
<schedulingMode>fair</schedulingMode>
<weight>5</weight>
<aclSubmitApps> dev_group</aclSubmitApps>
<aclAdministerApps>hadoop dev_group</aclAdministerApps>
</queue>


<queue name="test_group">
<minResources>23000mb,10vcores</minResources>
<maxResources>300000mb,100vcores</maxResources>
<maxRunningApps>22</maxRunningApps>
<schedulingMode>fair</schedulingMode>
<weight>4</weight>
<aclSubmitApps> test_group</aclSubmitApps>
<aclAdministerApps>hadoop test_group</aclAdministerApps>
</queue>

</queue>
<queuePlacementPolicy>
<rule name="user" create="false" />
<rule name="primaryGroup" create="false" />
<rule name="secondaryGroupExistingQueue" create="false" />
<rule name="default" queue="default" />
</queuePlacementPolicy>

<fairSharePreemptionTimeout>60</fairSharePreemptionTimeout>
<defaultFairSharePreemptionTimeout>60</defaultFairSharePreemptionTimeout>
</allocations>

不同

容量调度器的调度策略是,先选择资源利用率低的队列,然后在队列中同时考虑 FIFO 和内存因素
公平调度器仅考虑公平,而公平是通过任务缺额体现的,调度器每次选择缺额最大的任务(队列的资源量,任务的优先
级等仅用于计算任务缺额)

容量调度器的调度策略是,先选择资源利用率低的队列,然后在队列中同时考虑 FIFO 和内存因素;而公平调度器仅考虑公平,而公平是通过任务缺额体现的,调度器每次选择缺额最大的任务(队列的资源量,任务的优先级等仅用于计算任务缺额)

HDFS 存储权限

刚开始

1
2
3
4
5
6
7
8
9
10
[hadoop@hadoop01 sbin]$ hadoop fs -ls /demo
Found 1 items
-rw-r--r-- 2 hadoop supergroup 105 2022-05-16 23:36 /demo/demo.txt
[hadoop@hadoop01 sbin]$ hadoop fs -getfacl /demo/demo.txt
# file: /demo/demo.txt
# owner: hadoop
# group: supergroup
user::rw-
group::r--
other::r--

修改 /etc/hadoop/conf/hdfs-site.xml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
<property> 
<name>fs.permissions.umask-mode</name>
<value>026</value>
</property>


<!-- 开启 HDFS 的权限控制机制 -->
<property>
<name>dfs.permissions.enabled</name>
<value>true</value>
</property>
<!-- 开启 ACL 精细化控制 -->
<property>
<name>dfs.namenode.acls.enabled</name>
<value>true</value>
</property>

修改完后 重启 dfs

默认情况下新文件的权限默认是 666 与 umask 的交集,新目录的权限是 777 与 umask 的交集,如果 umask 为 026,那么新文件的权限就是 640,新目录的权限就是 751

测试

1
2
3
4
5
6
7
8
9
[hadoop@hadoop01 sbin]$ hadoop fs -put /tmp/demo_acl_test.txt /demo
[hadoop@hadoop01 sbin]$ hadoop fs -ls /demo
Found 2 items
-rw-r--r-- 2 hadoop supergroup 105 2022-05-16 23:36 /demo/demo.txt
-rw-r----- 2 hadoop supergroup 105 2022-05-25 04:20 /demo/demo_acl_test.txt
[hadoop@hadoop01 sbin]$ hadoop fs -mkdir /acl_test
[hadoop@hadoop01 sbin]$ hadoop fs -ls /
Found 10 items
drwxr-x--x - hadoop supergroup 0 2022-05-25 04:22 /acl_test

通过 ACL 机制,可以实现 HDFS 文件系统更精细化的权限控制

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
[hadoop@hadoop01 sbin]$ hdfs dfs -setfacl -m user:hive:rw- /demo/demo.txt
[hadoop@hadoop01 sbin]$ hadoop fs -getfacl /demo/demo_acl_test.txt
# file: /demo/demo_acl_test.txt
# owner: hadoop
# group: supergroup
user::rw-
group::r--
other::---

[hadoop@hadoop01 sbin]$ hadoop fs -getfacl /demo/demo.txt
# file: /demo/demo.txt
# owner: hadoop
# group: supergroup
user::rw-
user:hive:rw-
group::r--
mask::rw-
other::r--

Yarn、HDFS、Kafka 内存调优策略以及性能瓶颈

Yarn 的内存和 CPU 调优

在 Yarn 集群中,平衡内存、CPU、磁盘这三者的资源分配是很重要的,最基本的经验就是: 每两个 Container 使用一块磁盘、一个 CPU 核,这种配置,可以使集群的资源得到一个比较好的平衡利用

Yarn 的内存优化主要涉及 ResourceManager、NodeManager 相关进程以及 Yarn 的一些配置参数

  1. ResourceManager: 通常建议将 ResourceManager 独立运行在一台服务器上,所以只考虑操作系统对内存的占用即可
    比如 8G 内存的服务器,单独部署 ResourceManager

/etc/hadoop/conf/yarn-env.sh

1
2
export YARN_RESOURCEMANAGER_HEAPSIZE=8192 
export YARN_RESOURCEMANAGER_OPTS="-server -Xms${YARN_RESOURCEMANAGER_HEAPSIZE}m -Xmx${YARN_RESOURCEMANAGER_HEAPSIZE}m"

  1. NodeManager 充当 shuffle 任务的 server 端时,内存应该调大
    /etc/hadoop/conf/yarn-env.sh

    1
    2
    export YARN_NODEMANAGER_HEAPSIZE=4096 
    export YARN_NODEMANAGER_OPTS="-Xms${YARN_NODEMANAGER_HEAPSIZE}m -Xmx${YARN_NODEMANAGER_HEAPSIZE}m"
  2. 参数优化
    /etc/hadoop/conf/yarn-site.xml
    /etc/hadoop/conf/mapred-site.xml

需要根据任务内存,cpu 等进行综合考虑

RM 的内存资源配置
NM 的内存资源配置
AM 内存配置相关参数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
RM1:yarn.scheduler.minimum-allocation-mb,表示单个容器可以申请的最小内存,默认 1024MB。

RM2:yarn.scheduler.maximum-allocation-mb,表示单个容器可以申请的最大内存,默认8291MB。

APP1:yarn.app.mapreduce.am.resource.mb,MR 运行于 Yarn 上时,为 AM 分配多少内存。

APP2:yarn.app.mapreduce.am.command-opts,运行 MRAppMaster 时的 jvm 参数,可设置 -Xmx、-Xms 等选项。

NM 的内存资源配置

NM1:yarn.nodemanager.resource.memory-mb,表示节点可用的最大内存。

NM2:yarn.nodemanager.vmem-pmem-ratio,表示虚拟内存率,默认 2.1。

AM 内存配置相关参数

AM1:mapreduce.map.memory.mb,分配给 map Container 的内存大小。

AM2:mapreduce.map.java.opts,运行 map 任务的 jvm 参数,可设置 -Xmx、-Xms 等选项。

AM3:mapreduce.reduce.memory.mb,分配给 reduce Container 的内存大小。

AM4:mapreduce.reduce.java.opts,运行 reduce 任务的 jvm 参数,可设置 -Xmx、-Xms 等选项。

需要注意

RM1、RM2 的值均不能大于 NM1 的值

AM1 和 AM3 的值应该在 RM1 和 RM2 这两个值之间

AM3 的值最好为 AM1 的两倍

AM2 和 AM4 的值应该在 AM1 和 AM3 之间

  1. cpu 优化
    1
    2
    3
    4
    5
    yarn.nodemanager.resource.cpu-vcores 表示该节点服务器上 Yarn 可使用的虚拟 CPU 个数,默认为 8。由于需要给操作系统、datanode、nodemanager 进程预留一定量的 CPU,所以一般将系统 CPU 的 90% 留给此参数即可,例如集群节点有 32 个 core,那么分配 28 个 core 给 yarn。

    yarn.scheduler.minimum-allocation-vcores 表示单个任务可申请的最小虚拟核数,默认为 1。

    yarn.scheduler.maximum-allocation-vcores 表示单个任务可申请的最大虚拟核数,默认为 4。

HDFS 的内存和 CPU 调优

HDFS 性能参数配置

1
2
3
4
5
dfs.replication  副本数,一般设置为 3
dfs.block.size 数据块大小,一般为 128 或 128 的整数,据块设置太小,会增加 NameNode 的压力;数据块设置过大,会增加定位数据的时间
dfs.datanode.data.dir HDFS 数据块的存储路径,最好为独立磁盘的路径

dfs.datanode.max.transfer.threads datanode 可 同时处理的最大文件数量 ,建议将这个值尽量调大,最大值可以配置为 65535

HDFS 内存资源调优

主要是配置 Namenode 的堆内存。Namenode 堆内存配置过小,会导致频繁产生 Full GC,进而导致 namenode 宕机;而在 Hadoop 中,数据的读取、写入都要经过 namenode,所以 namenode 的堆内存需要足够多,尤其是在海量数据读写场景中. 一般将 Namenode 放在单独的服务器上

建议 Namenode 堆内存大小设置为物理内存的一半以上
/etc/hadoop/conf/hadoop-env.sh

1
2
export HADOOP_HEAPSIZE_MAX=30720 
export HADOOP_HEAPSIZE_MIN=30720

建议 Namenode 堆内存大小设置为物理内存的一半以上。
/etc/hadoop/conf/hadoop-env.sh

1
2
export HDFS_DATANODE_HEAPSIZE=4096 
export HDFS_DATANODE_OPTS="-Xms${HDFS_DATANODE_HEAPSIZE}m -Xmx${HDFS_DATANODE_HEAPSIZE}m"

Kafka 性能调优

Kafka 是一个高吞吐量分布式消息系统,并且提供了持久化存储功能,其高性能有两个重要特征:

  1. 磁盘连续读写性能远远高于随机读写的特点
  2. 通过将一个 topic 拆分多个 partition,可提供并发和吞吐量

内存调优,修改 系统文件

1
2
vm.dirty_background_ratio /proc/sys/vm/dirty_background_ratio  5%
vm.dirty_ratio /proc/sys/vm/dirty_ratio 10%

/opt/bigdata/kafka/current/config/server.properties

topic 的拆分

将不同的 partition 分布在不同在磁盘上,可以将磁盘的多个目录配置到 broker 的 log.dirs

1
log.dirs=/disk1/logs,/disk2/logs,/disk3/logs

配置参数优化

1
2
3
4
5
log.retention.hours=72
log.segment.bytes=1073741824

log.flush.interval.messages=10000
log.flush.interval.ms=1000

日志保留3 天,段文件 1G,每当 producer 写入 10000 条消息或 1s 刷数据到磁盘