Doris离线分析数仓集群实现资源隔离
一、背景
随着业务快速发展,目前离线分析数仓Doris集群,承载着多样化的计算需求,比如数据科学日常Job、业务离线跑批、客户侧报表查询等,会出现资源抢占情况,需要对不同账户资源请求进行资源限制,经过调研采用Doris官方的Workload Group方案。
Doris版本:doris-2.1.8-1-834d802457
二、Workload Group介绍:
Workload Group是Apache Doris提供的进程内资源隔离机制,通过对 BE进程内的CPU、内存、IO资源进行细粒度划分,实现不同业务负载之间的资源隔离。
原理如下图所示:

目前支持的隔离能力包括:
| 资源类型 | 隔离方式 | 说明 |
|---|---|---|
| CPU | 软限 / 硬限 | 软限按权重分配,硬限为绝对上限 |
| 内存 | 软限 / 硬限 | 硬限超限时自动 kill 查询释放内存 |
| IO | 限速 | 限制读本地/远程文件的 IO 吞吐 |
| 并发 | 排队机制 | 超并发查询进入队列等待 |
更多参考: https://doris.apache.org/zh-CN/docs/2.1/admin-manual/workload-management/workload-group
三、Doris集群调整,支持Cgroup(手动部署)
3.1 Cgroup环境配置
查看系统支持的 CGroup版本
root@doristest:~# cat /proc/filesystems | grep cgroup
nodev cgroup
nodev cgroup2
确认Cgroup生效版本:
root@doristest:~# ls /sys/fs/cgroup/cpu/
ls: cannot access '/sys/fs/cgroup/cpu/': No such file or directory
root@doristest:~# ls /sys/fs/cgroup/cgroup.controllers
/sys/fs/cgroup/cgroup.controllers # 说明生效版本为cgroup v2
3.2 创建Doris CGroup 目录
# ========== CGroup v1 操作 ==========
mkdir /sys/fs/cgroup/cpu/doris
# 设置权限(root 为运行 BE 的用户)
chmod 770 /sys/fs/cgroup/cpu/doris
chown -R root:root /sys/fs/cgroup/cpu/doris
# ========== CGroup v2 操作 ==========
mkdir /sys/fs/cgroup/doris
# 设置权限
chmod 770 /sys/fs/cgroup/doris
chown -R root:root /sys/fs/cgroup/doris # 视情况而定,目前为root
3.3 CGroup v2 额外配置
CGroup v2 权限管控更严格,需要额外配置:
# 修改根目录 cgroup.procs 文件权限
chmod a+w /sys/fs/cgroup/cgroup.procs
# 启用 cpu 控制器
# 进入 doris 目录
cd /sys/fs/cgroup/doris
# 启用 cpu 控制器(通过修改父级 subtree_control)
# 默认已经设置,可忽略
echo +cpu > ../cgroup.subtree_control
# 验证:查看 doris 目录下是否出现 cpu.max 文件
/sys/fs/cgroup/doris/cpu.max
# 且 cgroup.controllers 应包含 cpu
# cat /sys/fs/cgroup/cgroup.controllers
cpuset cpu io memory hugetlb pids rdma misc
3.4 配置 BE 并重启
编辑 be.conf 文件:
# ========== CGroup v1 配置 ==========
doris_cgroup_cpu_path = /sys/fs/cgroup/cpu/doris
# ========== CGroup v2 配置 ==========
doris_cgroup_cpu_path = /sys/fs/cgroup/doris
重启 BE 服务:
# 重启 BE
./bin/stop_be.sh
./bin/start_be.sh
验证:查看 be.INFO 日志
grep "add thread" log/be.INFO
# 出现 "add thread xxx to group" 字样表示配置成功
3.5 持久化配置(可选)
机器重启后 CGroup 配置会清空,建议使用 systemd 创建开机自动配置服务:
# /etc/systemd/system/doris-cgroup.service
[Unit]
Description=Doris CGroup Setup
Before=doris-be.service
[Service]
Type=oneshot
ExecStart=/bin/bash -c 'mkdir -p /sys/fs/cgroup/cpu/doris && chmod 770 /sys/fs/cgroup/cpu/doris && chown -R doris:doris /sys/fs/cgroup/cpu/doris'
[Install]
WantedBy=multi-user.target
设置开机自动启动:
systemctl enable doris-cgroup.service
四、通过Ansible批量启用Doris节点Cgroup
4.1 准备工作
在执行批量部署前,需要确认以下信息:
- 确认Cgroup版本:所有Doris BE节点的Cgroup版本(v1或v2)
- 准备主机清单:编辑Ansible的hosts文件,添加所有BE节点
- 确认BE用户:运行Doris BE服务的用户(当前为root)
4.2 配置主机清单
编辑 hosts 文件:
4.3 创建Ansible Playbook
创建文件 setup_doris_cgroup.yaml:
|
|
4.4 执行批量部署
语法检查和试运行
4.5 正式执行并验证部署结果
正式执行
通过Doris Manager管理节点调整Doris BE配置(滚动重启):
# ========== CGroup v1 配置 ==========
doris_cgroup_cpu_path = /sys/fs/cgroup/cpu/doris
# ========== CGroup v2 配置 ==========
doris_cgroup_cpu_path = /sys/fs/cgroup/doris

验证:
|
|
至此,Doris BE节点已经开启Cgroup资源限制.
五、Workload Group管理
5.1 创建 Workload Group
基础示例(CPU 软限)
完整配置示例
|
|
5.2 属性详解
| 属性名 | 类型 | 默认值 | 取值范围 | 说明 |
|---|---|---|---|---|
| cpu_share | INT | -1 | [1, 10000] | CPU 软限权重,值越大优先级越高 |
| cpu_hard_limit | INT | -1 | [1%, 100%] | CPU 硬限百分比(2.1 版本新增) |
| memory_limit | FLOAT | -1 | (0%, 100%] | 内存限制百分比 |
| enable_memory_overcommit | BOOL | true | true/false | true=软限(可超额),false=硬限 |
| max_concurrency | INT | 2147483647 | [0, 2147483647] | 最大并发查询数 |
| max_queue_size | INT | 0 | [0, 2147483647] | 排队队列长度(0=不排队) |
| queue_timeout | INT | 0 | [0, 2147483647] | 排队超时时间(毫秒) |
| scan_thread_num | INT | -1 | [1, 2147483647] | Scan 线程数(-1=使用 BE 配置) |
| max_remote_scan_thread_num | INT | -1 | [1, 2147483647] | 外表 Scan 最大线程数 |
| min_remote_scan_thread_num | INT | -1 | [1, 2147483647] | 外表 Scan 最小线程数 |
| read_bytes_per_second | INT | -1 | [1, 9223372036854775807] | 内表读 IO 限速(字节/秒) |
| remote_read_bytes_per_second | INT | -1 | [1, 9223372036854775807] | 外表读 IO 限速(字节/秒) |
注意事项:
- 创建时必须至少指定一个属性
- CGroup v1 的 cpu_share 默认值为 1024,取值范围 2-262144
- CGroup v2 的 cpu_share 默认值为 100,取值范围 1-10000
- 所有 Workload Group 的 memory_limit 累加不能超过 100%
- 所有 Workload Group 的 cpu_hard_limit 累加不能超过 100%
5.3 修改 Workload Group
ALTER WORKLOAD GROUP g1 PROPERTIES('cpu_share' = '4096');
-- 修改内存限制为硬限
ALTER WORKLOAD GROUP g1 PROPERTIES(
'memory_limit' = '30%',
'enable_memory_overcommit' = 'false'
);
-- 修改并发和排队参数
ALTER WORKLOAD GROUP g1 PROPERTIES(
'max_concurrency' = '100',
'max_queue_size' = '200',
'queue_timeout' = '30000'
);
-- 添加 CPU 硬限(需先开启硬限模式)
ALTER WORKLOAD GROUP g1 PROPERTIES('cpu_hard_limit' = '20%');
5.4 删除 Workload Group
- 删除指定 Workload Group
DROP WORKLOAD GROUP g1;
– 注意:系统默认的 normal 组不可删除
六、用户绑定与授权
6.1 查看可用 Workload Group
-- 查看当前用户有权限使用的 Workload Group
SELECT name FROM information_schema.workload_groups;
6.2 授权
-- 授予用户使用指定 Workload Group 的权限
GRANT USAGE_PRIV ON WORKLOAD GROUP 'g1' TO 'user_1'@'%';
-- 授予所有 Workload Group 权限
GRANT USAGE_PRIV ON WORKLOAD GROUP '*' TO 'user_1'@'%';
-- 撤销权限
REVOKE USAGE_PRIV ON WORKLOAD GROUP 'g1' FROM 'user_1'@'%';
6.3 绑定方式一:用户属性(推荐)
为用户设置默认 Workload Group,持久生效:
-- 设置用户默认 Workload Group
SET PROPERTY FOR 'user_1' = 'default_workload_group' = 'g1';
-- 查看用户属性
SHOW PROPERTY FOR 'user_1';
七、监控与查看
7.1 查看 Workload Group 列表
-- Show 语句
SHOW WORKLOAD GROUPS;
-- 系统表查询
SELECT * FROM information_schema.workload_groups;
7.2 查看资源使用情况
-- 查看各 Workload Group 内存使用(单位:MB)
SELECT
workload_group_id,
name,
MEMORY_USAGE_BYTES / 1024 / 1024 AS mem_used_mb,
CPU_USAGE_PERCENT AS cpu_percent
FROM workload_group_resource_usage;
-- 查看特定 Workload Group 详情
SELECT * FROM information_schema.workload_groups WHERE name = 'g1';
7.3 系统表字段说明
workload_groups 表
| 字段 | 说明 |
|---|---|
| ID | Workload Group ID |
| NAME | 名称 |
| CPU_SHARE | CPU 软限权重 |
| MEMORY_LIMIT | 内存限制百分比 |
| ENABLE_MEMORY_OVERCOMMIT | 是否允许内存超配 |
| MAX_CONCURRENCY | 最大并发数 |
| MAX_QUEUE_SIZE | 队列长度 |
| QUEUE_TIMEOUT | 排队超时时间 |
| CPU_HARD_LIMIT | CPU 硬限百分比 |
| SCAN_THREAD_NUM | Scan 线程数 |
| READ_BYTES_PER_SECOND | 内表 IO 限速 |
| REMOTE_READ_BYTES_PER_SECOND | 外表 IO 限速 |
八、CPU 软硬限模式切换
8.1 模式说明
| 模式 | 特点 | 适用场景 |
|---|---|---|
| CPU 软限 | 按权重分配 CPU 时间,空闲时可使用全部 CPU | 负载波动大,希望充分利用资源 |
| CPU 硬限 | 绝对上限,无论 CPU 是否空闲都不能超过 | 需要严格资源隔离,保障 SLA |
注意:一个集群同一时刻只能使用一种模式,不能混用。
8.2 从软限切换到硬限
步骤 1:为所有 Workload Group 设置硬限值
-- 必须为所有 Group 设置 cpu_hard_limit
ALTER WORKLOAD GROUP g1 PROPERTIES('cpu_hard_limit' = '30%');
ALTER WORKLOAD GROUP g2 PROPERTIES('cpu_hard_limit' = '20%');
ALTER WORKLOAD GROUP normal PROPERTIES('cpu_hard_limit' = '50%');
-- 验证:所有 Group 的 cpu_hard_limit 累加 <= 100%
SELECT SUM(cpu_hard_limit) FROM information_schema.workload_groups
WHERE cpu_hard_limit > 0;
步骤 2:开启集群硬限开关
-- 内存中立即生效(重启后失效)
ADMIN SET FRONTEND CONFIG ("enable_cpu_hard_limit" = "true");
-- 持久化配置:修改所有 FE 的 fe.conf
echo "experimental_enable_cpu_hard_limit = true" >> fe/conf/fe.conf
8.3 从硬限切换回软限
-- 关闭硬限开关(自动恢复为软限模式)
ADMIN SET FRONTEND CONFIG ("enable_cpu_hard_limit" = "false");
– 如需持久化,修改 fe.conf 为 false 或删除该配置
以上,为Doris离线分析数仓增加的资源限制的整体方案。
参考文档:https://doris.apache.org/zh-CN/docs/2.1/admin-manual/workload-management/workload-group