I have a JavaScript function that takes a number (1-31), creates a Date
and sends it to a server via an AJAX
request:
sendDate(d) {
let date = new Date(this.year, this.month, d);
htmx.ajax("GET", "/some/url", { values: { "date": date.toISOString() } });
}
The problem is, that JavaScript is doing some timezone correction which has the effect, that if I create a date like new Date(2022, 09, 14)
I get a date Wed Sep 14 2022 00:00:00 GMT 0200 (Central European Summer Time)
which when converted to ISO format becomes 2022-09-13T22:00:00.000Z
, ie. the previous day.
I know I can use .toLocaleDateString()
, but I would like to stick to the ISO-format and I would also like to avoid hacky solutions such as always creating the date with some specified time at the middle of the day or whatever.
Is there a simple way to create a regular date object and pass it on to a server without timezone shenanigans?
CodePudding user response:
There’s a way to do that: store the date as the UNIX timestamp. I do it this way and when it’s needed, I pass the timestamp from server to client and convert it into local date.
That said, I don’t think it’s a good idea to build the date on client and pass it to the server, since it could be modified on client. I believe it’s mostly done this way (and that’s also how it’s done in my projects): on the server side, you check the current timestamp (at the time request is sent) and do with it whatever you want.
It appears that you allow your user to pick a date. It would be a good approach to convert it then to timestamp and pass it to the server.
How would you do that? If I return
date.getTime()
and then parse it (in python) withdatetime.fromtimestamp(int(request.GET['date']) / 1000)
I still get the same timezone issue...
You won't have any issues in this case - apart from the fact your server just could happen to have a different local time. A time-zone independent solution would have to use utcfromtimestamp
instead of fromtimestamp
.
Either way, the timestamp itself can't have any timezone problems by definition.
CodePudding user response:
Would this give you the desired result?
sendDate(d) {
let date = new Date(this.year, this.month, d, 0, -new Date().getTimezoneOffset());
htmx.ajax("GET", "/some/url", { values: { "date": date.toISOString() } });
}
Not as elegant, but you can just create the string in the format you expect and then date from the values:
sendDate(d) {
let date = `${this.year}-${String(this.month).padStart(2, '0')}-${String(d).padStart(2, '0')}T00:00:00.000Z`
date = new Date(date)
htmx.ajax("GET", "/some/url", { values: { "date": date.toISOString() } });
}
Edit:
function myFunction() {
let year = 2022
let month = 6 - 1
let day = 25
let date = new Date(year, month, day, 0, -new Date().getTimezoneOffset());
console.log(date.toISOString())
};
function myFunction2() {
let year = 2022
let month = 6
let day = 25
let date = `${year}-${String(month).padStart(2, '0')}-${String(day).padStart(2, '0')}T00:00:00.000Z`
date = new Date(date)
console.log(date.toISOString())
};
myFunction();
myFunction2();