#! /usr/bin/perl # time-convert.pl # convert time between time zones, looking up daylight saving information # from the computer. # This whole program could have been made simpler using DateTime more # wholeheartedly, but I already had written a bunch of code which I # incorporated here with little change, so that is why it is the way it is. # See the usage() subroutine for what it does and how to use it. # TODO: # The obvious change is to include dates. But I don't need that, and I # didn't bother. # Copyright (C) 2006 Nick Urbanik # This program is free software; you can redistribute it and/or # modify it under the terms of the GNU General Public License # as published by the Free Software Foundation; either version 2 # of the License, or (at your option) any later version. # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. use warnings; use strict; use DateTime; use DateTime::TimeZone; use Getopt::Long; use Time::Local; sub usage() { ( my $prog = $0 ) =~ s{.*/(.*)$}{$1}xms; print <new( name => $to_tz ); $from_tz_obj = DateTime::TimeZone->new( name => $from_tz ); }; if ( $@ ) { print "to-tz or from-tz not understood:\n$@\n"; usage; } my $now = DateTime->now(); return $to_tz_obj->offset_for_datetime($now) - $from_tz_obj->offset_for_datetime($now); } sub main() { my ( $tolocal, $fromlocal, $tz, $fromtz, $totz, $list_tz ); GetOptions( 'to-local' => \$tolocal, 'from-local' => \$fromlocal, 'tz=s' => \$tz, 'from-tz=s' => \$fromtz, 'to-tz=s' => \$totz, 'list-tz' => \$list_tz, ) or print "Bad options\n" and usage; if ( $list_tz ) { print join( "\n", ( DateTime::TimeZone::all_names ) ), "\n"; exit 0; } if ( $tz ) { print "need either --tolocal or --fromlocal with --tz\n" and usage unless $tolocal or $fromlocal; } elsif ( not ( $fromtz and $totz ) ) { print "Need specify one timezone with --tz or two timezones.\n"; usage; } my $in_time = shift @ARGV or print "need specify time.\n" and usage; print "Cannot recognise time $in_time\n" and usage unless $in_time =~ /^\d+:\d+(?::[\d.]+)?$/; if ( $tolocal ) { $totz = 'local'; $fromtz = $tz; } elsif ( $fromlocal ) { $fromtz = 'local'; $totz = $tz; } my ( $sec, $min, $hour, $mday, $mon, $year ) = localtime time; ( $hour, $min, $sec ) = split /:/, $in_time; my $ctime = timelocal $sec, $min, $hour, $mday, $mon, $year; my $difference = calc_difference $fromtz, $totz; $ctime += $difference; my $new_mday; ( $sec, $min, $hour, $new_mday, $mon, $year ) = localtime $ctime; if ( $new_mday > $mday ) { print "Tomorrow "; } elsif ( $new_mday < $mday ) { print "Yesterday "; } printf "%d:%02d", $hour, $min; print ":$sec" if $sec; print "\n"; } main;