#!/usr/bin/perl -w
# InSHIT parser: exports data to CSV file

# Iain Tatch <iain@deepsea.force9.co.uk> Nov-2001
# This is public domain software: do with it as you wish.

use strict;
use LWP::UserAgent;
use HTTP::Request::Common;

my $VERSION = '1.1';

### Configurable stuff ###

my ($username, $password) = ('', '');
my $baseurl = 'http://www.quacky.co.uk/~ixion/cgi-bin/inshit/edit.pl';
my $outfile = 'inshit.csv';
# Set the following flag if you want to use a local copy of InSHIT rather than
# grabbing it on the fly from the server, and set $localfile as appropriate
my $uselocalnotremote = 1;
my $localfile = '/usr/home/iain/stuff/inshit.txt';
my $localfile = 'C:\WinNT\Profiles\iain\Personal\inshit.txt';

# Output file will be CSV format, columns:
# (1) Region, (2) Town, (3) Name, (4) Day Phone, (5) Home Phone,
# (6) Mobile Phone, (7) Email, (8) Tools Rating, (9) Mech Rating,
# (10) Tool-type Code, (11) Comments

### Main functionality ###

my $list;
if ( $uselocalnotremote ) {
  open (IN, "<$localfile") or die "Unable to read local copy of InSHIT: $!";
  while (<IN>) {
    $list .= $_;
  }
  close IN or warn "Problems closing local InSHIT file; will attempt to continue.";
} else {

  $username ||= shift;
  $password ||= shift;

  die "You need to specify username/password, either on the command line or in the file\n"
      unless $username && $password;

  my ($ua, $res);

  # Attempt to connect to quacky using LWP
  $ua = LWP::UserAgent->new;
  $ua->agent("ispe-$VERSION.$^O/Perl-$]");

  print "Attempting to log you in ...\n";
  $res = $ua->request(POST $baseurl, [ login=>$username, pword=>$password ]);
  $res->is_success or die "Couldn't complete user login request to server: $!";

  # Parse this to get the magic numbers we'll need to acquire a full InSHIT list
  my ($id, $key) = $res->content =~ /NAME="id" VALUE="(\d+)?".*NAME="key" VALUE="(.+?)"/;

  die "Unable to log you in (maybe wrong username/password)" unless $id && $key;

  print " OK\nRetrieving the InSHIT list ...";
  $res = $ua->request(POST $baseurl, [ id=>$id, key=>$key, 'Show Me The InSHIT List'=>'Show Me The InSHIT List' ]);
  $res->is_success or die "Couldn't complete list request to server: $!";

  $list = $res->content;

}

print " OK\nParsing ...\n";
$list =~ s/^.*<PRE>(.*)<\/PRE>.*$/$1/msg;

open(OUT, ">$outfile") or die "Unable to open output file: $!";
# Initialise CSV file with column headings
print OUT qq[Region,Town,Contact,Day Phone,Home Phone,Mobile,Email,Tool Skill,Tool Type,Mechanical Skill,Comments\n];

my %record;
for (split(/\n/, $list)) {
  chomp;
  # Skip over any blank lines
  next if /^\s*$/;
  # If we find a new region store the details
  if (/^(\w.+)$/) {
    writeout( \%record );
    %record = ( region=>$1, comments=>'' );
    next;
  }
  # If we find a town store the details
  if (/^\s{2}(\w.+)$/) {
    writeout( \%record );
    @record{'town', 'comments'} = ($1, '');
    next;
  }
  # If we find personal details, store them
  if (/^\s{7}(.*)\s{2}Day:\s/) {
    $record{name} = $1;
    /Day:\s(.*)\sMob/  && ($record{day}  = $1);
    /Mob:\s(.*)\sHome/ && ($record{home} = $1);
    /Home:\s(.*)$/     && ($record{mob}  = $1);
    next;
  }
  # If we find skill details, store them
  if (/Tools=(\d+)\sType=(.)\sMech=(\d+)\s+(.*)$/) {
    @record{qw(tools type mech email)} = ($1, $2, $3, $4);
    next;
  }
  # If we find comments, store them.
  $record{comments} .= $1 if /^\t\s{3}(.*)$/;
}

close OUT;

print " OK\n\nYour InSHIT data should be in $outfile\n";

sub writeout {
  my $r = shift;
  return unless defined $r->{region} && defined $r->{town};
  # escape any double-quotes in the comments field
  $r->{comments} =~ s/"/""/g;
  print OUT qq["$r->{region}","$r->{town}","$r->{name}","$r->{day}",];
  print OUT qq["$r->{home}","$r->{mob}","$r->{email}",];
  print OUT qq[$r->{tools},$r->{mech},$r->{type},"$r->{comments}"\n];
}

__END__
