首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >「译文」垂直缩放 Java 容器实践

「译文」垂直缩放 Java 容器实践

作者头像
东风微鸣
发布于 2022-04-21 09:33:43
发布于 2022-04-21 09:33:43
9150
举报

垂直缩放 Java 容器

👉️URL: https://www.openshift.com/blog/scaling-java-containers 📝Description: Scaling Java Containers

随着企业越来越多地了解到部署容器化应用程序的优点,有必要纠正 JVM 在云中表现不好的误解,尤其是在内存管理方面。虽然许多JVM可能不能完美地配置成在弹性云环境中运行,但各种可用的系统属性允许对JVM进行调优,以帮助最大限度地利用其主机环境。如果一个容器化的应用程序是使用OpenShift部署的,那么该应用程序可以利用Kubernetes Vertical Pod Autoscaler (VPA),这是一个alpha特性。VPA就是一个例子,JVM的默认内存管理设置可能会降低在云中运行应用程序的好处。这篇博文将介绍配置和测试一个与VPA一起使用的容器化Java应用程序的步骤,这将演示JVM在云中运行时的适应性。

垂直缩放

垂直缩放是增加或缩小可用于特定应用程序实例的资源的能力,这是在云中运行应用程序的优势之一。随着负载的增加,可以为容器分配更多的内存或CPU资源,并且可以在空闲时将其收缩以减少浪费。根据内存扩展Pod时,自动缩放器将根据Pod的内存使用量是否超过阈值提出建议。在Java应用程序中使用此功能可能会具有挑战性,因为VPA消耗的指标仅反映JVM的已提交总堆内存,而不是应用程序使用的内存量。

如果JVM不将未使用的内存释放回主机,则VPA仅考虑总堆大小的事实可能会成为一个问题。例如,如果应用程序内存使用量大幅增加,堆将扩展以容纳该内存,但此后可能不会收缩,以避免将来分配内存。在专用服务器上这样做会很好,因为它有助于最大程度地提高性能,但是在多租户弹性云环境中,一个容器使用的资源会以另一容器可用的资源为代价。因此,任何未被应用有效利用的内存消耗都可能浪费资源和金钱。

MaxHeapFreeRatio

为了帮助使提交的堆大小更接近于应用程序的内存使用情况,您需要配置几个JVM系统属性,其中之一是MaxHeapFreeRatio。MaxHeapFreeRatio指示在JVM开始缩小堆生成量以达到目标之前,应释放的最大堆比例。

例如,在默认设置下,MaxHeapFreeRatio=70,使用的堆大小为300MB,在需要减小JVM大小之前,总堆可能高达1GB。减小MaxHeapFreeRatio可以迫使JVM更积极地减小堆大小。通过调低该值,进程使用的内存量应更接近反映实际应用程序使用的内存。

Fig 1. MaxHeapFreeRatio=70

△ Fig 2. MaxHeapFreeRatio=40

调整大小测试

从理论上讲,MaxHeapFreeRatio听起来不错,但测试应有助于表明JVM是否会遵循此配置,并在使用高峰后减少堆。对于此测试,除了MaxHeapFreeRatio之外,还有一些其他系统属性使堆可以缩小。Xms不仅是初始堆大小,而且还是最小堆大小,因此可以这样说,将Xms设置为32m应该可以防止Xms充当假地板。其他设置包括GCTimeRatio=4 (该值允许JVM花更多时间(最多20%)执行垃圾收集)和AdaptiveSizePolicyWeight=90这应该告诉JVM在确定新的堆大小时,将当前gc的权重高于以前的gc。有关这些系统属性的更多细节,请查看这篇博文末尾的链接。Xmx最大堆设置为1.5 GB。大堆大小允许具有高吞吐量(或每秒有大量事务)的测试中的JVM拥有足够大的年轻代,以便在垃圾收集器无法足够快地清理时避免对象被提升。在调整大小测试中,MaxHeapFreeRatio被设置为40。

测试是在Wildfly 13服务器应用程序上执行的,该应用程序分配了20个随机对象,平均组合大小为4MB。服务器的负载由Apache JMeter驱动。流量模式由两个峰值组成,两个峰值之间有一个空闲时间。对于高峰时段,每秒添加一个线程,直到总数达到120,然后所有线程又持续一分钟。在空闲期间,两个线程运行了五分钟。在所有情况下,线程都会连续调用服务器。

为了演示MaxHeapFreeRatio,除了垃圾收集日志中的已用堆和已提交堆之外,还必须使用第三个度量。可以从使用的堆中计算出最大可能的堆值。然后查看提交的堆是否落在预期范围内很有趣。对于该测试,结果以视觉方式呈现。最大堆范围由用过的堆延伸的条形图表示,用橙色圆点表示。如果用蓝色圆点表示的已提交堆落在此范围内,则已根据MaxHeapFreeRatio调整了JVM的大小。

这是一个放大视图,以说明已使用的堆大小(橙色点),目标堆范围(橙色错误栏)和实际堆大小:

△ 调整测试结果图大小的详细信息。突出显示的示例的使用堆大小为377 MB,已提交堆大小为459MB。橙色框表示基于MaxHeapFreeRatio=40的最大堆大小为628 MB。

总体趋势表明,已提交的堆的大小将根据使用的堆进行减小:

△ 调整大小的测试结果表明,总堆大小符合MaxFreeHeapRatio并跟踪应用程序的已用堆。

这两个峰值时段和空闲时段都是可见的,这表明堆正在根据应用程序的实际内存使用量进行调整。请注意,提交的堆通常遵循MaxHeapFreeRatio,但并非总是如此。这不是问题-文档承认MaxHeapFreeRatio是目标,而不是严格的限制。此外,一般的行为将允许此系统属性启用自动缩放。如果没有设置这些系统属性,则提交的堆(蓝色标记)在空闲期间不会丢失。尽管JVM内的应用程序使用率有所下降,但JVM基本上会从主机消耗稳定的内存量。

性能测试

既然我们已经知道可以使用MaxHeapFreeRatio来强制堆对应于应用程序的内存使用情况,那么我们需要了解这些设置对应用程序性能的影响。我为内存密集型和CPU密集型应用程序创建了测试。两项测试均在同一Wildfly 13服务器应用程序上进行,测试之间的差异由参数控制。在内存测试中,每个请求平均分配4MB的内存,而CPU密集型测试平均分配200KB的内存,并运行一个微不足道的计算循环,即对数字进行加减运算,平均为100毫秒。在这两个测试中,通过在服务器达到2秒以上的响应时间之前找到最大吞吐量来获得结果。

除使用MaxHeapFreeRatio声明为变量外,这些测试均以与先前测试相同的系统属性运行。我还进行了一个参照组测试,其中Xmx和Xms设置为相等,以防止调整堆大小。

MaxHeapFreeRatio

TPS

已用MB

已提交MB

空闲MB

% 空闲

Free MB/Trans

25

188

283

383

100

26%

.53

30

250

291

390

99

26%

.40

40

295

320

472

152

32%

.52

40 (xmx=xms)

310

331

542

211

39%

.68

70

525

538

1038

500

48%

.95

从每秒事务的线性增加来看,我们可以看到更高的MaxHeapFreeRatio允许更大的吞吐量。但是,由于JVM维护了更多的可用内存以提高效率,因此吞吐量付出了代价。右列演示了每笔事务的可用内存成本。对于我们的示例应用程序,最有效点似乎是MaxHeapFreeRatio为30,因为该配置设法以最少的内存浪费执行最多的事务。

在弹性云环境中考虑这些成本很重要,因为您可以通过水平扩展而不是增加MaxHeapFreeRatio来处理应用程序上的额外负载。当然,这些结果适用于我们的特定测试应用程序,但是希望该实践可以帮助您调整云应用程序。

▽ 图5和图6.吞吐量分别为40和70的MaxHeapFreeRatio。结果表明两者之间没有显着差异,因为这两种设置大约每秒都能完成30个事务。

△ 图5和图6

MaxHeapFreeRatio分别为40和70的吞吐量。结果表明两者之间没有显着差异,因为这两种设置大约每秒都能完成30个事务。

总结

对于具有一定程度波动负载的任何应用程序,扩展应用程序以满足需求是一个相当大的问题。自动缩放是使用容器解决方案(例如Red Hat OpenShift)部署应用程序的主要好处。随着越来越多的企业看到以这种方式部署应用程序的好处,了解Java应用程序将能够充分利用诸如Kubernetes Vertical Pod Autoscaler之类的功能非常重要。每个Java版本似乎都有针对云量身定制的新功能,但是没有必要升级或等待新版本开始配置JVM并获得Red Hat OpenShift的好处。

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2021-02-05,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 东风微鸣技术博客 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
JVM 优化经验总结
Java 虚拟机有自己完善的硬件架构, 如处理器、堆栈、寄存器等,还具有相应的指令系统。JVM 屏蔽了与具体操作系统平台相关的信息,使得 Java 程序只需生成在 Java 虚拟机上运行的目标代码 (字节码), 就可以在多种平台上不加修改地运行。Java 虚拟机在执行字节码时,实际上最终还是把字节码解释成具体平台上的机器指令执行。
哲洛不闹
2018/09/18
5370
JVM 优化经验总结
JVM 优化思路
Full GC 的成本远高于 Mirror GC 因此某些情况下,尽量让对象进入新生代,虽然大部分情况下,JVM 会尝试在 Eden 区分配对象,但是由于空间紧张,新生代的数据会提前进入老年代。因此最大限度的避免新对象直接进入老年代。
王小明_HIT
2020/04/07
1.2K0
高效应用程序必须配置的7个JVM参数​
围绕垃圾收集和内存,您可以将 600 多个参数传递给 JVM。如果包括其他方面 JVM 参数计数将轻松超过 1000+。争论点太多,任何人都无法消化和理解。在本文中,我们将重点介绍七个重要的 JVM 参数,您可能会发现它们很有用。
用户5166556
2023/03/18
6540
高效应用程序必须配置的7个JVM参数​
Java 14 Hotspot 虚拟机垃圾回收调优指南!
出处:www.cnblogs.com/sxpujs/p/12638114.html
Java技术栈
2020/06/16
6480
Java  14 Hotspot 虚拟机垃圾回收调优指南!
jvm 参数设置与分析
之前的文章中介绍了 jvm 内存管理和垃圾收集的相关内容,结合这些理论知识,通过合理设置参数才能将系统的性能得以提升。
用户3147702
2022/06/27
1.1K0
基于容器的Java内存参数解析
在基于物理的服务器(此处主要与容器平台进行区分,故此描述)上运行Java应用程序时,我们通常会使用Java虚拟机参数"-Xms、-Xmx"来指定Java堆内存的初始值和最大值。如果要将我们的应用程序移植到容器平台,如何在容器环境中配置Java堆内存大小呢?有没有最佳做法?在本文中,我们将讨论可用于指定Java堆内存大小的JVM参数以及最优选择。
Luga Lee
2021/12/09
1.9K0
基于容器的Java内存参数解析
java(10)-JVM性能监控和优化
GC监控是为了鉴别JVM是否在高效地执行GC,以及是否有必要进行额外的性能调优。基于以上信息,我们可以修改应用程序或者调整GC算法(GC优化)。
黄规速
2022/04/14
1.4K0
java(10)-JVM性能监控和优化
了解Java垃圾收集
Java 的垃圾收集机制在 Java 应用程序开发中至关重要。此机制对于通过消除不再使用的对象来释放内存空间得过程来说至关重要。在这篇文章中,我带大家深入了解下 Java 垃圾收集的机制,并探索其工作原理、优点以及实现最佳性能的最佳实践。
wayn
2024/06/03
1750
了解Java垃圾收集
垃圾回收调整简介-Java快速进阶教程
从桌面上的小程序到大型服务器上的 Web 服务,各种各样的应用程序都使用 Java 平台标准版 (Java SE)。为了支持这种多样化的部署,Java HotSpot VM 提供了多个垃圾回收器,每个垃圾回收器都旨在满足不同的需求。Java SE 根据运行应用程序的计算机的类选择最合适的垃圾回收器。但是,这种选择可能并非适合每个应用。具有严格性能目标或其他要求的用户、开发人员和管理员可能需要显式选择垃圾回收器并调整某些参数以实现所需的性能级别。本文档提供的信息可帮助完成这些任务。
jack.yang
2025/04/05
770
垃圾回收调整简介-Java快速进阶教程
jvm优化实战(一篇文章看懂)
1 运行的项目卡住了,项目里面的日志没有输出,程序没有反应 2 服务器的cpu 负载突然升高; 3 只有在上线的情况,才会有多线程的情况,本地即使压测,也没有什么用处,所以多线程,一定要上线的情况进行压测;
一写代码就开心
2022/05/27
4530
jvm优化实战(一篇文章看懂)
服务优化指南
作者:Zane Blog 来自:http://luojinping.com/2017/08/13/服务调优/ 1. 服务异常的处理流程 2. 负载 2.1 查看机器 cpu 的负载 top -b -n
架构师小秘圈
2018/06/04
8160
服务器又报错了?教你如何优雅排查!
可以从以下几个方面监控CPU的信息: (1)中断; (2)上下文切换; (3)可运行队列; (4)CPU 利用率。
Bug开发工程师
2019/06/17
1.3K0
服务器又报错了?教你如何优雅排查!
6个重要的JVM性能参数
-Xmx可能是最重要的JVM参数。-Xmx定义要分配给应用程序的最大堆大小。。您可以这样定义应用程序的堆大小:-Xmx2g。
FunTester
2020/04/02
1.2K0
Java -jar参数详解:掌握Java可执行JAR文件的运行技巧
作为一种常用的开发语言,Java经常使用可执行的JAR(Java Archive)文件来打包和分发应用程序。使用java -jar命令运行JAR文件是一种方便快捷的方式。本文将详细介绍java -jar命令的各种参数,帮助您充分利用这个功能。
修己xj
2023/08/25
4.9K0
Java -jar参数详解:掌握Java可执行JAR文件的运行技巧
JVM系列三:JVM参数设置、分析
不管是YGC还是Full GC,GC过程中都会对导致程序运行中中断,正确的选择不同的GC策略,调整JVM、GC的参数,可以极大的减少由于GC工作,而导致的程序运行中断方面的问题,进而适当的提高Java程序的工作效率。但是调整GC是以个极为复杂的过程,由于各个程序具备不同的特点,如:web和GUI程序就有很大区别(Web可以适当的停顿,但GUI停顿是客户无法接受的),而且由于跑在各个机器上的配置不同(主要cup个数,内存不同),所以使用的GC种类也会不同(如何选择见GC种类及如何选择)。本文将注重介
lyb-geek
2018/03/27
1.8K0
linux下的java部署
注:在运行 JAR 包之前,确保你的 JAR 文件是可执行的,并且包含了正确的类和依赖项。如果 JAR 包依赖于其他库或配置文件,确保它们也在正确的位置可用。
Kiba518
2024/03/06
3400
linux下的java部署
JVM中优化指南
Java虚拟机有自己完善的硬件架构,如处理器、堆栈、寄存器等,还具有相应的指令系统。JVM屏蔽了与具体操作系统平台相关的信息,使得Java程序只需生成在Java虚拟机上运行的目标代表(字节码),就可以在多种平台上不加修改地运行。Java虚拟机在执行字节码时,实际上最终还是把字节码解释成具体平台上的机器指令执行。 我们以一个例子开始这篇文章。假设你是一个普通的Java对象,你出生在Eden区,在Eden区有许多和你差不多的小兄弟、小姐妹,可以把Eden区当成幼儿园,在这个幼儿园里大家玩了多长时间。Eden区不能无休止地放你们在里面,所以当年纪稍大,你就要被送到学校去上学,这里假设从小学到高中都称为Survivor区。开始的时候你在Survivor区里面划分出来的"From"区,读到高年级了,就进了Survivor区的“To”区,中间由于学习成绩不稳定,还经常来回折腾。直到你18岁的时候,高中毕业了,该去社会上闯闯了。于是你就去了年老代,年老代里面人也很多。在年老代里,你生活了20年(每次GC加一岁),最后寿终正寝,被GC回收。有一点没有提,你在年老代遇到了一个同学,他的名字叫爱德华(暮光之城里的帅哥吸血鬼),他以及他的家族永远不会死,那么他们就生活在永生代。 我认为优化JVM一定要抓住两点,第一点 :怎样缩短单次GC的时间;第二点 :怎样缩短GC频率。
海仔
2019/08/06
4550
JVM的Xms和Xmx参数设置为相同值有什么好处?
最近正在重新学习JVM的内存结构及相关优化内容,无意中看到IDEA的VM配置(安装时默认配置)中有如下的配置:
程序新视界
2020/09/10
21.5K5
【Java虚拟机】JVM调优和分析案例综合实战
jvm性能优化涉及到两个很重要的概念:吞吐量和响应时间。jvm调优主要是针对他们进行调整优化,达到一个理想的目标,根据业务确定目标是吞吐量优先还是响应时间优先。
互联网小阿祥
2023/05/28
5360
【Java虚拟机】JVM调优和分析案例综合实战
进阶2:JVM 启动参数
JVM(Java虚拟机)的启动参数是在启动JVM时可以设置的一些命令行参数。这些参数用于指定JVM的运行环境、内存分配、垃圾回收器以及其他选项。以下是一些常见的JVM启动参数:
你可以叫我老白
2023/06/28
7990
进阶2:JVM 启动参数
相关推荐
JVM 优化经验总结
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档