I am losing my mind on this and can't figure out the issue. I am using the following code to render a chart using morris.js and I keep getting a "Uncaught TypeError: Cannot read property 'match' of undefined" error. The javascript and php code is below, is I output the php json to the console and paste it into this -> enter link description here it works! But it doesn't in my code (which I've pretty well copied from the usage example and jsbin)
HTML
<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<script src="http://cdnjs.cloudflare.com/ajax/libs/raphael/2.1.0/raphael-min.js"></script>
<script src="http://code.jquery.com/jquery-1.8.2.min.js"></script>
<script src="http://cdnjs.cloudflare.com/ajax/libs/morris.js/0.5.0/morris.js"></script>
<meta charset=utf-8 />
<title>Temperature Monitor</title>
</head>
<body>
<h3 style="text-align: center">Temperature Monitor</h3>
<div id="tempMonitor"></div>
<script src="aquaponics.charts.js"></script>
</body>
</html>
JAVASCRIPT
function getSensorData() {
var dataSet;
$.ajax({
type: "POST",
url: "sensor-data.php",
data: { waterTemperature: true },
async: false,
success: function(data) {
dataSet = data;
}
});
return dataSet;
}
var dataSet = getSensorData();
var chart = Morris.Line({
element: 'tempMonitor',
data: [0, 0],
xkey: 'datetime',
ykeys: ['temp_c'],
labels: ['Series A', 'Series B']
});
chart.setData(dataSet);
PHP (sensor-data.php)
<?php
require('app-config.php');
$limit = query_limit;
$stmt = $dbh->prepare('SELECT * FROM sensor_waterTemperature ORDER BY id DESC');
$stmt->execute();
echo json_encode($stmt->fetchAll(PDO::FETCH_ASSOC));
JSON OUTPUT (from sensor-data.php)
[{"id":"590","datetime":"2014-07-06 19:05:24","temp_c":"26.25","temp_f":"79.25"},{"id":"589","datetime":"2014-07-06 19:00:14","temp_c":"26.31","temp_f":"79.36"},{"id":"588","datetime":"2014-07-06 18:55:13","temp_c":"26.31","temp_f":"79.36"},{"id":"587","datetime":"2014-07-06 18:50:12","temp_c":"26.31","temp_f":"79.36"},{"id":"586","datetime":"2014-07-06 18:45:11","temp_c":"26.31","temp_f":"79.36"},{"id":"585","datetime":"2014-07-06 18:40:10","temp_c":"26.38","temp_f":"79.48"},{"id":"584","datetime":"2014-07-06 18:35:09","temp_c":"26.38","temp_f":"79.48"},{"id":"583","datetime":"2014-07-06 18:30:08","temp_c":"26.38","temp_f":"79.48"},{"id":"582","datetime":"2014-07-06 18:25:07","temp_c":"26.38","temp_f":"79.48"},{"id":"581","datetime":"2014-07-06 18:20:06","temp_c":"26.38","temp_f":"79.48"},{"id":"580","datetime":"2014-07-06 18:15:05","temp_c":"26.38","temp_f":"79.48"},{"id":"579","datetime":"2014-07-06 17:17:44","temp_c":"26.38","temp_f":"79.48"},{"id":"578","datetime":"2014-07-06 18:07:48","temp_c":"26.38","temp_f":"79.48"}]
UPDATE I did some more debugging and found the error is happening on morris.js:598 (see below).
Morris.parseDate = function(date) {
var isecs, m, msecs, n, o, offsetmins, p, q, r, ret, secs;
if (typeof date === 'number') {
return date;
}
m = date.match(/^(\d+) Q(\d)$/); **<<< RIGHT HERE**
n = date.match(/^(\d+)-(\d+)$/);
o = date.match(/^(\d+)-(\d+)-(\d+)$/);
UPDATE 2 I tried this as well and same error occurs.
JAVASCRIPT
function getSensorData() {
$.ajax({
type: "POST",
url: "sensor-data.php",
data: { waterTemperature: true },
async: false,
success: function(data) {
Morris.Line({
element: 'tempMonitor',
data: data,
xkey: 'datetime',
ykeys: ['temp_c'],
labels: ['Series A', 'Series B']
});
}
});
}
getSensorData();
PHP
<?php
require('app-config.php');
$limit = query_limit;
$stmt = $dbh->prepare('SELECT * FROM sensor_waterTemperature ORDER BY id DESC');
$stmt->execute();
//echo json_encode($stmt->fetchAll(PDO::FETCH_ASSOC));
while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) {
echo '{ datetime: \''.$row['datetime'].'\', temp_c: '.round($row['temp_c'], 2).' },';
}
I had exactly the same problem, finally figured out that the problem is in parsing Json object. In your case, it can be something about sending empty object values, and "match" cannot identify "date" value.
Overall, error is saying that an "undefined" value is passing to a sub-method of Morris.js , so a good work around this problem (as worked for me) can be tracing your object values to understand where an empty value is passing to "match" method.
Hope it helps.