patternjavascriptMinor
Conversion of datetime strings in PHP pages to user's timezone
Viewed 0 times
conversiontimezonephpuserpagesstringsdatetime
Problem
I am working on a PHP/MySQL application that uses a different time zone from the server it runs on, and neither of the timezones are UTC. I'm converting displayed times to be in the user's timezone, and am wondering whether my approach is sensible. I would love any feedback you might have.
Firstly, the application's current time is written to the output HTML page as a
And, every instance of a
Then, after the page is loaded, the following JQuery gets the application time, the user time, figures out the difference between these, and adds that difference to the datetime data:
What am I doing wrong?
Firstly, the application's current time is written to the output HTML page as a
meta value:" />And, every instance of a
datetime string is wrapped thus:datetime_column ?>Then, after the page is loaded, the following JQuery gets the application time, the user time, figures out the difference between these, and adds that difference to the datetime data:
$("span.datetime-convert").each(function(){
var serverTime = parseDatetime($("meta[name='date']").attr("content"));
var userTime = new Date();
var userOffset = new Date(userTime.getTime() - serverTime.getTime());
var timeToConvert = parseDatetime($(this).text());
var convertedTime = new Date(timeToConvert.getTime() + userOffset.getTime());
$(this).text(convertedTime.toLocaleString());
});
function parseDatetime(value) {
var a = /^(\d{4})-(\d{2})-(\d{2}) (\d{2}):(\d{2}):(\d{2})$/.exec(value);
if (a) {
return new Date(+a[1], +a[2] - 1, +a[3], +a[4], +a[5], +a[6]);
}
return null;
}What am I doing wrong?
Solution
I would think it would be easier and more reliable to use timezone offsets rather than exact server time vs. client time. You can get the client-side offset using
PHP
HTML
JavaScript
Also there's no need to calculate the offset for each individual date. It can be actually a bit misleading when the offset is slighlty different for each date.
http://jsfiddle.net/xXVPC/1/
More functional:
new Date().getTimezoneOffset() which returns the offset in minutes from UTC. When the timezone is +2 then the offset is -120. PHP
" />HTML
JavaScript
var serverTimeZone= $("meta[name='timezoneoffset']").attr("content").substring(0,3);
// getTimezoneOffset returns (client timezone * -60).
// With timezones the the formula would be (clientTz - serverTz) * 60 * 60000
var timezoneOffset = (new Date().getTimezoneOffset() + (serverTimeZone * 60)) * 60000;
$("span.datetime-convert").each(function(){
var date = parseDatetime($(this).text());
if(date) { // If date is not wellformed the script would crash without this guard
var offsetDate = new Date(date.getTime() + timezoneOffset);
$(this).text(offsetDate .toLocaleString());
}
});
function parseDatetime(value) {
var a = /^(\d{4})-(\d{2})-(\d{2}) (\d{2}):(\d{2}):(\d{2})$/.exec(value);
if (a) {
return new Date(+a[1], +a[2] - 1, +a[3], +a[4], +a[5], +a[6]);
}
return null;
}Also there's no need to calculate the offset for each individual date. It can be actually a bit misleading when the offset is slighlty different for each date.
http://jsfiddle.net/xXVPC/1/
More functional:
var serverTimeZone= $("meta[name='timezoneoffset']").attr("content").substring(0,3);
// getTimezoneOffset returns (client timezone * -60).
// With timezones the the formula would be (clientTz - serverTz) * 60 * 60000
var timezoneOffset = (new Date().getTimezoneOffset() + (serverTimeZone * 60)) * 60000;
$("span.datetime-convert").each(function(){
var e = $(this);
parseDatetime(e.text(), new function(date) {
var offsetDate = new Date(date.getTime() + timezoneOffset);
e.text(offsetDate.toLocaleString());
});
});
function parseDatetime(value, callback) {
var a = /^(\d{4})-(\d{2})-(\d{2}) (\d{2}):(\d{2}):(\d{2})$/.exec(value);
if (a) {
callback(new Date(+a[1], +a[2] - 1, +a[3], +a[4], +a[5], +a[6]));
}
}Code Snippets
<meta name="timezoneoffset" content="<?php echo date('P') ?>" /><meta name="timezoneoffset" content="+0200" />var serverTimeZone= $("meta[name='timezoneoffset']").attr("content").substring(0,3);
// getTimezoneOffset returns (client timezone * -60).
// With timezones the the formula would be (clientTz - serverTz) * 60 * 60000
var timezoneOffset = (new Date().getTimezoneOffset() + (serverTimeZone * 60)) * 60000;
$("span.datetime-convert").each(function(){
var date = parseDatetime($(this).text());
if(date) { // If date is not wellformed the script would crash without this guard
var offsetDate = new Date(date.getTime() + timezoneOffset);
$(this).text(offsetDate .toLocaleString());
}
});
function parseDatetime(value) {
var a = /^(\d{4})-(\d{2})-(\d{2}) (\d{2}):(\d{2}):(\d{2})$/.exec(value);
if (a) {
return new Date(+a[1], +a[2] - 1, +a[3], +a[4], +a[5], +a[6]);
}
return null;
}var serverTimeZone= $("meta[name='timezoneoffset']").attr("content").substring(0,3);
// getTimezoneOffset returns (client timezone * -60).
// With timezones the the formula would be (clientTz - serverTz) * 60 * 60000
var timezoneOffset = (new Date().getTimezoneOffset() + (serverTimeZone * 60)) * 60000;
$("span.datetime-convert").each(function(){
var e = $(this);
parseDatetime(e.text(), new function(date) {
var offsetDate = new Date(date.getTime() + timezoneOffset);
e.text(offsetDate.toLocaleString());
});
});
function parseDatetime(value, callback) {
var a = /^(\d{4})-(\d{2})-(\d{2}) (\d{2}):(\d{2}):(\d{2})$/.exec(value);
if (a) {
callback(new Date(+a[1], +a[2] - 1, +a[3], +a[4], +a[5], +a[6]));
}
}Context
StackExchange Code Review Q#3534, answer score: 3
Revisions (0)
No revisions yet.