Ticket #3811: envcan.2.pl

File envcan.2.pl, 4.4 KB (added by Joe Ripley <vitaminjoe@…>, 17 years ago)

New version of envcan.pl. Adds caching support. Must be marked executable.

Line 
1#!/usr/bin/perl -w
2# MythWeather-revamp script to retreive weather information from Environment
3# Canada.
4#
5# Most of this code was taken directly from Lucien Dunning's
6# (ldunning@gmail.com) PERL scripts.  Kudos to Lucien for doing all of the
7# hard work that I shamelessly stole.
8#
9# TODO Code clean up and organization
10
11use strict;
12use LWP::Simple;
13use Date::Manip;
14use Getopt::Std;
15use ENVCANLocation;
16use ENVCANParser;
17use Data::Dumper;
18
19our ($opt_v, $opt_t, $opt_T, $opt_l, $opt_u, $opt_d);
20
21my $name = 'ENVCAN';
22my $version = 0.4;
23my $author  = 'Joe Ripley';
24my $email   = 'vitaminjoe@gmail.com';
25my $updateTimeout = 15*60;
26my $retrieveTimeout = 30;
27my @types = ('cclocation', 'station_id',
28                        'observation_time', 'observation_time_rfc822', 'weather',
29                        'temp', 'relative_humidity',
30                        'wind_dir', 'wind_degrees', 'wind_speed', 'wind_gust',
31                        'pressure', 'dewpoint', 'heat_index', 'windchill',
32                        'visibility', 'weather_icon', 'appt', 'wind_spdgst',
33                        '3dlocation', '6dlocation', 'date-0', 'icon-0', 'low-0', 'high-0',
34                        'date-1', 'icon-1', 'low-1', 'high-1',
35                        'date-2', 'icon-2', 'low-2', 'high-2', 'updatetime',
36                        'date-3', 'icon-3', 'low-3', 'high-3',
37                        'date-4', 'icon-4', 'low-4', 'high-4',
38                        'date-5', 'icon-5', 'low-5', 'high-5' );
39
40my $dir = "./";
41
42getopts('Tvtlu:d:');
43
44if (defined $opt_v) {
45        print "$name,$version,$author,$email\n";
46        exit 0;
47}
48
49if (defined $opt_T) {
50        print "$updateTimeout,$retrieveTimeout\n";
51        exit 0;
52}
53if (defined $opt_l) {
54        my $search = shift;
55        ENVCANLocation::AddStationIdSearch($search);
56        ENVCANLocation::AddRegionIdSearch($search);
57        ENVCANLocation::AddCitySearch($search);
58        ENVCANLocation::AddProvinceSearch($search);
59        my $results = doSearch();
60        my $result;
61        while($result = shift @$results) {
62                if ($result->{station_id} ne "NA" ) {
63                        print "$result->{station_id}::";
64                        print "$result->{city}, $result->{region_id}\n";
65                }
66        }
67
68exit 0;
69
70}
71
72
73if (defined $opt_t) {
74        foreach (@types) {print; print "\n";}
75        exit 0;
76}
77
78if (defined $opt_d) {
79        $dir = $opt_d;
80}
81
82# check variables for defined status
83my $loc = shift;
84if (!(defined $opt_u && defined $loc && !$loc eq "")) {
85    die "Invalid usage";
86}
87
88my $units = $opt_u;
89
90# check for cached data
91my $creationdate;
92my $nextupdate;
93my %results;
94my $getData = 1;
95if (open(CACHE, "$dir/envcan_$loc")) {
96    ($nextupdate, $creationdate) = split / /, <CACHE>;
97    if (Date_Cmp($nextupdate, "today") > 0) { # use cache
98        no strict "vars";
99        %results = eval <CACHE>;
100
101        if (%results) { $getData = 0; }
102        else { print STDERR "Error parsing cache $@\n"; }
103    }
104}
105close(CACHE);
106
107# no cache, grab from the web
108if ($getData) {
109    my $base_url = 'http://www.weatheroffice.gc.ca/forecast/city_e.html?';
110    my $response = get $base_url . $loc;
111    die unless defined $response;
112
113    %results = ENVCANParser::doParse($response, @types);
114    $results{'station_id'} = $loc;
115
116    # output cache
117    open (CACHE, ">$dir/envcan_$loc") or
118        die ("Cannot open cache ($dir/envcan_$loc) for writing.");
119    $Data::Dumper::Purity   = 1;
120    $Data::Dumper::Indent   = 0;
121
122    # cache is good for 15 minutes
123    my $newmin = 15;
124
125    $nextupdate = DateCalc("today", "+ $newmin minutes");
126    print CACHE UnixDate($nextupdate, "%O ") . UnixDate("today", "%O\n");
127    print CACHE Data::Dumper->Dump([\%results], ['*results']);
128}
129
130# do some quick conversions
131if ($units eq "ENG") {
132        $results{'temp'}       = int(((9/5) * $results{'temp'}) + 32);
133        $results{'dewpoint'}   = int(((9/5) * $results{'dewpoint'}) + 32);
134        $results{'windchill'}  = int(((9/5) * $results{'windchill'}) + 32);
135        $results{'appt'}       = int(((9/5) * $results{'appt'}) + 32);
136        $results{'visibility'} = sprintf("%.1f", ($results{'visibility'} * 0.621371192));
137        $results{'pressure'}   = sprintf("%.2f", $results{'pressure'} * 0.0295301);
138        $results{'wind_speed'} = sprintf("%.2f", $results{'wind_speed'} * 1.609344);
139        $results{'wind_spdgst'} = sprintf("%.2f (NA) mph", $results{'wind_spdgst'} * 1.609344);
140       
141        for (my $i=0;$i<6;$i++) {
142                $results{"high-$i"} = int(((9/5) * $results{"high-$i"}) + 32);
143                $results{"low-$i"} = int(((9/5) * $results{"low-$i"}) + 32);
144        }
145} else {
146        $results{'wind_spdgst'} = sprintf("%.2f (NA) kph", $results{'wind_spdgst'});
147}
148       
149
150foreach my $key (sort (keys %results)) {
151        print "$key". "::";
152        if (length($results{$key}) == 0) {
153                print "NA\n";
154        } else {
155                print $results{$key} ."\n";
156        }
157}
158