使用cgroup对storm中的拓扑进行资源隔离
为什么需要对storm中的拓扑进行资源隔离
从部署结构来看,storm集群上的业务拓扑是混跑的,不可避免会出现资源争夺进而相互影响,主要有以下几种情况:
- 由于程序bug导致资源占用异常
- 由于消息量突增,而拓扑Bolt的并行度设置太小,导致消息在storm内部队列(disruptor queue)堆积,最终导致CPU使用率增高
- 由于Bolt依赖的资源变慢,导致处理能力不足,导致消息堆积,CPU使用增高
cgroup简介
概念
cgroups(control groups)是Linux内核提供的一项用来限制及分离一组进程资源使用(CPU,内存,磁盘IO,网络等)的特性,从内核版本2.6.24开始支持。
cgroups中的基本概念如下:
- 任务(task):系统中的线程
- 控制组(cgroup):资源控制的最小单位
- 子系统(subsystem):不同子系统代表不同类型的资源,如cpu子系统,memory子系统,目前支持的子系统如下:
- cpu:基于时间片的CPU限制
- cpuset:基于CPU核心的CPU限制
- cpuact:生成CPU使用报告
- memory:内存限制、内存使用报告
- blkio:块设备输入输出限制,如磁盘IO
- devices、freezer、net_cls、hugetlb、perf_event
- 层级(hierachy):控制组的组织形式,关联了一个或多个subsystem的cgroups目录树
以上概念之间的关系可以通过一张图来概括:其中一个控制组关联了一组控制参数和线程pid,用于对特定线程组进行控制
配置项
下面对storm中可能使用到的cgroups配置项进行介绍:
通用配置项
- tasks & cgroup.procs:这两个参数的区别是,将一个线程pid加入tasks仅这个线程会受到相应控制组的控制,而将一个线程pid加入cgroup.procs,会将这个线程所属的线程组pid都加进来,这个线程组都会受到相应的控制组的控制
- notify_on_release & release_agent:两个参数配合使用,可以指定当一个控制组中的tasks全部退出时是否(由notify_on_release控制)触发指定的操作(由release_agent指定)
CPU子系统配置项:
- cpu.cfs_period_us & cpu.cfs_quota_us:CPU使用时间绝对上限
- cpu.stat:数据统计,nr_periods、nr_throttled、throttled_time
- cpu.shares:CPU使用时间权重相对值
详细参考资料
对cgroup有兴趣的同学可以参考如下资料,概念和例子应有尽有,就不在赘述
- https://www.kernel.org/doc/Documentation/cgroups/
- https://access.redhat.com/documentation/en-US/Red_Hat_Enterprise_Linux/6/html/Resource_Management_Guide/index.html
- http://coolshell.cn/articles/17049.html
- http://tiewei.github.io/devops/howto-use-cgroup/
- http://www.infoq.com/cn/articles/docker-kernel-knowledge-cgroups-resource-isolation
storm 0.9.x版本使用cgroup
0.9.x版本的storm并未提供cgroup的资源控制机制,因此需要使用外挂程序的方式(如定时执行脚本的方式)来对拓扑的资源使用进行限制, 以下为对每个worker的最大cpu使用时间进行限制的简单实现。
- CPU守护:每台supervisor上执行crontab定时任务,将worker进程定时加入CPU控制组,限制worker进程最大CPU使用时间
1 | 控制组结构: |
- cgroup清理:woker进程死掉后(一般由kill拓扑或者rebalance触发),自动清理无用的CPU控制组可以通过设置参数notify_on_release=1 & release_agent=/path/storm-cpu-cgroup-remove.sh来实现
- 阈值报警:当cgroup到达最大限制值时,需报警通知业务人员进行干预。可以通过cpu.stat中的统计值来实现,如
1 | alarm=(nr_throttled_t2-nr_throttled_t1)/(nr_periods_t2-nr_periods_t1) |
脚本参考:
https://github.com/lostk1ng/storm-cgroups
storm 1.0.x版本使用cgroup
1.0.x版本的storm官方文档已经声称支持cgroups, 但是发现相关PR只merge到了master分支,并没有merge到1.0.x-branch,因此目前最新版本的storm仍然不支持cgroups。