如何在Kubernetes中运行Kafka时管理页面缓存资源

kel*_*ket 6 page-caching apache-kafka cgroups kubernetes

我已经在Kubernetes上运行Kafka了一段时间没有任何重大问题; 然而,我最近推出了一组Cassandra pods并开始遇到Kafka的性能问题.

尽管Cassandra不像Kafka那样使用页面缓存,但它确实会频繁写入磁盘,这可能会影响内核的底层缓存.

我知道Kubernetes pod正在通过cgroup管理内存资源,可以通过在Kubernetes中设置内存请求和限制来配置,但我注意到Cassandra利用页面缓存可以增加我的Kafka pod中的页面错误数量,即使它们是似乎没有竞争资源(即,他们的节点上有可用的内存).

在Kafka中,更多页面错误会导致更多磁盘写入,这会妨碍顺序IO的优势并降低磁盘性能.如果您使用AWS的EBS卷,这将最终耗尽您的突发平衡并最终导致整个群集的灾难性故障.

我的问题是,是否有可能隔离Kubernetes中的页面缓存资源,或者以某种方式让内核知道我的Kafka pod所拥有的页面应该比我的Cassandra pod中的那些更长时间保存在缓存中?

Jon*_*ton 5

我认为这是一个有趣的问题,所以这是从一些挖掘中得出的一些发现。

最佳猜测:k8s OOB不能做到这一点,但是有足够的工具可用,因此它可能是研究和开发可作为DaemonSet部署的调整和策略应用程序的丰硕成果。

发现:

应用程序可以使用fadvise()系统调用向内核提供有关应用程序需要哪些文件支持的页面,哪些文件不能回收以及可以回收的页面的指导。

http://man7.org/linux/man-pages/man2/posix_fadvise.2.html

应用程序还可以使用O_DIRECT来尝试在执行IO时避免使用页面缓存:

https://lwn.net/Articles/457667/

有迹象表明,Cassandra已使用fadvise尝试优化以减少其页面缓存占用量:

http://grokbase.com/t/cassandra/commits/122qha309v/jira-created-cassandra-3948-sequentialwriter-doesnt-fsync-before-posix-fadvise

三星最近还对内核中的Cassandra和fadvise进行了修补(2017年1月),以更好地利用多流SSD:

http://www.samsung.com/us/labs/pdfs/collat​​eral/Multi-stream_Cassandra_Whitepaper_Final.pdf

Kafka知道页面缓存体系结构,尽管它似乎没有直接使用fadvise。内核提供的旋钮足以在专用主机上调整Kafka:

  • vm.dirty *,用于指导何时将已写入(脏)的页面返回到磁盘
  • vm.vfs_cache_pressure提供有关使用RAM进行页面缓存的积极程度的指南

内核中对特定于设备的写回线程的支持可以追溯到2.6天:

https://www.thomas-krenn.com/zh_CN/wiki/Linux_Page_Cache_Basics

Cgroup v1和v2专注于基于pid的IO限制,而不是基于文件的缓存调整:

https://andrestc.com/post/cgroups-io/

也就是说,旧的linux-ftools实用程序集有一个简单的命令行旋钮示例,用于在特定文件上使用fadvise:

https://github.com/david415/linux-ftools

这样就足够了。给定特定的kafka和cassandra工作负载(例如,大量读取和大量写入),特定优先级(相对于cassandra而言,kafka或相反)和特定IO配置(专用设备与共享设备),可能会出现一种特定的调整模型,归纳为政策模型。