From: Iskren Chernev Date: Tue, 7 Oct 2014 10:19:47 +0000 (-0700) Subject: Support 24:00:00.000 to mean next day, at midnight. X-Git-Tag: 2.8.4~15^2~1 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=1214808b97c60945ab4769a65ecc31d5140705b8;p=thirdparty%2Fmoment.git Support 24:00:00.000 to mean next day, at midnight. --- diff --git a/moment.js b/moment.js index 49b014149..f3f708325 100644 --- a/moment.js +++ b/moment.js @@ -701,7 +701,10 @@ overflow = m._a[MONTH] < 0 || m._a[MONTH] > 11 ? MONTH : m._a[DATE] < 1 || m._a[DATE] > daysInMonth(m._a[YEAR], m._a[MONTH]) ? DATE : - m._a[HOUR] < 0 || m._a[HOUR] > 23 ? HOUR : + m._a[HOUR] < 0 || m._a[HOUR] > 24 || + (m._a[HOUR] === 24 && (m._a[MINUTE] !== 0 || + m._a[SECOND] !== 0 || + m._a[MILLISECOND] !== 0)) ? HOUR : m._a[MINUTE] < 0 || m._a[MINUTE] > 59 ? MINUTE : m._a[SECOND] < 0 || m._a[SECOND] > 59 ? SECOND : m._a[MILLISECOND] < 0 || m._a[MILLISECOND] > 999 ? MILLISECOND : @@ -1384,12 +1387,25 @@ config._a[i] = input[i] = (config._a[i] == null) ? (i === 2 ? 1 : 0) : config._a[i]; } + // Check for 24:00:00.000 + if (config._a[HOUR] === 24 && + config._a[MINUTE] === 0 && + config._a[SECOND] === 0 && + config._a[MILLISECOND] === 0) { + config._nextDay = true; + config._a[HOUR] = 0; + } + config._d = (config._useUTC ? makeUTCDate : makeDate).apply(null, input); // Apply timezone offset from input. The actual zone can be changed // with parseZone. if (config._tzm != null) { config._d.setUTCMinutes(config._d.getUTCMinutes() + config._tzm); } + + if (config._nextDay) { + config._a[HOUR] = 24; + } } function dateFromObject(config) { @@ -1744,7 +1760,8 @@ function makeMoment(config) { var input = config._i, - format = config._f; + format = config._f, + res; config._locale = config._locale || moment.localeData(config._l); @@ -1768,7 +1785,14 @@ makeDateFromInput(config); } - return new Moment(config); + res = new Moment(config); + if (res._nextDay) { + // Adding is smart enough around DST + res.add(1, 'd'); + res._nextDay = undefined; + } + + return res; } moment = function (input, format, locale, strict) { diff --git a/test/moment/create.js b/test/moment/create.js index 193a3678a..1baed4a1e 100644 --- a/test/moment/create.js +++ b/test/moment/create.js @@ -146,6 +146,14 @@ exports.create = { test.done(); }, + 'iso format 24hrs' : function (test) { + test.equal(moment('2014-01-01T24:00:00.000').format('YYYY-MM-DD[T]HH:mm:ss.SSS'), + '2014-01-02T00:00:00.000', 'iso format with 24:00 localtime'); + test.equal(moment.utc('2014-01-01T24:00:00.000').format('YYYY-MM-DD[T]HH:mm:ss.SSS'), + '2014-01-02T00:00:00.000', 'iso format with 24:00 utc'); + test.done(); + }, + 'string without format - json' : function (test) { test.expect(5); test.equal(moment('Date(1325132654000)').valueOf(), 1325132654000, 'Date(1325132654000)'); diff --git a/test/moment/is_valid.js b/test/moment/is_valid.js index d6670c75e..69ac00d2e 100644 --- a/test/moment/is_valid.js +++ b/test/moment/is_valid.js @@ -108,7 +108,7 @@ exports.isValid = { '2010-00-00', '2010-01-00', '2010-01-40', - '2010-01-01T24', + '2010-01-01T24:01', // 24:00:00 is actually valid '2010-01-01T23:60', '2010-01-01T23:59:60' ], i; @@ -127,7 +127,7 @@ exports.isValid = { '2010-00-00T+00:00', '2010-01-00T+00:00', '2010-01-40T+00:00', - '2010-01-40T24+00:00', + '2010-01-40T24:01+00:00', '2010-01-40T23:60+00:00', '2010-01-40T23:59:60+00:00', '2010-01-40T23:59:59.9999+00:00' @@ -165,10 +165,10 @@ exports.isValid = { }, 'invalidAt' : function (test) { - test.expect(7); test.equal(moment([2000, 12]).invalidAt(), 1, 'month 12 is invalid: 0-11'); test.equal(moment([2000, 1, 30]).invalidAt(), 2, '30 is not a valid february day'); - test.equal(moment([2000, 1, 29, 24]).invalidAt(), 3, '24 is invalid hour'); + test.equal(moment([2000, 1, 29, 25]).invalidAt(), 3, '25 is invalid hour'); + test.equal(moment([2000, 1, 29, 24, 01]).invalidAt(), 3, '24:01 is invalid hour'); test.equal(moment([2000, 1, 29, 23, 60]).invalidAt(), 4, '60 is invalid minute'); test.equal(moment([2000, 1, 29, 23, 59, 60]).invalidAt(), 5, '60 is invalid second'); test.equal(moment([2000, 1, 29, 23, 59, 59, 1000]).invalidAt(), 6, '1000 is invalid millisecond'); diff --git a/test/moment/parsing_flags.js b/test/moment/parsing_flags.js index 7048370a2..efab2ef81 100644 --- a/test/moment/parsing_flags.js +++ b/test/moment/parsing_flags.js @@ -31,7 +31,8 @@ exports.parsingFlags = { test.equal(flags([2010, 1, 1, 8]).overflow, -1, 'hour valid'); test.equal(flags([2010, 1, 1, 0]).overflow, -1, 'hour 0 valid'); test.equal(flags([2010, 1, 1, -1]).overflow, 3, 'hour -1 invalid'); - test.equal(flags([2010, 1, 1, 24]).overflow, 3, 'hour 24 invalid'); + test.equal(flags([2010, 1, 1, 25, 01]).overflow, 3, 'hour 25 invalid'); + test.equal(flags([2010, 1, 1, 24, 01]).overflow, 3, 'hour 24:01 invalid'); //minutes test.equal(flags([2010, 1, 1, 8, 15]).overflow, -1, 'minute valid'); @@ -51,6 +52,12 @@ exports.parsingFlags = { test.equal(flags([2010, 1, 1, 8, 15, 12, -1]).overflow, 6, 'millisecond -1 invalid'); test.equal(flags([2010, 1, 1, 8, 15, 12, 1000]).overflow, 6, 'millisecond 1000 invalid'); + // 24 hrs + test.equal(flags([2010, 1, 1, 24, 0, 0, 0]).overflow, -1, '24:00:00.000 is fine'); + test.equal(flags([2010, 1, 1, 24, 1, 0, 0]).overflow, 3, '24:01:00.000 is wrong hour'); + test.equal(flags([2010, 1, 1, 24, 0, 1, 0]).overflow, 3, '24:00:01.000 is wrong hour'); + test.equal(flags([2010, 1, 1, 24, 0, 0, 1]).overflow, 3, '24:00:00.001 is wrong hour'); + test.done(); }, @@ -77,7 +84,8 @@ exports.parsingFlags = { //hours test.equal(flags('08', 'HH').overflow, -1, 'hour valid'); test.equal(flags('00', 'HH').overflow, -1, 'hour 0 valid'); - test.equal(flags('24', 'HH').overflow, 3, 'hour 24 invalid'); + test.equal(flags('25', 'HH').overflow, 3, 'hour 25 invalid'); + test.equal(flags('24:01', 'HH:mm').overflow, 3, 'hour 24:01 invalid'); //minutes test.equal(flags('08:15', 'HH:mm').overflow, -1, 'minute valid');