多个应用程序节点如何在 kubernetes 中公开 jmx?
multiple app nodes how to expose jmx in kubernetes?
- 在
kubernetes
中,我可以使用 service
公开服务。这很好。
- 假设我有 1 个 Web 实例和 10 个 java 服务器实例。
- 我有一个 windows 网关,我习惯于通过安装在上面的 jconsole 访问那 10 个 java 服务器实例。
- 显然我不会通过 kubernetes 服务公开所有应用程序 jmx 端口。
我在这里有哪些选择?我应该如何允许这个外部到 kubernetes 集群 windows 网关访问那 10 个服务器 jmx 端口?这里有什么做法吗?
我认为一种方法是使用唯一字符串 \ id 添加标签到您的 pod,例如 pod_name 并使用 expose 命令创建一个带有此唯一选择器的新服务 id\string.
kubectl label pods <podname> podname=<podname>
kubectl expose pod <podname> --port=9010 --name=<podname>_jmx
我们是按照下面的方式做的
- 为每个广告连播添加唯一标签。例如:podid=asdw23443
- 创建一个选择器为 podid=asdw23443 的新服务。确保在服务中通过 nodeport 或 loadbalancer 在 pod 上公开 jmx 端口。
如果您在服务中选择节点端口,因为您正在执行 NAT 操作,您可能必须为需要通过 jconsole 连接的每个 jvm 提供以下 JVM 参数
-Djava.rmi.server.hostname=<your-ip-address>
另一种选择是使用 kubectl port-forward 将 JMX 端口从 K8 pod 转发到您的本地 PC。
我是这样做的:
1).将以下 JVM 选项添加到您的应用程序:
-Dcom.sun.management.jmxremote
-Dcom.sun.management.jmxremote.authenticate=false
-Dcom.sun.management.jmxremote.ssl=false
-Dcom.sun.management.jmxremote.local.only=false
-Dcom.sun.management.jmxremote.port=1099
-Dcom.sun.management.jmxremote.rmi.port=1099
-Djava.rmi.server.hostname=127.0.0.1
这里的关键部分是:
应使用与 'jmxremote.port' 和 'jmxremote.rmi.port' 相同的端口。这只需要转发一个端口。
127.0.0.1 应作为 rmi 服务器主机名传递。这是 JMX 连接通过端口转发工作所必需的。
2).通过 kubectl 将 JMX 端口 (1099) 转发到本地 PC:
kubectl port-forward <your-app-pod> 1099
3).打开与本地端口 1099 的 jconsole 连接:
jconsole 127.0.0.1:1099
这种方式可以通过 JMX 调试任何 Java pod,而不必通过 K8 服务公开公开 JMX(从安全角度来看更好)。
另一个可能有用的选项是将 Jolokia (https://jolokia.org/) 代理附加到容器内的 Java 进程,以便它通过 HTTP 端口代理 JMX 并公开或转发端口此 HTTP 端口用于通过 HTTP 查询 JMX。
添加到 ,我想同时监控同一个 pod 的所有实例,因为我们将端口硬编码为 1099,这很困难,因为我只能用那个端口转发到一个 pod端口。
我使用 Shell 脚本在 运行 docker
时动态分配 pod
Docker文件
CMD /run.sh
run.sh
JMX_PORT=$(((RANDOM % 20)+1099))
echo "Running JMX on Port $JMX_PORT"
java ``eval echo $JAVA_OPTS`` ...
deployment.yml
env:
- name: JAVA_OPTS
value: "-Xms256m -Xmx6144m -Dcom.sun.management.jmxremote -Dcom.sun.management.jmxremote.authenticate=false -Dcom.sun.management.jmxremote.ssl=false -Dcom.sun.management.jmxremote.local.only=false -Dcom.sun.management.jmxremote.port=$JMX_PORT -Dcom.sun.management.jmxremote.rmi.port=$JMX_PORT -Djava.rmi.server.hostname=127.0.0.1"
eval 会将 JMX_PORT 评估为 bash 值,每个 pod 启动时可能会得到不同的 pod。我
- 在
kubernetes
中,我可以使用service
公开服务。这很好。 - 假设我有 1 个 Web 实例和 10 个 java 服务器实例。
- 我有一个 windows 网关,我习惯于通过安装在上面的 jconsole 访问那 10 个 java 服务器实例。
- 显然我不会通过 kubernetes 服务公开所有应用程序 jmx 端口。
我在这里有哪些选择?我应该如何允许这个外部到 kubernetes 集群 windows 网关访问那 10 个服务器 jmx 端口?这里有什么做法吗?
我认为一种方法是使用唯一字符串 \ id 添加标签到您的 pod,例如 pod_name 并使用 expose 命令创建一个带有此唯一选择器的新服务 id\string.
kubectl label pods <podname> podname=<podname>
kubectl expose pod <podname> --port=9010 --name=<podname>_jmx
我们是按照下面的方式做的
- 为每个广告连播添加唯一标签。例如:podid=asdw23443
- 创建一个选择器为 podid=asdw23443 的新服务。确保在服务中通过 nodeport 或 loadbalancer 在 pod 上公开 jmx 端口。
如果您在服务中选择节点端口,因为您正在执行 NAT 操作,您可能必须为需要通过 jconsole 连接的每个 jvm 提供以下 JVM 参数
-Djava.rmi.server.hostname=<your-ip-address>
另一种选择是使用 kubectl port-forward 将 JMX 端口从 K8 pod 转发到您的本地 PC。
我是这样做的:
1).将以下 JVM 选项添加到您的应用程序:
-Dcom.sun.management.jmxremote
-Dcom.sun.management.jmxremote.authenticate=false
-Dcom.sun.management.jmxremote.ssl=false
-Dcom.sun.management.jmxremote.local.only=false
-Dcom.sun.management.jmxremote.port=1099
-Dcom.sun.management.jmxremote.rmi.port=1099
-Djava.rmi.server.hostname=127.0.0.1
这里的关键部分是:
应使用与 'jmxremote.port' 和 'jmxremote.rmi.port' 相同的端口。这只需要转发一个端口。
127.0.0.1 应作为 rmi 服务器主机名传递。这是 JMX 连接通过端口转发工作所必需的。
2).通过 kubectl 将 JMX 端口 (1099) 转发到本地 PC:
kubectl port-forward <your-app-pod> 1099
3).打开与本地端口 1099 的 jconsole 连接:
jconsole 127.0.0.1:1099
这种方式可以通过 JMX 调试任何 Java pod,而不必通过 K8 服务公开公开 JMX(从安全角度来看更好)。
另一个可能有用的选项是将 Jolokia (https://jolokia.org/) 代理附加到容器内的 Java 进程,以便它通过 HTTP 端口代理 JMX 并公开或转发端口此 HTTP 端口用于通过 HTTP 查询 JMX。
添加到
我使用 Shell 脚本在 运行 docker
时动态分配 podDocker文件
CMD /run.sh
run.sh
JMX_PORT=$(((RANDOM % 20)+1099))
echo "Running JMX on Port $JMX_PORT"
java ``eval echo $JAVA_OPTS`` ...
deployment.yml
env:
- name: JAVA_OPTS
value: "-Xms256m -Xmx6144m -Dcom.sun.management.jmxremote -Dcom.sun.management.jmxremote.authenticate=false -Dcom.sun.management.jmxremote.ssl=false -Dcom.sun.management.jmxremote.local.only=false -Dcom.sun.management.jmxremote.port=$JMX_PORT -Dcom.sun.management.jmxremote.rmi.port=$JMX_PORT -Djava.rmi.server.hostname=127.0.0.1"
eval 会将 JMX_PORT 评估为 bash 值,每个 pod 启动时可能会得到不同的 pod。我