#!/usr/bin/perl

# Parse post office finder web pages
# Copyright (C) 2008  Edward Betts
# 
# 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., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.

use strict;
use warnings;
use Data::Dump 'dump';
use JSON::XS;
use File::Slurp;
binmode STDOUT, ':utf8';

use HTML::TableExtract;

my %seen;

# name is not unique
# postcode is not unique

my $indent = JSON::XS->new->indent(1)->space_after(1);
my $no_indent = JSON::XS->new;

for my $filename (<pages/*>) {
    my $te = HTML::TableExtract->new(keep_html => 1);
    $te->parse_file($filename);
    $te->table(5, 0) or next;

    my $i = address($te->table(5, 0));
    my $this = join (", ", map { s/&amp;/&/g; $_ } $i->{name}, @{$i->{address}});
    $seen{$this} and next;
    my $j = $indent->encode($i);
    $j =~ s/\]\s*\}$/\],\n/sm;
    my $when = when($te->table(4, 1));
    my $when_json = join ",\n", map { $_ = $no_indent->encode($_); s/,/, /g; "      $_" } @$when;
    $seen{$this} = qq($j   "when": [\n$when_json\n   ]\n});
}

print scalar (keys %seen), "\n";

my @postoffice = map $seen{$_}, sort { $a cmp $b } keys %seen;
write_file('postoffices.json', "[\n", join(",\n", @postoffice), "\n]\n");

sub address { 
    my @rows = shift->rows;
    my $name = (shift @rows)->[0];
    $name =~ s/^\s*//g;
    $name =~ s/\s*$//g;
    return {
        name => strip_p($name),
        address => [map { @$_ == 1 or die; strip_p($_->[0]) } @rows],
    }
}

sub when {
    my @rows = shift->rows;
    (shift @rows)->[0] eq '<b>Day</b>' or die;
    foreach (@rows) {
        $_->[0] =~ s/&nbsp;$//;
        $_->[0] = ucfirst lc $_->[0];
        splice @$_, 3, 1;
    }
    return \@rows;
}

sub strip_p {
    my $str = shift;
    $str =~ m{<p>(.*)</p>} or die;
    return $1;
}
