geo-metar02.pl to HTML.

index -|- end

Generated: Mon Aug 29 19:34:38 2016 from geo-metar02.pl 2014/11/18 11.7 KB. text copy

#!/usr/bin/perl -w
# NAME: geo_metar02.pl
# AIM: Get the METAR for a particular ICAO
# 18/11/2014 - Revisit - Had to install Geo::METAR - Added use batch : metar ICAO
# CPAN install: Open MSVC x64 prompt; perl -MCPAN -e shell;, then install Geo::METAR
# 22/07/2011 - First cut
use strict;
use warnings;
use File::Basename;  # split path ($name,$dir,$ext) = fileparse($file [, qr/\.[^.]*/] )
use Cwd;
use Socket;
use LWP::Simple;
use Geo::METAR;
use Date::Parse;
use Data::Dumper;

my $perl_dir = 'C:\GTools\perl';
unshift(@INC, $perl_dir);
require 'lib_utils.pl' or die "Unable to load 'lib_utils.pl ...\n";
# log file stuff
our ($LF);
my $pgmname = $0;
if ($pgmname =~ /(\\|\/)/) {
    my @tmpsp = split(/(\\|\/)/,$pgmname);
    $pgmname = $tmpsp[-1];
}
my $outfile = $perl_dir."\\temp.$pgmname.txt";
open_log($outfile);

# user variables
my $vers = "0.0.2 2014-11-18";
###my $vers = "0.0.1 2011-07-22";
my $load_log = 0;
my $in_file = '';
my $out_file = '';
my $verbosity = 0;
my $fetch_new = 0;

# program variables

my $TAFBASE  = 'http://weather.noaa.gov/pub/data/forecasts/taf/stations/';
my $METARBASE = 'http://weather.noaa.gov/pub/data/observations/metar/stations/';
# 1 hPa = 0.0 295 300 586 467 inHg (0.02953)
my $HP2INCHES = 0.0295300586467;
# 1 Knot = 1.15077845 Miles Per Hour.
my $KNOT2MPH = 1.15077845;
# 1 Miles Per Hour = 0.86897699264 Knot.
my $MPH2KNOT = 0.86897699264;

my $debug_on = 0;
my $def_file = 'YSDU';

sub VERB1() { return $verbosity >= 1; }
sub VERB2() { return $verbosity >= 2; }
sub VERB5() { return $verbosity >= 5; }
sub VERB9() { return $verbosity >= 9; }


my @geo_metar = qw( pressure visibility slp DATE HOURLY_TEMP_C date_time 
    modifier VISIBILITY DEW_F windvar TEMP_F debug HOURLY_DEW_C SITE 
    SKY WIND_VAR_1 WIND_DIR_ENG WIND_GUST_KTS REMARKS RUNWAY HOURLY_PRECIP
    runway type WIND_VAR_2 WIND_VAR WIND_DIR_ABB HOURLY_DEW_F WIND_MPH
    wind WIND_KTS unknown weather windtype remarks WEATHER_LOG TEMP_C
    WIND_GUST_MPH DEW_C WIND_DIR_DEG sky HOURLY_TEMP_F SLP alt TIME
    tokens MOD TYPE WEATHER METAR site temp_dew VERSION UNKNOWN ALT );
my %geo_arrays = (
    'SKY' => 1,
    'RUNWAY' => 1,
    'unknown' => 1,
    'weather' => 1,
    'remarks' => 1,
    'WEATHER_LOG' => 1,
    'sky' => 1,
    'tokens' => 1,
    'WEATHER' => 1,
    'UNKNOWN' => 1 );

### program variables
my @warnings = ();
my $cwd = cwd();
my $os = $^O;

my @ICAO_LIST = ();

sub show_warnings($) {
    my ($val) = @_;
    if (@warnings) {
        prt( "\nGot ".scalar @warnings." WARNINGS...\n" );
        foreach my $itm (@warnings) {
           prt("$itm\n");
        }
        prt("\n");
    } else {
        ###prt( "\nNo warnings issued.\n\n" );
    }
}

sub pgm_exit($$) {
    my ($val,$msg) = @_;
    if (length($msg)) {
        $msg .= "\n" if (!($msg =~ /\n$/));
        prt($msg);
    }
    show_warnings($val);
    close_log($outfile,$load_log);
    exit($val);
}


sub prtw($) {
   my ($tx) = shift;
   $tx =~ s/\n$//;
   prt("$tx\n");
   push(@warnings,$tx);
}

# 9.C = 5.F - 160
sub celcius_to_fahrenheight($) {
    my ($dc) = shift;
    my $df = (($dc * 9) + 160) / 5;
    return $df;
}
sub fahrenheight_to_celcius($) {
    my ($df) = @_;
    my $dc = (($df - 32) * 100) / 180;
    return $dc;
}

sub trim_metar_txt($) {
    my $met = shift;
   $met =~ s/\n/ /gm;
   $met =~ s/\r/ /gm;
   $met =~ s/\t/ /gm;
   $met = trim_all($met);
    return $met;
}

sub fetch_url {   # see gettaf01.pl
   my ($url) = shift;
   prt( "Fetching: $url\n" );
   my $txt = get($url);
    my $met = '';
   if ($txt && length($txt)) {
        $met = trim_all($txt);
        if (length($met)) {
          prt( "$met\n" );
        } else {
          prt( "FAILED to get URL $url ...\n" );
        }
   } else {
      prt( "FAILED to get URL $url ...\n" );
   }
    return $met;
}

sub process_in_list() {
    my ($inf,$url,$met,$file,@arr,$key,$val);
    my ($min,$len,$cnt,$lckey,$uckey);
    my ($line,$msg,$tmp);
    my $m = new Geo::METAR;
    my %dupes = ();
    my %list = ();
    foreach $inf (@ICAO_LIST) {
        $file = $perl_dir."\\temp.$inf.TXT";
        $url = $METARBASE.$inf.".TXT";
        $met = '';
        if (-f $file && !$fetch_new ) {
            if (open FIL, "<$file") {
                @arr = <FIL>;
                close FIL;
                $met = join(" ",@arr);
                $met = trim_all($met);
                if (length($met)) {
                    prt("Loaded metar from [$file]\n");
                }
            }
        } else {
            $met = fetch_url($url);
            if (length($met)) {
                $met = trim_metar_txt($met);
                if (length($met)) {
                    write2file($met,$file);
                    prt("Metar written to [$file]\n");
                }
            }
        }

        if (length($met)) {
           prt( "METAR: [$met]\n" ) if (VERB1());
            $m->metar($met);
            #prt( $m->dump );
            #prt(Dumper($m));
            @arr = sort keys(%{$m});
            $line = '';
            $msg = 'Keys: ';
            #prt("Keys: ".join(" ",@arr)."\n");
            foreach $key (@arr) {
                $line .= ' ' if (length($line));
                $line .= $key;
                if (length($line) > 80) {
                    $msg .= "$line\n";
                    $line = '';
                }
            }
            $msg .= $line if (length($line));
            prt("$msg\n") if (VERB5());
            $min = 0;
            $cnt = 0;
            foreach $key (sort @geo_metar) {
                next if ($key eq 'VERSION');
                $uckey = uc($key);
                $lckey = lc($key);
                if (defined ${$m}{$key}) {
                    $val = ${$m}{$key};
                    if (defined $geo_arrays{$key}) {
                        # we have an array ref
                    } else {
                        $val = trim_all($val);
                        if (length($val)) {
                            if (!defined $dupes{$uckey} && !defined $dupes{$lckey}) {
                                $len = length($key);
                                $min = $len if ($len > $min);
                                $dupes{$uckey} = 1;
                                $dupes{$lckey} = 1;
                                $list{$key} = $val;
                                $cnt++;
                            }
                        }
                    }
                }
            }

            prt("\nGot $cnt different items...\n");
            $msg = '';
            my ($epoch);
            foreach $key (sort keys %list) {
               $val = ${$m}{$key};
               if ($key eq "METAR") {
                   @arr = split(/\s+/,$val);
                   $tmp = $arr[0].' '.$arr[1];
                   $epoch = str2time($tmp);
               }
               $key .= ' ' while (length($key) < $min);
               if ($key =~ /^pressure/) {
                   $tmp = $val * $HP2INCHES;
                   $tmp = int(($tmp * 100) + 0.5) / 100;
                   $msg .= "$key = $val hPa $tmp inHg\n";
               } elsif ($key =~ /^TEMP_C\s*/) {
                   $tmp = celcius_to_fahrenheight($val);
                   $msg .= "$key = $val C $tmp F\n";
               } elsif ($key =~ /^TEMP_F\s*/) {
                   $tmp = fahrenheight_to_celcius($val);
                   $msg .= "$key = $val F $tmp C\n";
               } elsif ($key =~ /^WIND_KTS\b/) {
                   $tmp = $val * $KNOT2MPH;
                   $tmp = int(($tmp * 10) + 0.5) / 10;
                   $msg .= "$key = $val kt $tmp mph\n";
               } elsif ($key =~ /^WIND_MPH\b/) {
                   $tmp = $val * $MPH2KNOT;
                   $tmp = int(($tmp * 10) + 0.5) / 10;
                   $msg .= "$key = $val mph $tmp kt\n";
               } else {
                   $msg .= "$key = $val\n";
               }
            }
            if (length($out_file)) {
                write2file($msg,$out_file);
                prt("Results written to $out_file\n");
            } else {
                prt($msg);
                prt("Results written to stdout since no -o out_file given\n");
            }
            if ($epoch) {
                my $tm = time();
                my $diff = $tm - $epoch;
                prt("Age: ");
                prt("Metar epoch $epoch, now $tm, diff $diff ") if (VERB5());
                prt(" Appears ".secs_HHMMSS($diff)." old\n");
            }

        }
    }
}

#########################################
### MAIN ###
##prt(str2time("02/25/2011 11:50AM")."\n");
##pgm_exit(1,"TEMP EXIT");
parse_args(@ARGV);
process_in_list();
pgm_exit(0,"");
########################################
sub give_help {
    prt("$pgmname: version $vers\n");
    prt("Usage: $pgmname [options] ICAO [ICAO2 [ICAO3]]\n");
    prt("Options:\n");
    prt(" --help (-h or -?) = This help, and exit 0.\n");
    prt(" --verb[n]     (-v) = Bump [or set] verbosity. def=$verbosity\n");
    prt(" --load        (-l) = Load LOG at end. ($outfile)\n");
    prt(" --out <file>  (-o) = Write output to this file.\n");
    prt(" --new         (-n) = Fetch 'new' metar even if an existing file.\n");
    prt(" If no existing metar file, or -n specified, will fetch the metar\n");
    prt(" from : $METARBASE\n");
    prt(" THe metar string is decoded using Get::METAR, and the items found displayed,\n");
    prt(" or written to a file is and -o file given.\n");

}

sub need_arg {
    my ($arg,@av) = @_;
    pgm_exit(1,"ERROR: [$arg] must have following argument!\n") if (!@av);
}

sub parse_args {
    my (@av) = @_;
    my ($arg,$sarg,$verb);
    $verb = VERB2();
    while (@av) {
        $arg = $av[0];
        if ($arg =~ /^-/) {
            $sarg = substr($arg,1);
            $sarg = substr($sarg,1) while ($sarg =~ /^-/);
            if (($sarg =~ /^h/i)||($sarg eq '?')) {
                give_help();
                pgm_exit(0,"Help exit(0)");
            } elsif ($sarg =~ /^v/) {
                if ($sarg =~ /^v.*(\d+)$/) {
                    $verbosity = $1;
                } else {
                    while ($sarg =~ /^v/) {
                        $verbosity++;
                        $sarg = substr($sarg,1);
                    }
                }
                $verb = VERB2();
                prt("Verbosity = $verbosity\n") if ($verb);
            } elsif ($sarg =~ /^l/) {
                if ($sarg =~ /^ll/) {
                    $load_log = 2;
                } else {
                    $load_log = 1;
                }
                prt("Set to load log at end. ($load_log)\n") if ($verb);
            } elsif ($sarg =~ /^n/) {
                $fetch_new = 1;
                prt("Set to fetch new METAR...\n") if ($verb);

            } elsif ($sarg =~ /^o/) {
                need_arg(@av);
                shift @av;
                $sarg = $av[0];
                $out_file = $sarg;
                prt("Set out file to [$out_file].\n") if ($verb);
            } else {
                pgm_exit(1,"ERROR: Invalid argument [$arg]! Try -?\n");
            }
        } else {
            $in_file = uc($arg);
            push(@ICAO_LIST,$in_file);
            prt("Set input to [$in_file]\n") if ($verb);
        }
        shift @av;
    }
    if ($debug_on) {
        prtw("WARNING: DEBUG is ON!\n");
        if (length($in_file) ==  0) {
            $in_file = uc($def_file);
            push(@ICAO_LIST,$in_file);
            prt("Set DEFAULT input to [$in_file]\n");
        }
    }

    if (length($in_file) ==  0) {
        pgm_exit(1,"ERROR: No ICAO found in command!\n");
    }
}

# eof - geo_metar.pl

index -|- top

checked by tidy  Valid HTML 4.01 Transitional