Commit f5341f3f f5341f3f223b416b227e29cc6ae05c7900fae3a1 by Christian Gerdes

OraMon 1.1 med JmxMon

1 parent 1215b87b
......@@ -2,6 +2,7 @@
<classpath>
<classpathentry kind="src" path="src"/>
<classpathentry combineaccessrules="false" kind="src" path="/LILOM Library"/>
<classpathentry combineaccessrules="false" kind="src" path="/LILJM Library"/>
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-1.7">
<attributes>
<attribute name="owner.project.facets" value="java"/>
......@@ -12,6 +13,5 @@
<classpathentry kind="lib" path="lib/javax.servlet.jar"/>
<classpathentry kind="lib" path="lib/javax.servlet.jsp.jar"/>
<classpathentry kind="lib" path="lib/javax.servlet.jsp.jstl.jar"/>
<classpathentry combineaccessrules="false" kind="src" path="/LILJM Library"/>
<classpathentry kind="output" path="build/classes"/>
</classpath>
......
<%@page import="se.lil.om.Registry"%>
<%@page import="se.lil.om.OraMon"%>
<%@page import="java.util.ArrayList"%>
<%@page import="se.lil.jm.JmxMon"%>
<%@page language="java" contentType="text/html; charset=ISO-8859-1" pageEncoding="ISO-8859-1"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
......@@ -17,7 +16,7 @@ String errMsg = "";
if(request.getParameter("action") != null) {
if(request.getParameter("action").equals("add")) {
if(request.getParameter("data") != null && request.getParameter("data").length() != 0) {
Registry.getList().add(new OraMon());
//se.lil.om.Registry.getList().add(new OraMon());
} else {
error = true;
errMsg = "Data is empty. Nothing added.";
......@@ -26,34 +25,36 @@ if(request.getParameter("action") != null) {
}
%>
<% ArrayList<OraMon> monList = Registry.getList(); %>
<% if(error) { %>
<div style="background: Salmon; padding: 10px;">Error: <%= errMsg %></div>
<% } %>
<h1>OraMon Web 1.0</h1>
<h1>OraMon Web 1.1 with JmxMon</h1>
<h2>Status</h2>
<h2>Status Oracle Monitors</h2>
<p>Number of monitors: <%= monList.size() %></p>
<p>Number of monitors: <%= se.lil.om.Registry.getList().size() %></p>
<div style="background-color: LightSteelBlue; padding: 10px;">
<table>
<tr>
<th>Name</th>
<th>Connection String</th>
<th>Data Calls</th>
<th>Success</th>
<th>Failed</th>
<th>Last Exception</th>
<th>Age</th>
<th>RT</th>
</tr>
<% for (OraMon mon : Registry.getList()) { %>
<% for (OraMon mon : se.lil.om.Registry.getList()) { %>
<tr>
<td><%= mon.getDBName() %></td>
<td><%= mon.getConString() %></td>
<td><%= mon.getDataCalled() %></td>
<td><%= mon.getDataSucceeded() %></td>
<td><%= mon.getDataFailed() %></td>
<td><%= mon.getLastEx() %></td>
<td><%= mon.getAgeTs() %>s</td>
<td><%= mon.getLastRTms() %>ms</td>
</tr>
......@@ -61,7 +62,38 @@ if(request.getParameter("action") != null) {
</table>
</div>
<h2>Status JMX Monitors</h2>
<p>Number of monitors: <%= se.lil.jm.Registry.getList().size() %></p>
<div style="background-color: LightSteelBlue; padding: 10px;">
<table>
<tr>
<th>Name</th>
<th>Connection String</th>
<th>Data Calls</th>
<th>Success</th>
<th>Failed</th>
<th>Last Exception</th>
<th>Age</th>
<th>RT</th>
</tr>
<% for (JmxMon mon : se.lil.jm.Registry.getList()) { %>
<tr>
<td><%= mon.getServerName() %></td>
<td><%= mon.getConString() %></td>
<td><%= mon.getDataCalled() %></td>
<td><%= mon.getDataSucceeded() %></td>
<td><%= mon.getDataFailed() %></td>
<td><%= mon.getLastEx() %></td>
<td><%= mon.getAgeTs() %>s</td>
<td><%= mon.getLastRTms() %>ms</td>
</tr>
<% } %>
</table>
</div>
<!--
<h2>Administration</h2>
<div title="Add Monitor" style="background: WhiteSmoke; padding: 10px;">
......@@ -72,5 +104,7 @@ if(request.getParameter("action") != null) {
<input type="submit" name="action" value="add">
</form>
</div>
-->
</body>
</html>
\ No newline at end of file
......
/se
/lilom.jar
/JmxMonRESTgetMetrics.class
/JmxMonRESTgetData.class
/OraMonRESTgetData.class
/OraMonRESTgetMetrics.class
......
No preview for this file type
......@@ -83,7 +83,13 @@ public class JmxMonRESTgetData extends HttpServlet {
} catch (Throwable e) {
response.setStatus(500);
response.getWriter().println("{\"error\":true,\"msg\":\""+e.toString().replace("\n"," ").replace("\"","\\\"").trim()+"\"}");
Throwable lastCause = e.getCause();
Throwable thisCause = e;
while(lastCause != null) { thisCause = lastCause; lastCause = thisCause.getCause(); }
//response.getWriter().println("{\"error\":true,\"msg\":\""+e.toString().replace("\n"," ").replace("\"","\\\"").trim()+"\"}");
String rst = "{\"error\":true,\"msg\":\"" + e.toString() + ". Caused by: " + thisCause.toString() + "\"}";
rst.replace("\n"," ").replace("\"","\\\"").trim();
response.getWriter().println(rst);
e.printStackTrace();
}
}
......
import java.io.IOException;
import javax.management.remote.JMXServiceURL;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import se.lil.jm.JmxMon;
import se.lil.jm.Registry;
/**
* Servlet implementation class JmxMonRESTgetMetrics
*/
@WebServlet(description = "Gets JMX Monitors metrics", urlPatterns = { "/JmxMonREST/getMetrics" })
public class JmxMonRESTgetMetrics extends HttpServlet {
private static final long serialVersionUID = 1L;
/**
* @see HttpServlet#HttpServlet()
*/
public JmxMonRESTgetMetrics() {
super();
// TODO Auto-generated constructor stub
}
/**
* @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
*/
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
response.setContentType("application/json");
try {
StringBuffer sb = new StringBuffer();
JmxMon mon = null;
if(request.getParameterMap().containsKey("connectionString")) {
// Check that we have a valid connection string
JMXServiceURL url;
try {
url = new JMXServiceURL(request.getParameter("connectionString"));
} catch (Exception e) {
// Error, we need a correct connection string
response.setStatus(400);
response.getWriter().println("{\"error\":true,\"msg\":\"connectionString is not a correct JMX Service URL\"}");
return;
}
// Try to find the monitor in our list
for (JmxMon item : Registry.getList()) {
if(item.getConString().equals(url.toString())) {
mon = item;
}
}
// If not found return error
if(mon == null) {
// Not found, create it
response.setStatus(HttpServletResponse.SC_NOT_FOUND);
response.getWriter().println("{\"error\":true,\"msg\":\"Can not find a monitor with connection string "+url.toString()+"\"}");
return;
}
}
// Loop over all monitors and output a Json array with the default set of metrics
sb.append("{\"error\":false,\"nvarray\":");
sb.append("[");
sb.append(",{\"name\":\"Number of processors #\",\"value\":" + mon.getNumberOfCPUs() + "}");
sb.append(",{\"name\":\"Process CPU Used %\",\"value\":" + mon.getCPUPercent() + "}");
sb.append(",{\"name\":\"Process Threads #\",\"value\":" + mon.getThreads() + "}");
sb.append(",{\"name\":\"Process Loaded Classes #\",\"value\":" + mon.getLoadedClassCount() + "}");
sb.append(",{\"name\":\"Process File Descriptors %\",\"value\":" + mon.getSystemFileDescriptorsPercentUsed() + "}");
sb.append(",{\"name\":\"Process Heap Committed MB\",\"value\":" + mon.getHeapCommittedMB() + "}");
sb.append(",{\"name\":\"Process Heap Used MB\",\"value\":" + mon.getHeapUsedMB() + "}");
sb.append(",{\"name\":\"Process Heap Used %\",\"value\":" + mon.getHeapUsedPercent() + "}");
sb.append(",{\"name\":\"OldGen Used MB\",\"value\":" + mon.getOldGenUsedMB() + "}");
sb.append(",{\"name\":\"OldGen Used %\",\"value\":" + mon.getOldGenUsedPercent() + "}");
sb.append(",{\"name\":\"OldGen After Last GC MB\",\"value\":" + mon.getOldGenAfterGCMB() + "}");
sb.append(",{\"name\":\"PermGen After Last GC MB\",\"value\":" + mon.getPermGenAfterGCMB() + "}");
sb.append(",{\"name\":\"GC Time (Overhead) %\",\"value\":" + mon.getGCOverhead() + "}");
sb.append(",{\"name\":\"System Load (per cpu)\",\"value\":" + mon.getAverageLoadPerCpu() + "}");
sb.append(",{\"name\":\"System Load (total)\",\"value\":" + mon.getAverageLoad() + "}");
sb.append(",{\"name\":\"System Memory %\",\"value\":" + mon.getSystemMemoryPercentUsed() + "}");
sb.append(",{\"name\":\"System Swap %\",\"value\":" + mon.getSystemSwapPercentUsed() + "}");
sb.append("]}");
response.getWriter().println(sb.toString());
} catch (Throwable e) {
response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
response.getWriter().println("{\"error\":true,\"msg\":\""+e.toString().replace("\n"," ").trim()+"\"}");
e.printStackTrace();
}
}
}
......@@ -237,11 +237,11 @@ public class JmxMon {
}
public long getAgeTs() {
if(lastFetchTSns > 0) return (System.nanoTime() - lastFetchTSns)/(1000*1000*1000);
else return 0;
return (System.nanoTime() - lastFetchTSns)/(1000*1000*1000);
}
Lock lock = new ReentrantLock();
Throwable lastEx = null;
public boolean getData() throws Throwable {
// Start thread safe
......@@ -260,8 +260,32 @@ public class JmxMon {
try {
long startTSns = System.nanoTime();
getDataCalls++;
// Check that we have a valid connection
if (jmxc == null || mbsc == null) open();
// Check if connection is valid
boolean stale = false;
try {
mbsc.getDefaultDomain();
} catch (Exception e) {
stale = true;
}
if(stale) {
// Try reconnect
try {
jmxc.close();
} catch (Exception e) {}
jmxc = null;
mbsc = null;
open();
mbsc.getDefaultDomain(); // This will throw an exception if we cant communicate with the server and abort this call
}
// Do the update of data
numCpus = (Integer)getAttributeValue("java.lang:type=OperatingSystem", "AvailableProcessors");
Object val = getAttributeValue("java.lang:type=OperatingSystem", "AvailableProcessors");
if(val == null) {
// Something is wrong with the connection, we cant get number of cpus. Abort
throw new Exception("Bad JMX Connection: AvailableProcessors not found in java.lang:type=OperatingSystem MBean. JMX Connection String: " + this.url.toString());
}
numCpus = (Integer)val;
fetchUpdateAttribute("java.lang:type=OperatingSystem", "ProcessCpuTime");
fetchUpdateAttribute("java.lang:type=OperatingSystem", "OpenFileDescriptorCount");
fetchUpdateAttribute("java.lang:type=OperatingSystem", "MaxFileDescriptorCount");
......@@ -299,6 +323,10 @@ public class JmxMon {
}
return true;
} catch (Throwable e) {
Throwable lastCause = e.getCause();
Throwable thisCause = e;
while(lastCause != null) { thisCause = lastCause; lastCause = thisCause.getCause(); }
lastEx = thisCause;
throw (e);
} finally {
lock.unlock();
......@@ -306,6 +334,10 @@ public class JmxMon {
// End thread safe
}
public Throwable getLastEx() {
return lastEx;
}
//NUM_CPUS
int numCpus = 0;
public long getNumberOfCPUs() {
......
......@@ -26,7 +26,7 @@ public class TestRunner {
//JmxMon mon1 = new JmxMon("service:jmx:rmi:///jndi/iiop://u02878.ht.kap.rsv.se:17040/weblogic.management.mbeanservers.runtime"); // 10.3.6.0.161018.2 PS
//JmxMon mon1 = new JmxMon("service:jmx:rmi:///jndi/iiop://u01891.ef.kap.rsv.se:17020/weblogic.management.mbeanservers.runtime"); // 10.3.6.0.161018.2 CMS
//JmxMon mon1 = new JmxMon("service:jmx:rmi:///jndi/iiop://u30450:34502/weblogic.management.mbeanservers.runtime"); // CMS
mon1.open();
//mon1.open();
//mon2.open();
jmxList.add(mon1);
//jmxList.add(mon2);
......
......@@ -93,7 +93,7 @@ public class OraMon {
}
}
public String getDBName() throws Throwable {
public String getDBName() {
return this.dbName;
}
......@@ -178,6 +178,7 @@ public class OraMon {
}
Lock lock = new ReentrantLock();
Throwable lastEx = null;
public boolean getData() throws Throwable {
// Start thread safe
......@@ -248,6 +249,10 @@ public class OraMon {
lastRTns = lastFetchTSns - startTSns;
return true;
} catch (Throwable e) {
Throwable lastCause = e.getCause();
Throwable thisCause = e;
while(lastCause != null) { thisCause = lastCause; lastCause = thisCause.getCause(); }
lastEx = thisCause;
throw (e);
} finally {
lock.unlock();
......@@ -255,6 +260,10 @@ public class OraMon {
// End thread safe
}
public Throwable getLastEx() {
return lastEx;
}
public OraMon() {
// TODO Auto-generated constructor stub
}
......