这里是weihubeats,觉得文章不错可以关注公众号小奏技术,文章首发。拒绝营销号,拒绝标题党

背景

线上的RocketMQ集群有运行一段时间了。比如测试环境和线上环境的RocketMQ集群部署的机器内存大小肯定不一样。所以可能要写多个部署脚本。非常麻烦
官方的部署脚本是不支持根据宿主机内存大小动态设置JVM启动参数的

可以看到是写死的,给4g。
但是比如我线上的机器内存大小为8g,实际我要给的内存可能是6g。我又需要手动改脚本非常麻烦。所以想要修改基于宿主机内存大小自动调节JVM内存大小

基于jvm自带参数

实际上jdk在11就支持动态参数了,比如上面的脚本我们可以改成如下方式

choose_gc_options()
{# Example of JAVA_MAJOR_VERSION value : '1', '9', '10', '11', ...# '1' means releases befor Java 9JAVA_MAJOR_VERSION=$("$JAVA" -version 2>&1 | sed -r -n 's/.* version "([0-9]*).*$/\1/p')if [ -z "$JAVA_MAJOR_VERSION" ] || [ "$JAVA_MAJOR_VERSION" -lt "9" ] ; thenJAVA_OPT="${JAVA_OPT} -server -XX:MaxRAMPercentage=70 -XX:MinRAMPercentage=70 -XX:MetaspaceSize=128m -XX:MaxMetaspaceSize=320m"JAVA_OPT="${JAVA_OPT} -XX:+UseG1GC -XX:G1HeapRegionSize=16m -XX:G1ReservePercent=25 -XX:InitiatingHeapOccupancyPercent=30 -XX:SoftRefLRUPolicyMSPerMB=0"JAVA_OPT="${JAVA_OPT} -Xlog:gc*:file=${GC_LOG_DIR}/rmq_srv_gc_%p_%t.log:time,tags:filecount=5,filesize=30M"elseJAVA_OPT="${JAVA_OPT} -server -Xms8g -Xmx8g -XX:MetaspaceSize=128m -XX:MaxMetaspaceSize=320m"JAVA_OPT="${JAVA_OPT} -XX:+UseG1GC -XX:G1HeapRegionSize=16m -XX:G1ReservePercent=25 -XX:InitiatingHeapOccupancyPercent=30 -XX:SoftRefLRUPolicyMSPerMB=0"JAVA_OPT="${JAVA_OPT} -Xlog:gc*:file=${GC_LOG_DIR}/rmq_srv_gc_%p_%t.log:time,tags:filecount=5,filesize=30M"fi
}
  1. -XX:MaxRAMPercentage 用于设置JVM可使用的最大RAM百分比。举例来说,你可以使用 -XX:MaxRAMPercentage=75 指定JVM最多可用服务器内存的75%。

但是实际启动会报错,当前的服务器jdk版本不支持
我的jdk版本为1.8.0_362
实际我们是可以改动RocketMQ源码去支持jdk11的部署,但是这种方式比较耗费精力。所以我这里决定使用sh脚本来实现

sh脚本实现

核心脚本代码主要是这几行

# 获取宿主机内存总量(单位:M)
total_mem=$(grep MemTotal /proc/meminfo | awk '{print int($2/1024)}')# 将内存总量转为单位:G 向上取整
mem_in_g=$((total_mem + 1023 / 1024))# 判断内存大小,按需设定内存分配比例
if [ $mem_in_g -lt 16 ]; thenmem_ratio=90
elif [ $mem_in_g -ge 16 -a $mem_in_g -lt 32 ]; thenmem_ratio=95
elif [ $mem_in_g -ge 32 ]; thenmem_ratio=95
fiheap_size=$(($total_mem * $mem_ratio /100 / 1024))
metaspace_size=$(echo "$total_mem * 0.02" | bc | awk '{print int($1+0.5)}' | sed -e 's/^0\{1,\}//')
max_metaspace_size=$(echo "$total_mem * 0.04" | bc | awk '{print int($1+0.5)}' | sed -e 's/^0\{1,\}//')choose_gc_options()
{# Example of JAVA_MAJOR_VERSION value : '1', '9', '10', '11', ...# '1' means releases befor Java 9JAVA_MAJOR_VERSION=$("$JAVA" -version 2>&1 | sed -r -n 's/.* version "([0-9]*).*$/\1/p')if [ -z "$JAVA_MAJOR_VERSION" ] || [ "$JAVA_MAJOR_VERSION" -lt "9" ] ; thenJAVA_OPT="${JAVA_OPT} -server -Xms${heap_size}g -Xmx${heap_size}g -XX:MetaspaceSize=${metaspace_size}m -XX:MaxMetaspaceSize=${max_metaspace_size}m"JAVA_OPT="${JAVA_OPT} -XX:+UseG1GC -XX:G1HeapRegionSize=16m -XX:G1ReservePercent=25 -XX:InitiatingHeapOccupancyPercent=30 -XX:SoftRefLRUPolicyMSPerMB=0"JAVA_OPT="${JAVA_OPT} -verbose:gc -Xloggc:${GC_LOG_DIR}/rmq_srv_gc_%p_%t.log -XX:+PrintGCDetails -XX:+PrintGCDateStamps"JAVA_OPT="${JAVA_OPT} -XX:+UseGCLogFileRotation -XX:NumberOfGCLogFiles=5 -XX:GCLogFileSize=30m"elseJAVA_OPT="${JAVA_OPT} -server -Xms8g -Xmx8g -XX:MetaspaceSize=128m -XX:MaxMetaspaceSize=320m"JAVA_OPT="${JAVA_OPT} -XX:+UseG1GC -XX:G1HeapRegionSize=16m -XX:G1ReservePercent=25 -XX:InitiatingHeapOccupancyPercent=30 -XX:SoftRefLRUPolicyMSPerMB=0"JAVA_OPT="${JAVA_OPT} -Xlog:gc*:file=${GC_LOG_DIR}/rmq_srv_gc_%p_%t.log:time,tags:filecount=5,filesize=30M"fi
}

上面的脚本都有注释。我们大致还是解释下

  1. 获取宿主机的内存大小(非可用内存,我们要保证宿主机分配不到预定内存就启动报错)
  2. 小于16g内存给总内存的90%
  3. 大于等于16g小于32g内存我们给总内存的95%
  4. 大于等于32g的我们也给95%内存(实际这里可以和判断3一起,但是为了以后可能调整分配的内存大小就暂时分开)
  5. 元空间大小我们给总内存的0.02
  6. 最大元空间大小我们给总内存的0。04
  7. 注意获取到的总内存要向上取整,因为8g的机器我们实际获取到的内存大小大概为7296M,我们加一个1023(一个无线趋近于1的数就可以向上取整了)

最后给一个完整的runserver.sh

  • runserver.sh
#!/bin/sh# Licensed to the Apache Software Foundation (ASF) under one or more
# contributor license agreements.  See the NOTICE file distributed with
# this work for additional information regarding copyright ownership.
# The ASF licenses this file to You under the Apache License, Version 2.0
# (the "License"); you may not use this file except in compliance with
# the License.  You may obtain a copy of the License at
#
#     http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.#===========================================================================================
# Java Environment Setting
#===========================================================================================
error_exit ()
{echo "ERROR: $1 !!"exit 1
}find_java_home()
{case "`uname`" inDarwin)JAVA_HOME=$(/usr/libexec/java_home);;*)JAVA_HOME=$(dirname $(dirname $(readlink -f $(which javac))));;esac
}find_java_home[ ! -e "$JAVA_HOME/bin/java" ] && JAVA_HOME=$HOME/jdk/java
[ ! -e "$JAVA_HOME/bin/java" ] && JAVA_HOME=/usr/java
[ ! -e "$JAVA_HOME/bin/java" ] && error_exit "Please set the JAVA_HOME variable in your environment, We need java(x64)!"export JAVA_HOME
export JAVA="$JAVA_HOME/bin/java"
export BASE_DIR=$(dirname $0)/..
export CLASSPATH=.:${BASE_DIR}/conf:${BASE_DIR}/lib/*:${CLASSPATH}#===========================================================================================
# JVM Configuration
#===========================================================================================
# The RAMDisk initializing size in MB on Darwin OS for gc-log
DIR_SIZE_IN_MB=600# 获取宿主机内存总量(单位:M)
total_mem=$(grep MemTotal /proc/meminfo | awk '{print int($2/1024)}')# 将内存总量转为单位:G 向上取整
mem_in_g=$((total_mem + 1023 / 1024))# 判断内存大小,按需设定内存分配比例
if [ $mem_in_g -lt 16 ]; thenmem_ratio=90
elif [ $mem_in_g -ge 16 -a $mem_in_g -lt 32 ]; thenmem_ratio=95
elif [ $mem_in_g -ge 32 ]; thenmem_ratio=95
fiheap_size=$(($total_mem * $mem_ratio /100 / 1024))
metaspace_size=$(echo "$total_mem * 0.02" | bc | awk '{print int($1+0.5)}' | sed -e 's/^0\{1,\}//')
max_metaspace_size=$(echo "$total_mem * 0.04" | bc | awk '{print int($1+0.5)}' | sed -e 's/^0\{1,\}//')choose_gc_log_directory()
{case "`uname`" inDarwin)if [ ! -d "/Volumes/RAMDisk" ]; then# create ram disk on Darwin systems as gc-log directoryDEV=`hdiutil attach -nomount ram://$((2 * 1024 * DIR_SIZE_IN_MB))` > /dev/nulldiskutil eraseVolume HFS+ RAMDisk ${DEV} > /dev/nullecho "Create RAMDisk /Volumes/RAMDisk for gc logging on Darwin OS."fiGC_LOG_DIR="/Volumes/RAMDisk";;*)# check if /dev/shm exists on other systemsif [ -d "/dev/shm" ]; thenGC_LOG_DIR="/dev/shm"elseGC_LOG_DIR=${BASE_DIR}fi;;esac
}choose_gc_options()
{# Example of JAVA_MAJOR_VERSION value : '1', '9', '10', '11', ...# '1' means releases befor Java 9JAVA_MAJOR_VERSION=$("$JAVA" -version 2>&1 | sed -r -n 's/.* version "([0-9]*).*$/\1/p')if [ -z "$JAVA_MAJOR_VERSION" ] || [ "$JAVA_MAJOR_VERSION" -lt "9" ] ; thenJAVA_OPT="${JAVA_OPT} -server -Xms${heap_size}g -Xmx${heap_size}g -XX:MetaspaceSize=${metaspace_size}m -XX:MaxMetaspaceSize=${max_metaspace_size}m"JAVA_OPT="${JAVA_OPT} -XX:+UseG1GC -XX:G1HeapRegionSize=16m -XX:G1ReservePercent=25 -XX:InitiatingHeapOccupancyPercent=30 -XX:SoftRefLRUPolicyMSPerMB=0"JAVA_OPT="${JAVA_OPT} -verbose:gc -Xloggc:${GC_LOG_DIR}/rmq_srv_gc_%p_%t.log -XX:+PrintGCDetails -XX:+PrintGCDateStamps"JAVA_OPT="${JAVA_OPT} -XX:+UseGCLogFileRotation -XX:NumberOfGCLogFiles=5 -XX:GCLogFileSize=30m"elseJAVA_OPT="${JAVA_OPT} -server -Xms8g -Xmx8g -XX:MetaspaceSize=128m -XX:MaxMetaspaceSize=320m"JAVA_OPT="${JAVA_OPT} -XX:+UseG1GC -XX:G1HeapRegionSize=16m -XX:G1ReservePercent=25 -XX:InitiatingHeapOccupancyPercent=30 -XX:SoftRefLRUPolicyMSPerMB=0"JAVA_OPT="${JAVA_OPT} -Xlog:gc*:file=${GC_LOG_DIR}/rmq_srv_gc_%p_%t.log:time,tags:filecount=5,filesize=30M"fi
}choose_gc_log_directory
choose_gc_options
JAVA_OPT="${JAVA_OPT} -XX:-OmitStackTraceInFastThrow"
JAVA_OPT="${JAVA_OPT} -XX:-UseLargePages"
#JAVA_OPT="${JAVA_OPT} -Xdebug -Xrunjdwp:transport=dt_socket,address=9555,server=y,suspend=n"
JAVA_OPT="${JAVA_OPT} ${JAVA_OPT_EXT}"
JAVA_OPT="${JAVA_OPT} -cp ${CLASSPATH}"$JAVA ${JAVA_OPT} $@

RocketMQ部署之动态设置JVM启动参数相关推荐

  1. 使用-XX:+PrintCommandLineFlags展示JVM启动参数

    导语: 近期在学习周志明老师的<<深入理解Java虚拟机: JVM高级特性与最佳实践(第3版)>>, 在IDEA中测试老师的示例代码时, 发现程序的输出和老师的输出不一样, 想 ...

  2. JVM 启动参数详解:博观而约取、厚积而薄发

    JVM 作为一个通用的虚拟机,我们可以通过启动 Java 命令时指定不同的 JVM 参数,让 JVM 调整自己的运行状态和行为,内存管理和垃圾回收的 GC 算法,添加和处理调试和诊断信息等等.本节概括 ...

  3. JVM 启动参数详解

    JVM 启动参数详解 JVM 作为一个通用的虚拟机,我们可以通过启动Java命令时指定不同JVM参数,让 JVM调整自己的运行状态和行为,内存管理和垃圾回收的GC算法等等. 直接通过命令行启动 Jav ...

  4. 全网最硬核 JVM TLAB 分析 3. JVM EMA期望算法与TLAB相关JVM启动参数

    今天,又是干货满满的一天.这是全网最硬核 JVM 系列的开篇,首先从 TLAB 开始.由于文章很长,每个人阅读习惯不同,所以特此拆成单篇版和多篇版 全网最硬核 JVM TLAB 分析(单篇版不包含额外 ...

  5. JVM启动参数解析(转)

    JVM启动参数解析(转) (2010-03-17 19:45:19) 转载 标签: jvm 启动参数 it 分类:他山之石攻己之玉 dk1.4.2 JVM官方地址:http://java.sun.co ...

  6. 【Java 虚拟机原理】垃圾回收算法 ( 设置 JVM 命令参数输出 GC 日志 | GC 日志输出示例 | GC 日志分析 )

    文章目录 一.设置 JVM 命令参数输出 GC 日志 二.GC 日志示例 三.GC 日志分析 一.设置 JVM 命令参数输出 GC 日志 在 IntelliJ IDEA 的启动参数中设置 -XX:+P ...

  7. 不需要再手工指定JVM启动参数-XX:+UseCompressedOops

    技术团队通过 GCeasy 工具分析完几千次用户上传的GC日志后, 发现一个现象: 仍然有很多Java程序传入了JVM启动参数 -XX:+UseCompressedOops. 实际上,如果JVM的版本 ...

  8. JVM启动参数详解(含调优)

    java启动参数共分为三类: 其一是标准参数(-),所有的JVM实现都必须实现这些参数的功能,而且向后兼容: 其二是非标准参数(-X),默认jvm实现这些参数的功能,但是并不保证所有jvm实现都满足, ...

  9. JVM启动参数配置详解

    JVM启动参数配置详解 1. JDK8的JVM启动参数默认配置 2. JDK8的JVM启动参数说明 2.1 基本参数 2.2 G1相关参数 2.3 辅助信息 1. JDK8的JVM启动参数默认配置 - ...

最新文章

  1. ORACLE告警日志文件
  2. Linux编程之定制带级别的log
  3. Central Authentication Service
  4. 【QGIS入门实战精品教程】3.1:QGIS如何连接SQL Server数据库?
  5. 英特尔FPGA技术大会: 加快塑造边缘、网络和云端的未来
  6. 浙江大学计算机科学与技术博士培养研究方向,浙江大学计算机科学技术学院博士研究生导师简介:王跃明...
  7. PHPnow中ZendDebugger与ZendOptimizer 共存
  8. Keil 5安装教程
  9. ADB常用命令--测试人员必备
  10. 云计算十字真言及其在小博无线的实践
  11. 如何查看我的订单-REST的流程API设计案例
  12. 计算机英语词汇合成词有哪些,2018年12月英语四级词汇讲解丨考点归纳:合成词...
  13. C++ SuperLU 混合编程
  14. 城市生活污水处理技术现状及活性炭的应用
  15. 使用DISM启用或禁用Windows功能
  16. PCB中solder层和paste层的区别
  17. 苹果11怎样设置自动锁屏 iPhone11自动锁屏操作方法
  18. 使用lucene的多字段排序--回复网友BUFFON
  19. JavaScript限时秒杀
  20. 12种高效的管理方法

热门文章

  1. 半年翻倍!内存条掀起涨价潮
  2. C3PO链接池配置(附带jar)
  3. EPLAN一敲键盘就卡死
  4. Ubuntu虚拟机共享文件夹无法显示解决方法
  5. 2008年初盘点:2007年IT行业五大热门职位
  6. 成都的“大众点评+街旁”
  7. zte怎么开虚拟服务器,zte路由器设置虚拟服务器
  8. Google Project Fi:抛弃手机卡,打通WiFi与蜂窝网络
  9. 使用O2OA二次开发搭建企业办公平台(十二)流程开发篇:报销审批流程需求和应用创建
  10. 袋鼠云正式入驻中国信创服务社区,直播首秀等你来看!