我的任务定义配置有以下限制:
"cpu": "1024",
"memory": "8192"
我正在使用“ docker” cgroup标志在docker容器中运行jar:
java -XX:+UseContainerSupport -XX:MaxRAMPercentage=80 -XX:InitialRAMPercentage=70 /myjar.jar foo.Main
但是ECS会因为OOM错误而终止我的服务。
我已经进行了测量,并使用以下方法测量了JVM内存使用率,并在我的应用程序中报告了它作为调试措施:
val bean: MemoryMXBean = ManagementFactory.getMemoryMXBean
val hmu: MemoryUsage = bean.getHeapMemoryUsage
val nhu = bean.getNonHeapMemoryUsage
... reporting these metrics ...
在图像中,顶部是云手表报告的已用内存。如您所见,它是100%。
下图显示了应用程序报告的内存:
val pc = (1.0 * hmu.getUsed) / hmu.getCommitted
从文档中:
* Below is a picture showing an example of a memory pool:
*
* <pre>
* +----------------------------------------------+
* +//////////////// | +
* +//////////////// | +
* +----------------------------------------------+
*
* |--------|
* init
* |---------------|
* used
* |---------------------------|
* committed
* |----------------------------------------------|
* max
/**
* Returns the amount of memory in bytes that is committed for
* the Java virtual machine to use. This amount of memory is
* guaranteed for the Java virtual machine to use.
*
* @return the amount of committed memory in bytes.
*
*/
public long getCommitted() {
return committed;
};
/**
* Returns the amount of used memory in bytes.
*
* @return the amount of used memory in bytes.
*
*/
public long getUsed() {
return used;
};
我的Docker文件非常简单:
FROM openjdk:10-jdk
COPY service.jar /affinity-service.jar
COPY start.sh /start.sh
RUN chmod +x /start.sh
CMD ["/start.sh"]
和start.sh
是:
#!/bin/bash
set -x
OPTS=""
#... setting flags from ENV values...
#...
#...
java -XX:+UseContainerSupport -XX:MaxRAMPercentage=80 -XX:InitialRAMPercentage=70 ${OPTS} -jar /service.jar com.....Service
答案 0 :(得分:1)
MaxRAMPercentage
和InitialRAMPercentage
标志不会限制Java进程的内存。
这些标志唯一影响的是堆大小-有关详细信息,请参见this answer。
正如我所解释的here,Java进程可以使用比堆大小大得多的内存。
坏消息是-仅通过JVM标志来设置硬盘内存限制是不可能的,以确保JVM不会被操作系统杀死。但是same answer可能会给出一个想法,如何分析Java进程的内存占用量。