commit 345c7d6adcb4ef7d07431c8b368b5f5a990300a4
Author: dsorber <david.sorber@gmail.com>
Date:   Sun Apr 28 21:24:21 2013 -0400

    Adding javascript (using Google Charts) graph of the last 60 data points to the per day display page.

diff --git a/525.743/code/web/app.wsgi b/525.743/code/web/app.wsgi
index f9a80ed..694de44 100644
--- a/525.743/code/web/app.wsgi
+++ b/525.743/code/web/app.wsgi
@@ -51,10 +51,10 @@ def application(environ, start_response):
         # Load the day template
         template = loader.load('day.html')
 
+        # Parse the date out of the URL (TODO: validate all this)
         day = environ['PATH_INFO'][5:7]
         month = environ['PATH_INFO'][7:9]
         year = environ['PATH_INFO'][9:13]
-
         date = '%s/%s/%s' % (month, day, year)
 
         # Create the response args
@@ -64,12 +64,27 @@ def application(environ, start_response):
         # grab the results, then close the DB connection.
         db_conn = sqlite3.connect(DB_PATH)
         db = db_conn.cursor()
-        db.execute("select strftime('%H:%M:%S', ts, 'unixepoch'), "
+        db.execute("select strftime('%%H:%%M:%%S', ts, 'unixepoch'), "
                    "       temp1, temp2, temp3, temp4, relay_status "
                    "from temp_data "
-                   "where date(ts, 'unixepoch') is date('2013-04-22')"
-                   "order by ts desc")
+                   "where date(ts, 'unixepoch') is date('%s-%s-%s')"
+                   "order by ts desc" % (year, month, day))
         response_args['results'] = db.fetchall()
+
+        # Chart query
+        db.execute("select strftime('%%H:%%M:%%S', ts, 'unixepoch'), temp1, "
+                   "       temp2, temp3, temp4 from ( "
+                   "select ts, temp1, temp2, temp3, temp4 "
+                   "from temp_data "
+                   "where date(ts, 'unixepoch') is date('%s-%s-%s')"
+                   "order by ts desc limit 60) order by ts" 
+                   % (year, month, day))
+        chart_results = db.fetchall()
+        # This is a bit of hack to get around a javascript issue in
+        # the template
+        response_args['chart_results'] = chart_results[:-1]
+        response_args['chart_last_row'] = chart_results[-1]
+
         db_conn.close()
 
         # Generate the stream and then render it to HTML
diff --git a/525.743/code/web/templates/day.html b/525.743/code/web/templates/day.html
index c7bf23f..06d5a61 100644
--- a/525.743/code/web/templates/day.html
+++ b/525.743/code/web/templates/day.html
@@ -1,59 +1,86 @@
 <html xmlns="http://www.w3.org/1999/xhtml"
       xmlns:py="http://genshi.edgewall.org/">
 <head>
-<title>Beer Fermenation Control System</title>
-<style type="text/css">
-	body			{font-family: sans-serif;
-		     	 	 font-size: 16px}
-	h3				{font-size: 24px;}
-	table			{border: 1px solid #000;
-			 	 	 border-spacing: 0px;}
-	table a:link	{color: #000;
-					 text-decoration: none;}
-	table a:visited	{color: #000;
-					 text-decoration: none;}
-	table a:hover	{color: #000;
-					 text-decoration: underline;}
-	tr.even			{background-color: #FFF;}
-	tr.odd			{background-color: #FFC;}
-	th				{border: 1px solid #000;
-			 	 	 padding: 10px;
-			 	 	 border-spacing: 2px;}
-	td				{border-top: 1px solid #000;
-				 	 padding: 2px 5px;}
-	.center			{text-align: center;}
-	.sensor1		{background-color: #FC0;}
-	.sensor2		{background-color: #C3F;}
-	.sensor3		{background-color: #0C0;}
-	.sensor4		{background-color: #F60;}
-	.avg      		{background-color: #AAA;}
-	.max      		{background-color: #CCC;}
-	.min      		{background-color: #EEE;}
-	.relay_on		{font-weight: bold;
-					 color: #0C0;}
-</style>
+	<title>Beer Fermenation Control System</title>
+	<style type="text/css">
+		body			{font-family: sans-serif;
+			     	 	 font-size: 16px}
+		h3				{font-size: 24px;}
+		table			{border: 1px solid #000;
+				 	 	 border-spacing: 0px;}
+		table a:link	{color: #000;
+						 text-decoration: none;}
+		table a:visited	{color: #000;
+						 text-decoration: none;}
+		table a:hover	{color: #000;
+						 text-decoration: underline;}
+		tr.even			{background-color: #FFF;}
+		tr.odd			{background-color: #FFC;}
+		th				{border: 1px solid #000;
+				 	 	 padding: 10px;
+				 	 	 border-spacing: 2px;}
+		td				{border-top: 1px solid #000;
+					 	 padding: 2px 5px;}
+		.center			{text-align: center;}
+		.sensor1		{background-color: #FC0;}
+		.sensor2		{background-color: #C3F;}
+		.sensor3		{background-color: #0C0;}
+		.sensor4		{background-color: #F60;}
+		.avg      		{background-color: #AAA;}
+		.max      		{background-color: #CCC;}
+		.min      		{background-color: #EEE;}
+		.relay_on		{font-weight: bold;
+						 color: #0C0;}
+	</style>
+	<script type="text/javascript" src="https://www.google.com/jsapi"></script>
+	<script type="text/javascript">
+	  google.load("visualization", "1", {packages:["corechart"]});
+	  google.setOnLoadCallback(drawChart);
+	  function drawChart() {
+	    var data = google.visualization.arrayToDataTable([
+	    	['Time', 'Sensor 1', 'Sensor 2', 'Sensor 3', 'Sensor 4'],
+	    	<py:for each="row in chart_results">
+	      		['${row[0]}', ${row[1]}, ${row[2]}, ${row[3]}, ${row[4]}],
+	      	</py:for>
+	      	<py:with vars="row=chart_last_row">
+	      		['${row[0]}', ${row[1]}, ${row[2]}, ${row[3]}, ${row[4]}]
+	      	</py:with>
+	    ]);
+
+	    var options = {
+	    	backgroundColor: {strokeWidth: 1},
+	      	vAxis: {maxValue: 90, minValue: 55}
+	    };
+
+	    var chart = new google.visualization.LineChart(document.getElementById('chart_div'));
+	    chart.draw(data, options);
+	  }
+	</script>
 </head>
 <body>
-<h1>${title}</h1>
-<table>
-	<tr>
-		<th>Time</th>
-		<th class="sensor1">Sensor 1</th>
-		<th class="sensor2">Sensor 2</th>
-		<th class="sensor3">Sensor 3</th>
-		<th class="sensor4">Sensor 4</th>
-		<th class="max">Relay Status</th>
-	</tr>
-	<tr py:for="ctr, row in enumerate(results)" class="${ctr % 2 and 'odd' or 'even'}">
-		<td>${row[0]}</td>
-		<td class="center">${row[1]}</td>
-		<td class="center">${row[2]}</td>
-		<td class="center">${row[3]}</td>
-		<td class="center">${row[4]}</td>
-		<td class="center ${row[5] == 1 and 'relay_on' or ''}">${int(row[5]) and 'on' or 'off'}</td>
-	</tr>
-</table>
-<br />
-<a href="/bcfs">Back</a>
+	<h1>${title}</h1>
+	<h3>Graph of Last 60 Readings</h3>
+	<div id="chart_div" style="width: 900px; height: 500px;"></div>
+	<h3>Table of All Readings</h3>
+	<table>
+		<tr>
+			<th>Time</th>
+			<th class="sensor1">Sensor 1</th>
+			<th class="sensor2">Sensor 2</th>
+			<th class="sensor3">Sensor 3</th>
+			<th class="sensor4">Sensor 4</th>
+			<th class="max">Relay Status</th>
+		</tr>
+		<tr py:for="ctr, row in enumerate(results)" class="${ctr % 2 and 'odd' or 'even'}">
+			<td>${row[0]}</td>
+			<td class="center">${row[1]}</td>
+			<td class="center">${row[2]}</td>
+			<td class="center">${row[3]}</td>
+			<td class="center">${row[4]}</td>
+			<td class="center ${row[5] == 1 and 'relay_on' or ''}">${int(row[5]) and 'on' or 'off'}</td>
+		</tr>
+	</table>
+	<br />
+	<a href="/bfcs">Back</a>
 </body>
 </html>
