When I create a new date, when I try modifying it to e.g. get a date 30 days ago, the timezone the date is represented in changes when I print it out, and the math ends up incorrect because of it.
In the example below it's initially printing in EDT and then changes to EST after using setDate
. Not just that, but the math ends up being incorrect (off by one hour) since the time is the same but the timezones are different by an hour, and subtracting whole days should obviously result in the same time.
> d = new Date();
< Thu Apr 04 2024 17:14:02 GMT-0400 (Eastern Daylight Time)
> d.setDate(d.getDate() - 30)
< 1709676842549
> d
< Tue Mar 05 2024 17:14:02 GMT-0500 (Eastern Standard Time)
What am I missing or doing wrong here?
What are you missing? That the timezone offset is always calculated with respect to the date you are looking at and not of the current date.
You seem to be in a timezone which distinguishes beetween daylight saving time and standard time. Ie during summer you have a different offset to UTC than during winter. And the date where this is changed is somewhere in between the 4th of March and the 4th of April. That's just how daylight saving time works.
So today (on the 4th of April) your timezone offset is UTC -4 hours. But on the 4th of March it was UTC -5 hours. So for any calculations with the time of the day on a certain date X
, you always need to take into account what is the UTC offset for this specific date X
is. You must not just use today's offset. It might work, but it might also be wrong.
Also for adding longer timespans to a specific date, you cannot just do something like
let d1 = new Date(2024, 2, 4).getTime();
let d2 = d1 + 86400 * 30 * 1000; //a day has 86400 seconds,
to add 30 days, because if there is a DST switch during that timespan, your calculations will be off by one hour ...
Actually in your shown example, when using setDate(...)
the time of the day stays the same (ie 17:14) just the UTC offset changes. But 30 days in this case are not the same as 30x24 = 720 hours, but 719 or 721, depending on whether you switched from DST to standard time or vice versa.
I personally only seldomly work with the plain Date
object in Javascript, because of these issues, but use some 3rd party libraries, which provide better methods for such date-calculations and dealing with different timezones.