Having time in ISO 8601 format (e.g. 2019-09-17T16:15:20Z
), how can I convert/normalize this time from one time zone to another time zone (such as ET
= US Eastern Time, CT
= US Central Time, PT
= US Pacific Time) ?
Desired solution should accept any time zone abbreviation, standard and non-standard abbreviations.
Perl subroutine
sub normalizeDateTime
{
... # ???
}
print normalizeDateTime('2019-09-17T16:15:20Z', 'ET');
We can use DateTime
based libraries
use DateTime::TimeZone;
use DateTime::Format::ISO8601;
use DateTime::TimeZone::Alias;
and set desired non-standard abbreviations as aliases,
DateTime::TimeZone::Alias->set('ET' => 'America/New_York');
DateTime::TimeZone::Alias->set('CT' => 'America/Chicago');
DateTime::TimeZone::Alias->set('PT' => 'America/Los_Angeles');
sub normalizeDateTime
{
my $dt = DateTime::Format::ISO8601
->new()
->parse_datetime($_[0])
->set_time_zone($_ = DateTime::TimeZone->new(name => $_[1]));
$dt . DateTime::TimeZone::offset_as_string($_->offset_for_datetime($dt))
=~ s/^[+-]00:?00$/Z/r
=~ s/^([+-]\d{2})(\d{2})$/$1:$2/r;
}
so then we can use such time zone names directly as valid time zones:
print normalizeDateTime('2019-09-17T16:15:20Z', 'ET');
2019-09-17T12:15:20-04:00