source: trunk/npemap.org.uk/cgi/get-postcodes.fcgi @ 47

Last change on this file since 47 was 47, checked in by Dominic Hargreaves, 15 years ago

Use a config file for the DB parameters

  • Property svn:executable set to *
File size: 2.9 KB
Line 
1#!/usr/bin/perl
2
3use strict;
4use warnings;
5
6use DBI;
7use CGI::Fast qw/:standard -debug/;
8use JSON;
9
10use vars qw($dbname $dbhost $dbuser $dbpass);
11
12sub print_err;
13sub setup_dbh;
14
15# Read in database config
16my $config = 'npemap.conf';
17do $config or die "Can't read $config!\n";
18
19
20# Set up database handler to try and make sure it's ready for the first
21# request
22# No point in handling errors here since they'll get handled by the request
23# handler
24my $dbh;
25setup_dbh();
26
27
28my @fields = qw(mineasting minnorthing maxeasting maxnorthing);
29my $max_distance = 50000; # in metres
30
31my $cgi;
32# Process incoming requests
33REQUEST: while ($cgi = new CGI::Fast) {
34
35    # In case the database went away, make sure we have a connection
36    unless (setup_dbh()) {
37        print_err('Error setting up database connection');
38        next REQUEST;
39    }
40
41    # Input validation
42    foreach my $field (@fields) {
43        unless (defined $cgi->param($field)) {
44            print_err ("Parameter '$field' missing");
45            next REQUEST;
46        }
47    }
48
49    # Are the Eastings in a valid range?
50    foreach (qw(mineasting maxeasting)) {
51        if (($cgi->param($_) > 700000) or
52            ($cgi->param($_) < 0)) {
53            print_err ("Parameter '$_' must be an integer between 0 and 700,000");
54            next REQUEST;
55        }
56    }
57
58    # Are the Northings in a valid range?
59    foreach (qw(minnorthing maxnorthing)) {
60        if (($cgi->param($_) > 1300000) or
61            ($cgi->param($_) < 0)) {
62            print_err("Parameter '$_' must be an integer between 0 and 1,300,000");
63            next REQUEST;
64        }
65    }
66   
67    # Is the box too big?
68    if (($cgi->param('maxeasting') - $cgi->param('mineasting') > $max_distance) or ($cgi->param('maxnorthing') - $cgi->param('minnorthing') > $max_distance)) {
69        print_err("The requested box is too large");
70    }
71
72    my $sth = $dbh->prepare("SELECT outward || ' ' || inward AS postcode, easting, northing FROM postcodes WHERE easting >= ? AND easting <= ? AND northing >= ? AND northing <= ?");
73    if ($sth->execute($cgi->param('mineasting'), $cgi->param('maxeasting'), $cgi->param('minnorthing'), $cgi->param('maxnorthing'))) {
74        my $hr = $sth->fetchall_hashref('postcode');
75        print "Content-type: text/javascript\n\n";
76
77        foreach my $key (keys %$hr) {
78            my $hash = $$hr{$key};
79            print "addMarker('$$hash{postcode}', $$hash{easting}, $$hash{northing});\n";
80        }
81        #print objToJson($hr) . "\n";
82    } else {
83        print_err("Database error retrieving data");
84    }
85
86}
87
88# No more requests to serve, so tidy up
89$dbh->disconnect;
90
91# Helper routines
92sub print_err($) {
93    my $err = shift;
94    my $obj = { 'error' => $err };
95    print "Content-type: text/x-json\n\n";
96    print objToJson($obj) . "\n";
97}
98
99sub setup_dbh {
100    # $dbh is global
101    my $data_source = "dbi:Pg:dbname=$dbname";
102    $data_source .= ";host=$dbhost" if $dbhost;
103    return $dbh = DBI->connect_cached($data_source, $dbuser, $dbpass);
104}
Note: See TracBrowser for help on using the repository browser.