1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package it.jnrpe.plugin.jmx;
17
18 import it.jnrpe.Status;
19 import it.jnrpe.plugins.PluginBase;
20
21 import java.io.BufferedReader;
22 import java.io.IOException;
23 import java.io.InputStream;
24 import java.io.InputStreamReader;
25 import java.io.PrintStream;
26 import java.util.HashMap;
27 import java.util.Iterator;
28 import java.util.Map;
29
30 import javax.management.MBeanServerConnection;
31 import javax.management.ObjectName;
32 import javax.management.openmbean.CompositeDataSupport;
33 import javax.management.openmbean.CompositeType;
34 import javax.management.remote.JMXConnector;
35 import javax.management.remote.JMXConnectorFactory;
36 import javax.management.remote.JMXServiceURL;
37
38
39
40
41
42
43
44
45 public abstract class JMXQuery extends PluginBase {
46
47 private String url;
48 private int verbatim;
49 private JMXConnector connector;
50 private MBeanServerConnection connection;
51 private String warning, critical;
52 private String attribute, info_attribute;
53 private String attribute_key, info_key;
54 private String object;
55 private String username, password;
56
57 private Object checkData;
58 private Object infoData;
59
60 private static final String OK_STRING = "JMX OK -";
61 private static final String WARNING_STRING = "JMX WARNING -";
62 private static final String CRITICAL_STRING = "JMX CRITICAL -";
63 private static final int RETURN_UNKNOWN = 3;
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78 private static final String UNKNOWN_STRING = "JMX UNKNOWN";
79
80 protected void connect() throws IOException {
81 JMXServiceURL jmxUrl = new JMXServiceURL(url);
82
83 if (username != null) {
84 Map<String, String[]> m = new HashMap<String, String[]>();
85 m.put(JMXConnector.CREDENTIALS, new String[] { username, password });
86 connector = JMXConnectorFactory.connect(jmxUrl, m);
87 } else {
88 connector = JMXConnectorFactory.connect(jmxUrl);
89 }
90 connection = connector.getMBeanServerConnection();
91 }
92
93 protected void disconnect() throws IOException {
94 if (connector != null) {
95 connector.close();
96 connector = null;
97 }
98 }
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125 protected Status report(Exception ex, PrintStream out) {
126 if (ex instanceof ParseError) {
127 out.print(UNKNOWN_STRING + " ");
128 reportException(ex, out);
129 out.println(" Usage: check_jmx -help ");
130 return Status.UNKNOWN;
131 } else {
132 out.print(CRITICAL_STRING + " ");
133 reportException(ex, out);
134 out.println();
135 return Status.CRITICAL;
136 }
137 }
138
139 protected void reportException(Exception ex, PrintStream out) {
140
141 if (verbatim < 2)
142 out.print(rootCause(ex).getMessage());
143 else {
144 out.print(ex.getMessage() + " connecting to " + object + " by URL "
145 + url);
146 }
147
148 if (verbatim >= 3)
149 ex.printStackTrace(out);
150
151 }
152
153 private static Throwable rootCause(Throwable ex) {
154 if (ex.getCause() == null)
155 return ex;
156 return rootCause(ex.getCause());
157 }
158
159 protected Status report(PrintStream out) {
160 Status status;
161 if (compare(critical)) {
162 status = Status.CRITICAL;
163 out.print(CRITICAL_STRING);
164 } else if (compare(warning)) {
165 status = Status.WARNING;
166 out.print(WARNING_STRING);
167 } else {
168 status = Status.OK;
169 out.print(OK_STRING);
170 }
171
172 boolean shown = false;
173 if (infoData == null || verbatim >= 2) {
174 out.print(' ');
175 if (attribute_key != null)
176 out.print(attribute + '.' + attribute_key + " is " + checkData);
177 else {
178 out.print(attribute + " is " + checkData);
179 shown = true;
180 }
181
182 }
183
184 if (!shown && infoData != null) {
185 if (infoData instanceof CompositeDataSupport)
186 report((CompositeDataSupport) infoData, out);
187 else
188 out.print(infoData.toString());
189 }
190
191 out.println();
192 return status;
193 }
194
195 public String getUrl() {
196 return url;
197 }
198
199 public void setUrl(String url) {
200 this.url = url;
201 }
202
203 public int getVerbatim() {
204 return verbatim;
205 }
206
207 public void setVerbatim(int verbatim) {
208 this.verbatim = verbatim;
209 }
210
211 public String getWarning() {
212 return warning;
213 }
214
215 public void setWarning(String warning) {
216 this.warning = warning;
217 }
218
219 public String getCritical() {
220 return critical;
221 }
222
223 public void setCritical(String critical) {
224 this.critical = critical;
225 }
226
227 public String getAttribute() {
228 return attribute;
229 }
230
231 public void setAttribute(String attribute) {
232 this.attribute = attribute;
233 }
234
235 public String getInfo_attribute() {
236 return info_attribute;
237 }
238
239 public void setInfo_attribute(String info_attribute) {
240 this.info_attribute = info_attribute;
241 }
242
243 public String getAttribute_key() {
244 return attribute_key;
245 }
246
247 public void setAttribute_key(String attribute_key) {
248 this.attribute_key = attribute_key;
249 }
250
251 public String getInfo_key() {
252 return info_key;
253 }
254
255 public void setInfo_key(String info_key) {
256 this.info_key = info_key;
257 }
258
259 public String getObject() {
260 return object;
261 }
262
263 public void setObject(String object) {
264 this.object = object;
265 }
266
267 public String getUsername() {
268 return username;
269 }
270
271 public void setUsername(String username) {
272 this.username = username;
273 }
274
275 public String getPassword() {
276 return password;
277 }
278
279 public void setPassword(String password) {
280 this.password = password;
281 }
282
283 public Object getInfoData() {
284 return infoData;
285 }
286
287 public void setInfoData(Object infoData) {
288 this.infoData = infoData;
289 }
290
291 private void report(CompositeDataSupport data, PrintStream out) {
292 CompositeType type = data.getCompositeType();
293 out.print(",");
294 for (Iterator it = type.keySet().iterator(); it.hasNext();) {
295 String key = (String) it.next();
296 if (data.containsKey(key))
297 out.print(key + '=' + data.get(key));
298 if (it.hasNext())
299 out.print(';');
300 }
301 }
302
303 private boolean compare(String level) {
304 if (checkData instanceof Number) {
305 Number check = (Number) checkData;
306 if (check.doubleValue() == Math.floor(check.doubleValue())) {
307 return check.doubleValue() >= Double.parseDouble(level);
308 } else {
309 return check.longValue() >= Long.parseLong(level);
310 }
311 }
312 if (checkData instanceof String) {
313 return checkData.equals(level);
314 }
315 if (checkData instanceof Boolean) {
316 return checkData.equals(Boolean.parseBoolean(level));
317 }
318 throw new RuntimeException(level
319 + "is not of type Number,String or Boolean");
320 }
321
322 protected void execute() throws Exception {
323 Object attr =
324 connection.getAttribute(new ObjectName(object), attribute);
325 if (attr instanceof CompositeDataSupport) {
326 CompositeDataSupport cds = (CompositeDataSupport) attr;
327 if (attribute_key == null)
328 throw new ParseError("Attribute key is null for composed data "
329 + object);
330 checkData = cds.get(attribute_key);
331 } else {
332 checkData = attr;
333 }
334
335 if (info_attribute != null) {
336 Object info_attr =
337 info_attribute.equals(attribute) ? attr : connection
338 .getAttribute(new ObjectName(object),
339 info_attribute);
340 if (info_key != null && (info_attr instanceof CompositeDataSupport)
341 && verbatim < 4) {
342 CompositeDataSupport cds = (CompositeDataSupport) attr;
343 infoData = cds.get(info_key);
344 } else {
345 infoData = info_attr;
346 }
347 }
348
349 }
350
351 private void parse(String[] args) throws ParseError {
352 try {
353 for (int i = 0; i < args.length; i++) {
354 String option = args[i];
355 if (option.equals("-help")) {
356 printHelp(System.out);
357 System.exit(RETURN_UNKNOWN);
358 } else if (option.equals("-U")) {
359 this.url = args[++i];
360 } else if (option.equals("-O")) {
361 this.object = args[++i];
362 } else if (option.equals("-A")) {
363 this.attribute = args[++i];
364 } else if (option.equals("-I")) {
365 this.info_attribute = args[++i];
366 } else if (option.equals("-J")) {
367 this.info_key = args[++i];
368 } else if (option.equals("-K")) {
369 this.attribute_key = args[++i];
370 } else if (option.startsWith("-v")) {
371 this.verbatim = option.length() - 1;
372 } else if (option.equals("-w")) {
373 this.warning = args[++i];
374 } else if (option.equals("-c")) {
375 this.critical = args[++i];
376 } else if (option.equals("-username")) {
377 this.username = args[++i];
378 } else if (option.equals("-password")) {
379 this.password = args[++i];
380 }
381 }
382
383 if (url == null || object == null || attribute == null)
384 throw new Exception("Required options not specified");
385 } catch (Exception e) {
386 throw new ParseError(e);
387 }
388
389 }
390
391 private void printHelp(PrintStream out) {
392 InputStream is =
393 JMXQuery.class.getClassLoader().getResourceAsStream(
394 "jmxquery/HELP");
395 BufferedReader reader = new BufferedReader(new InputStreamReader(is));
396 try {
397 while (true) {
398 String s = reader.readLine();
399 if (s == null)
400 break;
401 out.println(s);
402 }
403 } catch (IOException e) {
404 out.println(e);
405 } finally {
406 try {
407 reader.close();
408 } catch (IOException e) {
409 out.println(e);
410 }
411 }
412 }
413
414 }