一、优化方向:
有五个方向:flink、elasticsearch、kafka、主机、数据过滤和代码;
完整优化方案可以查看:大数据—— Flink 的优化_Vicky_Tang的博客-CSDN博客_flink优化。
以下是我们实际在用的优化方法归纳。
Job:
这一方向一般由管理侧(如paas)进行优化,例如:
(1)把JobManager的jvm上限从1G提升到3G。在22年9月中旬的优化中,对运行稳定性效果的提升明显,峰值jvm占用比从98.6%降低到45%,压测不再出现job因内存问题卡掉的情况;
(2)采用hdfs进行数据存储。生产环境已经采用,对照组是测试环境的独立集群,负载能力和容错能力远远超过测试环境的集群,且可能动态调整性能使用,例如slot的使用量;
(3)对log4j的日志做滚动处理。目的是缩减flink日志对大小,减少日志对磁盘的影响,便于日志的查询和检出。百度有较多的例子,目前应用在测试环境独立集群,在生产环境则由yarn进行管理和优化;
(4)增加多个集群,分离不同jar的job。分离jar到不同集群中,一个jar对应一个集群,一个集群对应一组job。这是一种冗余模式,避免一个job异常导致其他job挂起。同时,由于软件和系统机制的制约,一套flink集群并不能真正分配到足量的cpu和内存资源,多一套集群也可以进一步使用剩余系统资源。目前apm-job和小并发度日志中心job在一套1Gjvm集群,两个大并发度写入es的日志中心job在另一套3Gjvm集群。
Task:
这一方向一般由应用侧(如csd)进行优化,例如:
包含了elasticsearch.yml、jvm.options和索引属性。
Elasticsearch.yml
优化空间较小,一般就是要集群,多配置几台主机几个节点,增强负载能力和容量。
Jvm.options
主要优化的阵地,包含的优化配置内容,按照优先级排序如下:最大和最小使用内存、垃圾回收器和垃圾回收器日志。
-Xms40g
-Xmx40g
-XX:+UseG1GC
# full gc效率更高
-XX:+ExplicitGCInvokesConcurrent
-XX:+UseGCOverheadLimit
# 启动并发GC周期时的堆内存占用百分比.
-XX:InitiatingHeapOccupancyPercent=40
# 指定STW工作线程的数量
-XX:ParallelGCThreads=20
# 标记线程的数量
-XX:ConcGCThreads=8
# G1为分配担保预留的空间比例 默认10%
-XX:G1ReservePercent=15
# 表示每次GC最大的停顿毫秒数,默认200,减少该值会增加系统load。
-XX:MaxGCPauseMillis=100
## JDK 8 GC logging
8:-XX:+PrintGCDetails
8:-XX:+PrintGCDateStamps
8:-XX:+PrintTenuringDistribution
8:-XX:+PrintGCApplicationStoppedTime
8:-Xloggc:logs/gc.log
8:-XX:+UseGCLogFileRotation
8:-XX:NumberOfGCLogFiles=32
8:-XX:GCLogFileSize=64m
(4)配置内存熔断机制:现场对内存熔断的限制是98%,但效果不明显,暂不推荐。
索引属性
log.retention.hours=96
log.segment.bytes=1073741824
queued.max.requests=20000
message.max.bytes=20971520
replica.fetch.max.bytes=20971520
socket.send.buffer.bytes=10485760
socket.receive.buffer.bytes=10485760
socket.request.max.bytes=104857600
num.network.threads=49
中间件flink、redis、kafka和mysql均在同一套三台主机上,CPU总数100C,256G内存,2T的磁盘。
ElasticSearch在24-26的一天三台主机上,64G内存,30T的磁盘。
优化方向应当是给flink、redis和kafka分离出至少三台同配置主机,并保证100C能够只服务于中间件。
Log4j配置文件:
业务侧将日志级别限制为error,仅查看error日志则日志数量会较少,压力大大减轻。
日志格式配置:
日志格式配置中,包含过滤方法,要业务侧给出过滤规则,屏蔽一些不需要的日志,减少日志的同时,提升日志可用性和命中率。
配置文件:
flink的job启动语句中加入:-isDayStore true
topic.splitcount = {"logfmt-019":2,"logbad":3}
代码内部: