2

Let the following snippet:

var dateJS = new Date("1950-09-09T23:00:00.000Z");
var dateMoment = moment("1950-09-09T23:00:00.000Z");

console.log("Javascript Epoch Time:", dateJS.valueOf());
console.log("Moment Epoch Time:", dateMoment.valueOf());
console.log("Is DST?", dateMoment.isDST());
<script src="https://cdnjs.cloudflare.com/ajax/libs/moment.js/2.23.0/moment.min.js"></script>

If you run it with some Firefox versions (such as Firefox 61.0.1) or with Microsoft Edge you get Is DST? true. Instead, if you run it with some other Firefox versions (such as 64.0) or any Chrome you get Is DST? false.

What could be the reason?

NEW SNIPPET:

var mar1947 = moment("1947-03-20T00:00:00.000Z");
var sep1947 = moment("1947-09-10T00:00:00.000Z");
var mar1950 = moment("1950-03-20T00:00:00.000Z");
var sep1950 = moment("1950-09-10T00:00:00.000Z");
var mar2019 = moment("2019-03-20T00:00:00.000Z");
var sep2019 = moment("2019-09-10T00:00:00.000Z");

console.log("March 1947: Epoch Time / DST:", mar1947.valueOf(), mar1947.isDST());
console.log("September 1947: Epoch Time / DST:", sep1947.valueOf(), sep1947.isDST());
console.log("March 1950: Epoch Time / DST:", mar1950.valueOf(), mar1950.isDST());
console.log("September 1950: Epoch Time / DST:", sep1950.valueOf(), sep1950.isDST());
console.log("March 2019: Epoch Time / DST:", mar2019.valueOf(), mar2019.isDST());
console.log("September 2019: Epoch Time / DST:", sep2019.valueOf(), sep2019.isDST());
<script src="https://cdnjs.cloudflare.com/ajax/libs/moment.js/2.23.0/moment.min.js"></script>

Please run the snippet with Chrome and then with Firefox 61.0.1 or Microsoft Edge and see if the result is the same.

It will not.

(Full playground here https://codepen.io/anon/pen/yZMqrV)

smartmouse
  • 13,912
  • 34
  • 100
  • 166
  • I get `Is DST? true` with Chrome v71, not `Is DST? false`. (Also get `true` in Firefox 64 and Edge, but you said you do too...) – T.J. Crowder Dec 28 '18 at 11:43
  • I get `false` on Chrome 71, `false` on Firefox 64 and `true` on Edge (Win 10, timezone Europe/Rome). I noted that `dateMoment.format()` outputs `1950-09-10T00:00:00+01:00` on Chrome, while I get `1950-09-10T01:00:00+02:00` on Edge. Are you having the same issue with the lastest version of moment (2.22.2)? Does using [`moment.utc`](http://momentjs.com/docs/#/parsing/utc/) to parse input change results? – VincenzoC Dec 28 '18 at 11:54
  • @VincenzoC Yes, the same happens even with the latest version (2.23.0). – smartmouse Dec 28 '18 at 11:59
  • I edited my question: I'm using latest version of Moment now. – smartmouse Dec 28 '18 at 12:00
  • 1
    @smartmouse thanks for the feedback, Using moment 2.23.0 and `moment.utc("1950-09-09T23:00:00.000Z")` I get `Is DST? false` even on Edge. – VincenzoC Dec 28 '18 at 12:04
  • 1
    I have to admit I'd be fairly surprised if Moment's timezone files had coverage of the DST rules in effect in all the various different locations around the world in 1950... – T.J. Crowder Dec 28 '18 at 12:28
  • @VincenzoC Using `.utc()` doesn't solve my issues, since I'm using dates with .`startOf('day')` and this cause a bug: https://codepen.io/anon/pen/gZGMXOhttps://github.com/moment/moment/issues/1442 – smartmouse Dec 28 '18 at 14:39
  • Here is the correct link to github issue: https://github.com/moment/moment/issues/1442 – smartmouse Dec 28 '18 at 16:49
  • Coming back to my question, I think the answer to it can be found here: https://momentjscom.readthedocs.io/en/latest/moment/05-query/08-is-dst-shifted. "The resulting time is browser-dependent". – smartmouse Dec 28 '18 at 17:06
  • 1
    Probably a duplicate of [*Browsers, time zones, Chrome 67 Error*](https://stackoverflow.com/questions/50609860/browsers-time-zones-chrome-67-error), i.e. it's an issue with historical timezone offsets, which weren't observed until recent versions of ECMAScript. Where I live, there is no daylight saving so not an issue. :-) – RobG Dec 29 '18 at 11:58
  • Yes, it seems to be an historical DST application issue. – smartmouse Dec 29 '18 at 15:00
  • I have updated my question. – smartmouse Feb 01 '19 at 12:48

1 Answers1

5

The answer to the question "Is MomentJS browser independent?" could be "No". Getting the Long from a Moment date could depends on the browser you are using. The same affects Date object of Javascript.

The issue is related to an historical DST application in every country in the world and then with historical timezone offsets, which weren't observed until recent versions of ECMAScript. So old browser, such as Firefox 61.0.1 and Microsoft Edge haven't the right coverage of the DST rules in effect in all the various different locations around the world.

To solve this problem you have to use the .utc() method of MomentJS (as VincenzoC's comment in my answer).

So, the following code works in every browser: it always returns the same time (Epoch Time) and it "normalizes" DST for every time (it is always false):

var mar1947 = moment("1947-03-20T00:00:00.000Z").utc().startOf('day');
var sep1947 = moment("1947-09-10T00:00:00.000Z").utc().startOf('day');
var mar1950 = moment("1950-03-20T00:00:00.000Z").utc().startOf('day');
var sep1950 = moment("1950-09-10T00:00:00.000Z").utc().startOf('day');
var mar2019 = moment("2019-03-20T00:00:00.000Z").utc().startOf('day');
var sep2019 = moment("2019-09-10T00:00:00.000Z").utc().startOf('day');

console.log("March 1947:", mar1947.valueOf(), mar1947.isDST());
console.log("September 1947:", sep1947.valueOf(), sep1947.isDST());
console.log("March 1950:", mar1950.valueOf(), mar1950.isDST());
console.log("September 1950:", sep1950.valueOf(), sep1950.isDST());
console.log("March 2019:", mar2019.valueOf(), mar2019.isDST());
console.log("September 2019:", sep2019.valueOf(), sep2019.isDST());
<script src="https://cdnjs.cloudflare.com/ajax/libs/moment.js/2.23.0/moment.min.js"></script>

Please be aware that this method doesn't work propertly if you use it after (instead of before) other methods, like startOf() (see related issue on github)

Here you can use some playgrounds: Codepen1, Codepen2

smartmouse
  • 13,912
  • 34
  • 100
  • 166