Skip to content

Instantly share code, notes, and snippets.

@opsmekanix
Last active July 7, 2016 05:46
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save opsmekanix/b794c48e2a6de5153079 to your computer and use it in GitHub Desktop.
Save opsmekanix/b794c48e2a6de5153079 to your computer and use it in GitHub Desktop.
javascript example of creating simple sensu client dashboard
Recently I've been working with Sensu and learning how awesome it is to have collected data available from
Sensu's built-in API. While building an internal dashboard by embedding graphite graphs into a xwiki page this afternoon, I
thought why not add a [stashboard](http://www.stashboard.org) like block element to the dashboard as I have API access to the
Sensu data. Stashboard is something I've always admired for it's and ability to display status to an audience that doesn't
care about details, (PMs, Management, End-Users). After all, `imatation is the sincerest form of flattery` and how hard is
it to hack a little javascript?
Did I mention this is my first attempt at manipulating the DOM with javascript? :) While simple_dash.html works, it needs a
bit of updating. For one thing I wasn't able to capture the essence of stashboard, as there's too much detail in my output.
But I was successful in drawing a table of dots which change color based on Sensu node history. After being unable to
find pre-canned examples on doing something like this, I decided to publish todays javascript adventure as a gist.
To actually use simple_dash.html, one needs to add & replace valid sensu monitored hostnames to lines 8-9 and a valid
sensu server name to line 96.
~~The other challenge is embedding this in xwiki~~. ~~I was able to create javascript alertboxes by using `{{html clean="false"}}`
on the page, but I think xwiki isn't happy with people putting tables in '<div>' blocks~~. (The issue was caused by loading http content from the sensu server and embed it in a wiki page served over https. Browsers don't like to mix secure/unsecure source in the same page.) While there's still work to be done,
I'm pretty happy with how this has progressed.
<html>
<title>testpage</title>
<div id="HostStatus" style="width: 100%;word-break: nowrap; border: 2px black;"> </div>
<noscript> This page uses javascript to display historic sensu status</noscript>
<script language="Javascript" type="text/javascript">
var sensu_client_hosts = [
"host1.example.com", "host2.example.com",
"host3.example.com"
];
function runIt(hosts) {
// get history from sensu server for each host. Store in global hashmap
for (var myhost in hosts) {
printData(hosts[myhost], getHistory(hosts[myhost]) ) ;
}
}
function printData(hostname,hostdata) {
// convert string data into json
var jsonblob = JSON.parse(hostdata);
// build table
var tbl = document.createElement('table');
tbl.setAttribute("border", "2");
tbl.setAttribute("style", "display: inline-table; border: 1px dashed gray;");
var tr = tbl.insertRow();
var td = tr.insertCell();
td.appendChild(document.createTextNode(hostname));
td.colSpan=2;
for (var item in jsonblob) {
var tr1 = tbl.insertRow();
var td1 = tr1.insertCell();
td1.appendChild(document.createTextNode(jsonblob[item]['check']));
var td2 = tr1.insertCell();
td2.id=hostname + jsonblob[item]['check'];
//need to close table and update cell later using Element ID as my guess is table
//isn't ready just yet.
}
//body.appendChild(tbl);
document.getElementById("HostStatus").appendChild(tbl);
// table is closed. drawing colored circles
for (var item in jsonblob) {
var updateThisID = hostname + jsonblob[item]['check'];
var color = calcColor(jsonblob[item]['history']);
document.createTextNode(drawDots(updateThisID , color));
}
}
function calcColor(myData) {
// return string 'green', 'yellow', 'red' for status color
var color = "blue";
var result = 0;
var sum = 0;
var count = 0;
for (var val in myData) {
var datapoint = parseInt(myData[val]);
sum += datapoint;
count += 1;
}
result = sum/count;
if (result >= 0 && result < 0.75) {
color = "green";
} else if ( result >= 0.75 && result < 1.5) {
color = "yellow";
} else {
color = "red";
}
return color;
}
function drawDots(myElementName, dotColor){
var svg1 = document.createElementNS("http://www.w3.org/2000/svg", "svg");
svg1.setAttribute("height",30);
svg1.setAttribute("width",30);
document.getElementById(myElementName).appendChild(svg1);
var circles = document.createElementNS("http://www.w3.org/2000/svg", "circle");
circles.setAttribute("cx",15);
circles.setAttribute("cy",15);
circles.setAttribute("r",9);
circles.setAttribute("fill", dotColor);
circles.setAttribute("stroke", "black");
circles.setAttribute("stroke-width", 3);
svg1.appendChild(circles);
}
function getHistory(myHostName){
var req = new XMLHttpRequest() ;
var url = "http://sensu-server.example.com:4567/clients/" + myHostName + "/history/"
req.open("GET", url, false ) ;
req.send(null);
return (req.responseText) ;
}
//main
window.onload = runIt(sensu_client_hosts);
</script>
</html>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment