Fix issue 255: date supplied as YYYY-MM-DD shows previous day's date...
authorDan Vanderkam <danvk@google.com>
Tue, 13 Mar 2012 23:12:45 +0000 (19:12 -0400)
committerDan Vanderkam <danvk@google.com>
Tue, 13 Mar 2012 23:12:45 +0000 (19:12 -0400)
JavaScript date parsing is stunningly complex. This was broken by
https://github.com/danvk/dygraphs/commit/769e8bc7b8799385e2677b26a5c0a72e839f44ca

The underlying issue is that new Date("YYYY-MM-DD") parses the date in
UTC, but new Date("YYYY/MM/DD") parses it in the local time zone.

auto_tests/misc/local.html
auto_tests/tests/no_hours.js [new file with mode: 0644]
dygraph-utils.js

index ae39e7f..6db0207 100644 (file)
@@ -37,6 +37,7 @@
   <script type="text/javascript" src="../tests/date_formats.js"></script>
   <script type="text/javascript" src="../tests/formats.js"></script>
   <script type="text/javascript" src="../tests/update_while_panning.js"></script>
+  <script type="text/javascript" src="../tests/no_hours.js"></script>
   <script type="text/javascript" src="../tests/update_options.js"></script>
   <script type="text/javascript" src="../tests/utils_test.js"></script>
   <script type="text/javascript" src="../tests/multiple_axes.js"></script>
diff --git a/auto_tests/tests/no_hours.js b/auto_tests/tests/no_hours.js
new file mode 100644 (file)
index 0000000..4f782d5
--- /dev/null
@@ -0,0 +1,77 @@
+/**
+ * @fileoverview Tests that we don'show specify hours, minutes or seconds
+ * in your dates if you don't specify them. This can get mixed up becaues of
+ * time zones.
+ *
+ * @author danvk@google.com (Dan Vanderkam)
+ */
+var noHoursTestCase = TestCase("no-hours");
+
+noHoursTestCase.prototype.setUp = function() {
+  document.body.innerHTML = "<div id='graph'></div>";
+};
+
+noHoursTestCase.prototype.tearDown = function() {
+};
+
+function getLegend() {
+  var legend = document.getElementsByClassName("dygraph-legend")[0];
+  return legend.textContent;
+}
+
+noHoursTestCase.prototype.testNoHours = function() {
+  var opts = {
+    width: 480,
+    height: 320
+  };
+  var data = "Date,Y\n" +
+      "2012/03/13,-1\n" +
+      "2012/03/14,0\n" +
+      "2012/03/15,1\n" +
+      "2012/03/16,0\n"
+  ;
+
+  var graph = document.getElementById("graph");
+  var g = new Dygraph(graph, data, opts);
+
+  g.setSelection(0);
+  assertEquals("2012/03/13: Y:-1", getLegend());
+
+  g.setSelection(1);
+  assertEquals("2012/03/14: Y:0", getLegend());
+
+  g.setSelection(2);
+  assertEquals("2012/03/15: Y:1", getLegend());
+
+  g.setSelection(3);
+  assertEquals("2012/03/16: Y:0", getLegend());
+};
+
+noHoursTestCase.prototype.testNoHoursDashed = function() {
+  var opts = {
+    width: 480,
+    height: 320
+  };
+  var data = "Date,Y\n" +
+      "2012-03-13,-1\n" +
+      "2012-03-14,0\n" +
+      "2012-03-15,1\n" +
+      "2012-03-16,0\n"
+  ;
+
+  var graph = document.getElementById("graph");
+  var g = new Dygraph(graph, data, opts);
+
+  g.setSelection(0);
+  assertEquals("2012/03/13: Y:-1", getLegend());
+
+  g.setSelection(1);
+  assertEquals("2012/03/14: Y:0", getLegend());
+
+  g.setSelection(2);
+  assertEquals("2012/03/15: Y:1", getLegend());
+
+  g.setSelection(3);
+  assertEquals("2012/03/16: Y:0", getLegend());
+};
+
index 689f8eb..c6c3a60 100644 (file)
@@ -494,9 +494,17 @@ Dygraph.dateParser = function(dateStr) {
   var dateStrSlashed;
   var d;
 
-  // Let the system try the format first.
-  d = Dygraph.dateStrToMillis(dateStr);
-  if (d && !isNaN(d)) return d;
+  // Let the system try the format first, with one caveat:
+  // YYYY-MM-DD[ HH:MM:SS] is interpreted as UTC by a variety of browsers.
+  // dygraphs displays dates in local time, so this will result in surprising
+  // inconsistencies. But if you specify "T" or "Z" (i.e. YYYY-MM-DDTHH:MM:SS),
+  // then you probably know what you're doing, so we'll let you go ahead.
+  // Issue: http://code.google.com/p/dygraphs/issues/detail?id=255
+  if (dateStr.search("-") == -1 ||
+      dateStr.search("T") != -1 || dateStr.search("Z") != -1) {
+    d = Dygraph.dateStrToMillis(dateStr);
+    if (d && !isNaN(d)) return d;
+  }
 
   if (dateStr.search("-") != -1) {  // e.g. '2009-7-12' or '2009-07-12'
     dateStrSlashed = dateStr.replace("-", "/", "g");