스프링 부트 JMX에 원격으로 액세스하는 방법
봄철이면 JMX 콩이 자동으로 노출된다는 걸 알아요.Visual VM을 사용하여 로컬로 액세스할 수 있었습니다.
하지만 JMX 빈을 사용하여 앱에 원격으로 연결하는 방법은 무엇입니까?디폴트 포트가 있습니까?또는 다른 포트를 정의해야 합니까?
고마워, 레이
디폴트로는 JMX는 로컬에서 자동으로 액세스 할 수 있기 때문에jconsole
포트 노출 없이 로컬 Java 앱을 모두 로컬로 탐지합니다.
JMX를 통해 원격으로 앱에 액세스하려면 RMI 레지스트리 포트를 지정해야 합니다.주의할 점은 연결 시 JMX가 해당 포트에서 초기화하고 랜덤 하이 포트로 데이터 접속을 다시 확립한다는 것입니다.이것은 중간에 방화벽이 있는 경우에는 큰 문제가 됩니다.(「이봐 sysadmins, just opening everything, mkay?」)
JMX를 설정한 포트와 같은 포트로 강제로 다시 연결하려면 다음 몇 가지 옵션이 있습니다.주의: JMX 와 RMI 에 다른 포토를 사용할 수도, 같은 포토를 사용할 수도 있습니다.
옵션 1: 명령줄
-Dcom.sun.management.jmxremote.port=$JMX_REGISTRY_PORT
-Dcom.sun.management.jmxremote.rmi.port=$RMI_SERVER_PORT
Spring Boot을 사용하는 경우 이 기능을(appname).conf
사용자 옆에 있는 파일(appname).jar
도입이 가능합니다.
옵션 2: Tomcat/Tomee 구성
Jmx Remote Life cycle Listener를 설정합니다.
메이븐 자:
<dependency>
<groupId>org.apache.tomcat</groupId>
<artifactId>tomcat-catalina-jmx-remote</artifactId>
<version>8.5.9</version>
<type>jar</type>
</dependency>
server.xml 을 설정합니다.
<Listener className="org.apache.catalina.mbeans.JmxRemoteLifecycleListener"
rmiRegistryPortPlatform="10001" rmiServerPortPlatform="10002" />
옵션 3: 프로그래밍 방식으로 구성
@Configuration
public class ConfigureRMI {
@Value("${jmx.rmi.host:localhost}")
private String rmiHost;
@Value("${jmx.rmi.port:1099}")
private Integer rmiPort;
@Bean
public RmiRegistryFactoryBean rmiRegistry() {
final RmiRegistryFactoryBean rmiRegistryFactoryBean = new RmiRegistryFactoryBean();
rmiRegistryFactoryBean.setPort(rmiPort);
rmiRegistryFactoryBean.setAlwaysCreate(true);
return rmiRegistryFactoryBean;
}
@Bean
@DependsOn("rmiRegistry")
public ConnectorServerFactoryBean connectorServerFactoryBean() throws Exception {
final ConnectorServerFactoryBean connectorServerFactoryBean = new ConnectorServerFactoryBean();
connectorServerFactoryBean.setObjectName("connector:name=rmi");
connectorServerFactoryBean.setServiceUrl(String.format("service:jmx:rmi://%s:%s/jndi/rmi://%s:%s/jmxrmi", rmiHost, rmiPort, rmiHost, rmiPort));
return connectorServerFactoryBean;
}
}
비결은, 곧 알게 되실제로serviceUrl
여기서 jmx:rmi 호스트/포트와 jndi:rmi 호스트/포트를 모두 지정합니다.둘 다 지정하면 랜덤으로 높은 "문제"가 발생하지 않습니다.
편집: JMX 리모트가 기능하려면 인증에 대해 결정해야 합니다.3개의 다른 순서로 실행하는 것이 좋습니다.1) 기본 셋업과-Dcom.sun.management.jmxremote.authenticate=false
다음으로 2) 패스워드 파일을 추가합니다.-Dcom.sun.management.jmxremote.password.file
)의 순서에 대해서는, 여기를 참조해 주세요.+-Dcom.sun.management.jmxremote.ssl=false
3) SSL을 셋업합니다.
"$JAVA"에 다음 JVM 속성 추가OPTS" (어플리케이션 내):
-Dcom.sun.management.jmxremote -Dcom.sun.management.jmxremote.port=<PORT_NUMBER> -Dcom.sun.management.jmxremote.authenticate=false -Dcom.sun.management.jmxremote.ssl=false -Djava.rmi.server.hostname=<HOST'S_IP>
Jconsole/Visual VM에서 다음을 사용하여 연결합니다.
service:jmx:rmi:///jndi/rmi://<HOST'S_IP>:<PORT_NUMBER>/jmxrmi
보안을 활성화하지는 않지만 원격 서버에 연결하는 데 도움이 됩니다.
Java 1.8.0_71 및 Spring Boot(1.3.3)에서의 테스트된 접근법.해제).모니터링되는 JVM의 JVM 인수에 다음 매개 변수를 추가합니다.
-Dcom.sun.management.jmxremote -Dcom.sun.management.jmxremote.port=12348 -Dcom.sun.management.jmxremote.authenticate=true -Dcom.sun.management.jmxremote.ssl=false -Dcom.sun.management.jmxremote.rmi.port=12349 -Dcom.sun.management.jmxremote.password.file=/somewhere/jmxremote.password -Dcom.sun.management.jmxremote.access.file=/somewhere/jmx/jmxremote.access
그com.sun.management.jmxremote.port
고정 RMI 레지스트리 포트를 정의하기 위해 사용됩니다.com.sun.management.jmxremote.rmi.port
는 고정 RMI 포트를 사용하도록 JVM에 지시하기 위해 사용되며 랜덤 RMI 포트를 사용하지 않습니다.
이를 설정하면 12348 및 12349 포트를 여는 방화벽을 통해 리모트호스트에서 감시 대상 JVM에 JVM 클라이언트를 연결할 수 있습니다.
java -jar cmdline-jmxclient-0.10.3.jar user:pwd hostip:12348
리모트 머신에서, 이하의 출력을 생성합니다(데모를 위해서만 출력).
java.lang:type=Runtime
java.lang:name=PS Scavenge,type=GarbageCollector
Tomcat:J2EEApplication=none,J2EEServer=none,WebModule=//localhost/,j2eeType=Filter,name=requestContextFilter
java.nio:name=mapped,type=BufferPool
Tomcat:host=localhost,type=Host
java.lang:name=Compressed Class Space,type=MemoryPool
.......
이 항아리는 여기에서 다운로드됩니다.
또 다른 대안
jmxremote.password 및 jmxremote.access 파일 참조
import java.util.HashMap;
import java.util.Map;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.DependsOn;
import org.springframework.jmx.support.ConnectorServerFactoryBean;
import org.springframework.remoting.rmi.RmiRegistryFactoryBean;
@Configuration
public class ConfigureRMI {
@Value("${jmx.rmi.password.file:/tmp/jmxremote.password}")
private String passwordFile;
@Value("${jmx.rmi.access.file:/tmp/jmxremote.access}")
private String accessFile;
@Value("${jmx.rmi.port:19999}")
private Integer rmiPort;
@Bean
public RmiRegistryFactoryBean rmiRegistry() {
final RmiRegistryFactoryBean rmiRegistryFactoryBean = new RmiRegistryFactoryBean();
rmiRegistryFactoryBean.setPort(rmiPort);
rmiRegistryFactoryBean.setAlwaysCreate(true);
return rmiRegistryFactoryBean;
}
@Bean
@DependsOn("rmiRegistry")
public ConnectorServerFactoryBean connectorServerFactoryBean() throws Exception {
final ConnectorServerFactoryBean connectorServerFactoryBean = new ConnectorServerFactoryBean();
connectorServerFactoryBean.setObjectName("connector:name=rmi");
Map<String, Object> properties = new HashMap<>();
properties.put("jmx.remote.x.password.file", passwordFile);
properties.put("jmx.remote.x.access.file", accessFile);
connectorServerFactoryBean.setEnvironmentMap(properties);
connectorServerFactoryBean.setServiceUrl(String.format("service:jmx:rmi:///jndi/rmi://:%s/jmxrmi", rmiPort));
return connectorServerFactoryBean;
}
}
언급URL : https://stackoverflow.com/questions/29412072/how-to-access-spring-boot-jmx-remotely
'your programing' 카테고리의 다른 글
jQuery를 사용하여 실패 시 AJAX 요청을 재시도하는 가장 좋은 방법은 무엇입니까? (0) | 2023.04.02 |
---|---|
몽구스로 데이터베이스를 삭제하는 방법? (0) | 2023.04.02 |
유효한 JSON을 얻기 위한 정규식 이스케이프 (0) | 2023.03.13 |
CMS를 직접 작성해야 합니까? (0) | 2023.03.13 |
스프링 부트 오류:java.lang.ArrayStoreException:sun.reflect.annotation.존재하지 않는 유형예외 프록시 (0) | 2023.03.13 |