Skip to content

Commit 256ad56

Browse files
committed
Fixes #558: NullPointerException in cli-activemq-jmx when NumberOfPages address property changed type (#559)
(cherry picked from commit 5eae510)
1 parent 735c3f7 commit 256ad56

File tree

5 files changed

+70
-11
lines changed

5 files changed

+70
-11
lines changed

cli-activemq-jmx/src/main/java/com/redhat/amqx/management/ObjectReader.java

Lines changed: 43 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,14 @@
66
import org.slf4j.LoggerFactory;
77

88
import javax.management.AttributeNotFoundException;
9+
import javax.management.InstanceNotFoundException;
10+
import javax.management.MBeanAttributeInfo;
11+
import javax.management.MBeanException;
12+
import javax.management.MBeanInfo;
13+
import javax.management.MBeanServerConnection;
14+
import javax.management.ObjectName;
15+
import javax.management.ReflectionException;
16+
import java.io.IOException;
917
import java.lang.reflect.InvocationHandler;
1018
import java.lang.reflect.InvocationTargetException;
1119
import java.lang.reflect.Method;
@@ -100,7 +108,10 @@ private Map<String, Object> extractMethodProperty(Method method, Object object,
100108
throw new DestinationException(
101109
String.format("Unable to access '%s' of '%s' object!", object.getClass(), method.getName()));
102110
} catch (Throwable e) {
103-
logger.debug(e.getCause().toString());
111+
logger.debug(e.toString());
112+
if (e.getCause() != null) {
113+
logger.debug(e.getCause().toString());
114+
}
104115
}
105116
return methodPropertyMap;
106117
}
@@ -169,6 +180,37 @@ public Map<String, Object> getObjectProperties(Object object, List<String> exclu
169180
}
170181
return propertiesMap;
171182
}
183+
184+
public Map<String, Object> getRawObjectProperties(MBeanServerConnection mBeanServerConnection, ObjectName objectName, List<String> excludeMethodList) throws DestinationException {
185+
Map<String, Object> propertiesMap = new HashMap<>();
186+
187+
MBeanInfo info;
188+
try {
189+
info = mBeanServerConnection.getMBeanInfo(objectName);
190+
} catch (Throwable e) {
191+
throw new RuntimeException(e);
192+
}
193+
for (MBeanAttributeInfo attributeInfo : info.getAttributes()) {
194+
String attributeName = attributeInfo.getName();
195+
196+
// get rid of get/is+lowercase first letter
197+
String propertyName = getPropertyNameByMethod(attributeName, 0);
198+
199+
Object value = null;
200+
try {
201+
value = mBeanServerConnection.getAttribute(objectName, attributeName);
202+
propertiesMap.put(propertyName, value);
203+
} catch (MBeanException | AttributeNotFoundException | InstanceNotFoundException | ReflectionException |
204+
IOException e) {
205+
206+
e.printStackTrace();
207+
} catch (Throwable e) {
208+
logger.debug(e.toString());
209+
}
210+
}
211+
212+
return propertiesMap;
213+
}
172214
}
173215

174216
class ProxyHandler implements InvocationHandler {

cli-activemq-jmx/src/main/java/com/redhat/amqx/management/Resolver.java

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
package com.redhat.amqx.management;
22

3+
import javax.management.ObjectName;
4+
35
/**
46
* Interface for resolving view management
57
* objects like queues, topics, broker information.
@@ -18,6 +20,8 @@ public interface Resolver<T, R, S, U, V> {
1820

1921
U getAddressView(String addressName) throws Exception;
2022

23+
public ObjectName getAddressObjectName(String addressName) throws Exception;
24+
2125
V getDivertView(String addressName, String divertName) throws Exception;
2226

2327
}

cli-activemq-jmx/src/main/java/com/redhat/amqx/management/activemq/ActiveMQResolver.java

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,12 @@ public QueueViewMBean getAddressView(String queueName) throws Exception {
5757
return null;
5858
}
5959

60+
@Override
61+
public ObjectName getAddressObjectName(String addressName) throws Exception {
62+
System.err.println("Does not exist for AMQ!");
63+
return null;
64+
}
65+
6066
@Override
6167
public QueueViewMBean getDivertView(String addressName, String divertName) throws Exception {
6268
System.err.println("Does not exist for AMQ!");

cli-activemq-jmx/src/main/java/com/redhat/amqx/management/artemis/AbstractArtemisManager.java

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@
88
import com.redhat.amqx.management.AbstractConnectionManager;
99
import com.redhat.amqx.management.Credentials;
1010
import com.redhat.amqx.management.Resolver;
11-
import org.apache.activemq.artemis.api.core.ActiveMQAddressDoesNotExistException;
1211
import org.apache.activemq.artemis.api.core.management.ActiveMQServerControl;
1312
import org.apache.activemq.artemis.api.core.management.AddressControl;
1413
import org.apache.activemq.artemis.api.core.management.DivertControl;
@@ -20,6 +19,7 @@
2019
import org.slf4j.Logger;
2120
import org.slf4j.LoggerFactory;
2221

22+
import javax.management.ObjectName;
2323
import java.io.IOException;
2424
import java.util.*;
2525

@@ -176,8 +176,8 @@ public Map<String, Object> getDestinationProperties(String addressName, String d
176176
}
177177
}
178178

179-
AddressControl addressControl = (AddressControl) getResolver().getAddressView(addressName);
180-
propertiesMap.putAll(objectReader.getObjectProperties(addressControl, excludeMethods));
179+
ObjectName addressObjectName = getResolver().getAddressObjectName(addressName);
180+
propertiesMap.putAll(objectReader.getRawObjectProperties(mBeanServerConnection, addressObjectName, excludeMethods));
181181
propertiesMap.put("address-settings", new JSONObject(getServerControlMBean().getAddressSettingsAsJSON(addressName)));
182182
return propertiesMap;
183183
}

cli-activemq-jmx/src/main/java/com/redhat/amqx/management/artemis/ArtemisResolver.java

Lines changed: 14 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
import org.apache.activemq.artemis.api.core.SimpleString;
55
import org.apache.activemq.artemis.api.core.management.*;
66
import org.apache.activemq.artemis.api.core.RoutingType;
7+
import org.jetbrains.annotations.NotNull;
78

89
import javax.management.MBeanServerConnection;
910
import javax.management.MBeanServerInvocationHandler;
@@ -16,10 +17,12 @@ public class ArtemisResolver implements Resolver<ActiveMQServerControl, QueueCon
1617
private final String DEFAULT_DOMAIN = "org.apache.activemq.artemis";
1718
private MBeanServerConnection mBeanServerConnection;
1819
private String brokerName;
20+
private ObjectNameBuilder objectNameBuilder;
1921

2022
public ArtemisResolver(MBeanServerConnection mBeanServerConnection, String brokerName) {
2123
this.mBeanServerConnection = mBeanServerConnection;
2224
this.brokerName = brokerName;
25+
this.objectNameBuilder = ObjectNameBuilder.create(DEFAULT_DOMAIN, brokerName, true);
2326
}
2427

2528
@Override
@@ -29,40 +32,44 @@ public String getBrokerName() {
2932

3033
@Override
3134
public ActiveMQServerControl getBrokerView() throws Exception {
32-
ObjectName objectName = ObjectNameBuilder.create(DEFAULT_DOMAIN, brokerName, true).getActiveMQServerObjectName();
3335
// 1.0 org.apache.activemq.artemis:module=Core,type=Server
3436
// 1.2 org.apache.activemq.artemis:type=Broker,brokerName="<broker-name>",module=Core,ServerType=Server";
3537
// 1.5.1 org.apache.activemq.artemis:type=Broker,brokerName="amq",serviceType=Address,name="queue-anycast2"
3638
// 2.0 org.apache.activemq.artemis:broker="<brokerName>",component=addresses,address="<addressName>",subcomponent=queues,routing-type="<routingType>",queue="<queueName>"
37-
objectName = ObjectNameBuilder.create(DEFAULT_DOMAIN, brokerName, true).getActiveMQServerObjectName();
39+
ObjectName objectName = objectNameBuilder.getActiveMQServerObjectName();
3840
return MBeanServerInvocationHandler.newProxyInstance(mBeanServerConnection, objectName, ActiveMQServerControl.class, false);
3941
}
4042

4143
@Override
4244
public QueueControl getQueueView(String addressName, String queueName) throws Exception {
43-
ObjectName objectName = ObjectNameBuilder.create(DEFAULT_DOMAIN, brokerName, true).getQueueObjectName(new SimpleString(addressName), new SimpleString(queueName), RoutingType.ANYCAST);
45+
ObjectName objectName = objectNameBuilder.getQueueObjectName(new SimpleString(addressName), new SimpleString(queueName), RoutingType.ANYCAST);
4446
return MBeanServerInvocationHandler.newProxyInstance(mBeanServerConnection, objectName, QueueControl.class, false);
4547
}
4648

4749
@Override
4850
public QueueControl getTopicView(String addressName, String topicName) throws Exception {
4951
// if address doesn't add RoutingType.MULTICAST, it does not have any type
50-
ObjectName objectName = ObjectNameBuilder.create(DEFAULT_DOMAIN, brokerName, true).getQueueObjectName(new SimpleString(addressName), new SimpleString(topicName), RoutingType.MULTICAST);
52+
ObjectName objectName = objectNameBuilder.getQueueObjectName(new SimpleString(addressName), new SimpleString(topicName), RoutingType.MULTICAST);
5153
return MBeanServerInvocationHandler.newProxyInstance(mBeanServerConnection, objectName, QueueControl.class, false);
5254
}
5355

5456
public AcceptorControl getAcceptorView(String acceptorName) throws Exception {
55-
ObjectName objectname = ObjectNameBuilder.create(DEFAULT_DOMAIN, brokerName, true).getAcceptorObjectName(acceptorName);
57+
ObjectName objectname = objectNameBuilder.getAcceptorObjectName(acceptorName);
5658
return MBeanServerInvocationHandler.newProxyInstance(mBeanServerConnection, objectname, AcceptorControl.class, false);
5759
}
5860

5961
public AddressControl getAddressView(String addressName) throws Exception {
60-
ObjectName objectname = ObjectNameBuilder.create(DEFAULT_DOMAIN, brokerName, true).getAddressObjectName(new SimpleString(addressName));
62+
ObjectName objectname = getAddressObjectName(addressName);
6163
return MBeanServerInvocationHandler.newProxyInstance(mBeanServerConnection, objectname, AddressControl.class, false);
6264
}
6365

66+
@NotNull
67+
public ObjectName getAddressObjectName(String addressName) throws Exception {
68+
return objectNameBuilder.getAddressObjectName(new SimpleString(addressName));
69+
}
70+
6471
public DivertControl getDivertView(String addressName, String divertName) throws Exception {
65-
ObjectName objectname = ObjectNameBuilder.create(DEFAULT_DOMAIN, brokerName, true).getDivertObjectName(divertName, addressName);
72+
ObjectName objectname = objectNameBuilder.getDivertObjectName(divertName, addressName);
6673
return MBeanServerInvocationHandler.newProxyInstance(mBeanServerConnection, objectname, DivertControl.class, false);
6774
}
6875

0 commit comments

Comments
 (0)