#!/usr/bin/perl -w -I../perllib # report.cgi: # Display summary reports for FixMyStreet # And RSS feeds for those reports etc. # # Copyright (c) 2007 UK Citizens Online Democracy. All rights reserved. # Email: matthew@mysociety.org. WWW: http://www.mysociety.org # # $Id: reports.cgi,v 1.41 2009-12-08 11:13:30 louise Exp $ use strict; use Standard; use Encode; use POSIX qw(strcoll); use URI::Escape; use FixMyStreet::Alert; use mySociety::MaPit; use mySociety::Web qw(ent NewURL); use mySociety::VotingArea; sub main { my $q = shift; my $all = $q->param('all') || 0; my $rss = $q->param('rss') || ''; my $cobrand = Page::get_cobrand($q); # Look up council name, if given my $q_council = $q->param('council') || ''; my $base_url = Cobrand::base_url($cobrand); # Manual misspelling redirect if ($q_council =~ /^rhondda cynon taff$/i) { print $q->redirect($base_url . '/reports/Rhondda+Cynon+Taf'); return; } my ($one_council, $area_type, $area_name); if ($q_council =~ /^(\d\d)([a-z]{2})?([a-z]{2})?$/i) { my $va_info = mySociety::MaPit::call('area', uc $q_council); if ($va_info->{error}) { # Given a bad/old ONS code print $q->redirect($base_url . '/reports'); return; } $area_name = Page::short_name($va_info); if (length($q_council) == 6) { $va_info = mySociety::MaPit::call('area', $va_info->{parent_area}); $area_name = Page::short_name($va_info) . '/' . $area_name; } $rss = '/rss' if $rss; print $q->redirect($base_url . $rss . '/reports/' . $area_name); return; } elsif (mySociety::Config::get('COUNTRY') eq 'NO' && $q_council eq 'Oslo') { $one_council = mySociety::MaPit::call('area', 3); $area_type = $one_council->{type}; $area_name = $one_council->{name}; } elsif (mySociety::Config::get('COUNTRY') eq 'NO' && $q_council =~ /,/) { my ($kommune, $fylke) = split /\s*,\s*/, $q_council; my @area_types = Cobrand::area_types($cobrand); my $areas_k = mySociety::MaPit::call('areas', $kommune, type => \@area_types); my $areas_f = mySociety::MaPit::call('areas', $fylke, type => \@area_types); if (keys %$areas_f == 1) { ($fylke) = values %$areas_f; $kommune = decode_utf8($kommune); foreach (values %$areas_k) { if ($_->{name} eq $kommune && $_->{parent_area} == $fylke->{id}) { $one_council = $_; $area_type = $_->{type}; $area_name = $_->{name}; last; } } } if (!$one_council) { # Given a false council name print $q->redirect($base_url . '/reports'); return; } } elsif ($q_council =~ /\D/) { my @area_types = Cobrand::area_types($cobrand); my $areas = mySociety::MaPit::call('areas', $q_council, type => \@area_types, min_generation=>Cobrand::area_min_generation($cobrand) ); if (keys %$areas == 1) { ($one_council) = values %$areas; $area_type = $one_council->{type}; $area_name = $one_council->{name}; } else { foreach (keys %$areas) { if ($areas->{$_}->{name} =~ /^\Q$q_council\E (Borough|City|District|County) Council$/) { $one_council = $areas->{$_}; $area_type = $areas->{$_}->{type}; $area_name = $q_council; } } } if (!$one_council) { # Given a false council name print $q->redirect($base_url . '/reports'); return; } } elsif ($q_council =~ /^\d+$/) { my $va_info = mySociety::MaPit::call('area', $q_council); if ($va_info->{error}) { print $q->redirect($base_url . '/reports'); return; } print $q->redirect($base_url . '/reports/' . Page::short_name($va_info)); return; } $all = 0 unless $one_council; # Look up ward name, if given my $q_ward = $q->param('ward') || ''; my $ward; if ($one_council && $q_ward) { my $qw = mySociety::MaPit::call('areas', $q_ward, type => $mySociety::VotingArea::council_child_types, min_generation => Cobrand::area_min_generation($cobrand)); foreach my $id (sort keys %$qw) { if ($qw->{$id}->{parent_area} == $one_council->{id}) { $ward = $qw->{$id}; last; } } if (!$ward) { # Given a false ward name print $q->redirect($base_url . '/reports/' . Page::short_name($one_council)); return; } } # RSS - reports for sent reports, area for all problems in area if ($rss && $one_council) { my $url = Page::short_name($one_council); $url .= '/' . Page::short_name($ward) if $ward; if ($rss eq 'area' && $area_type ne 'DIS' && $area_type ne 'CTY') { # Two possibilites are the same for one-tier councils, so redirect one to the other print $q->redirect($base_url . '/rss/reports/' . $url); return; } my $type = 'council_problems'; # Problems sent to a council my (@params, %title_params); $title_params{COUNCIL} = $area_name; push @params, $one_council->{id} if $rss eq 'reports'; push @params, $ward ? $ward->{id} : $one_council->{id}; if ($ward && $rss eq 'reports') { $type = 'ward_problems'; # Problems sent to a council, restricted to a ward $title_params{WARD} = $q_ward; } elsif ($rss eq 'area') { $title_params{NAME} = $ward ? $q_ward : $q_council; $type = 'area_problems'; # Problems within an area } print $q->header( -type => 'application/xml; charset=utf-8' ); my $xsl = Cobrand::feed_xsl($cobrand); my $out = FixMyStreet::Alert::generate_rss($type, $xsl, "/$url", \@params, \%title_params, $cobrand, $q); $out =~ s/matthew.fixmystreet/emptyhomes.matthew.fixmystreet/g if $q->{site} eq 'emptyhomes'; print $out; return; } my $areas_info; if ($one_council) { $areas_info = mySociety::MaPit::call('areas', [ $one_council->{id}, $one_council->{parent_area} ]) if $one_council->{parent_area}; $areas_info = { $one_council->{id} => $one_council } unless $areas_info; } else { # Show all councils on main report page my @area_types = Cobrand::area_types($cobrand); $areas_info = mySociety::MaPit::call('areas', \@area_types, min_generation=>Cobrand::area_min_generation($cobrand) ); } my $problems = Problems::council_problems( $ward ? $ward->{id} : undef, $one_council ? $one_council->{id} : undef ); my (%fixed, %open); my $re_councils = join('|', keys %$areas_info); foreach my $row (@$problems) { if (!$row->{council}) { # Problem was not sent to any council, add to possible councils while ($row->{areas} =~ /,($re_councils)(?=,)/g) { add_row($row, 0, $1, \%fixed, \%open); } } else { # Add to councils it was sent to $row->{council} =~ s/\|.*$//; my @council = split /,/, $row->{council}; foreach (@council) { next if $one_council && $_ != $one_council->{id}; add_row($row, scalar @council, $_, \%fixed, \%open); } } } if (!$one_council) { print Page::header($q, title=>_('Summary reports'), expires=>'+1h'); print $q->p( _('This is a summary of all reports on this site; select a particular council to see the reports sent there.'), ' ', _('Greyed-out lines are councils that no longer exist.') ); my $c = 0; print '
' . _('Name') . ' | ' . _('New problems') . ' | ' . _('Older problems') . ' | '; if ($q->{site} ne 'emptyhomes') { print '' . _('Old problems, state unknown') . ' | ';
}
print '' . _('Recently fixed') . ' | ' . _('Older fixed') . ' |
---|---|---|---|---|---|
' . $areas_info->{$_}->{name}; if ($areas_info->{$_}->{parent_area} && $url =~ /,|%2C/) { print ', ' . $areas_info->{$areas_info->{$_}->{parent_area}}->{name}; } print ' | '; summary_cell(\@{$open{$_}{new}}); if ($q->{site} eq 'emptyhomes') { my $c = 0; $c += @{$open{$_}{older}} if $open{$_}{older}; $c += @{$open{$_}{unknown}} if $open{$_}{unknown}; summary_cell($c); } else { summary_cell(\@{$open{$_}{older}}); summary_cell(\@{$open{$_}{unknown}}); } summary_cell(\@{$fixed{$_}{new}}); summary_cell(\@{$fixed{$_}{old}}); print "