From c6e881d0814e9a2527bd61a3f863e12aaa5abf22 Mon Sep 17 00:00:00 2001 From: "tara%tequilarista.org" <> Date: Tue, 31 Oct 2000 07:02:41 +0000 Subject: Landing Gerv and Adam's changes for bug #6682 --- reports.cgi | 1160 +++++++++++++++++++++++++++++++---------------------------- 1 file changed, 607 insertions(+), 553 deletions(-) (limited to 'reports.cgi') diff --git a/reports.cgi b/reports.cgi index b48ad7133..68a00e6f0 100755 --- a/reports.cgi +++ b/reports.cgi @@ -28,19 +28,28 @@ # Joe Robins , # If using the usebuggroups parameter, users shouldn't be able to see # reports for products they don't have access to. +# Gervase Markham and Adam Spiers +# Added ability to chart any combination of resolutions/statuses. +# Derive the choice of resolutions/statuses from the -All- data file +# Removed hardcoded order of resolutions/statuses when reading from +# daily stats file, so now works independently of collectstats.pl +# version +# Added image caching by date and datasets use diagnostics; use strict; + use GD; eval "use Chart::Lines"; require "CGI.pl"; -require "globals.pl"; +use vars qw(%FORM); # globals from CGI.pl -use vars @::legal_product; +require "globals.pl"; +use vars qw(@legal_product); # globals from er, globals.pl my $dir = "data/mining"; -my $week = 60 * 60 * 24 * 7; + my @status = qw (NEW ASSIGNED REOPENED); my %bugsperperson; @@ -48,12 +57,12 @@ my %bugsperperson; # functions differently than the value passed in my %reports = - ( - "most_doomed" => \&most_doomed, - "most_doomed_for_milestone" => \&most_doomed_for_milestone, - "most_recently_doomed" => \&most_recently_doomed, - "show_chart" => \&show_chart, - ); + ( + "most_doomed" => \&most_doomed, + "most_doomed_for_milestone" => \&most_doomed_for_milestone, + "most_recently_doomed" => \&most_recently_doomed, + "show_chart" => \&show_chart, + ); # If we're using bug groups for products, we should apply those restrictions # to viewing reports, as well. Time to check the login in that case. @@ -66,14 +75,12 @@ print "Content-type: text/html\n"; print "Content-disposition: inline; filename=bugzilla_report.html\n\n"; # If we're here for the first time, give a banner. Else respect the banner flag. -if ( (!defined $::FORM{'product'}) || ($::FORM{'banner'}) ) - { - PutHeader ("Bug Reports") - } -else - { - print("Bug Reports"); - } +if ( (!defined $FORM{'product'}) || ($FORM{'banner'}) ) { + PutHeader ("Bug Reports") +} +else { + print("Bug Reports"); +} GetVersionTable(); @@ -81,84 +88,79 @@ GetVersionTable(); # We only want those products that the user has permissions for. my @myproducts; if(Param("usebuggroups")) { - push( @myproducts, "-All-"); - foreach my $this_product (@::legal_product) { - if(GroupExists($this_product) && !UserInGroup($this_product)) { - next; - } else { - push( @myproducts, $this_product ) + push( @myproducts, "-All-"); + foreach my $this_product (@legal_product) { + if(GroupExists($this_product) && !UserInGroup($this_product)) { + next; + } else { + push( @myproducts, $this_product ) + } } - } } else { - push( @myproducts, "-All-", @::legal_product ); + push( @myproducts, "-All-", @legal_product ); } -$::FORM{'output'} = $::FORM{'output'} || "most_doomed"; # a reasonable default - -if (! defined $::FORM{'product'}) - { - &choose_product; - } -else - { - # If usebuggroups is on, we don't want people to be able to view - # reports for products they don't have permissions for... - if(Param("usebuggroups") && - GroupExists($::FORM{'product'}) && - !UserInGroup($::FORM{'product'})) { - print "

Permission denied.

\n"; - print "Sorry; you do not have the permissions necessary to view\n"; - print "reports for this product.\n"; - print "

\n"; - PutFooter(); - exit; - } +$FORM{'output'} ||= "most_doomed"; # a reasonable default + +if (! defined $FORM{'product'}) { + &choose_product; +} +else { + # If usebuggroups is on, we don't want people to be able to view + # reports for products they don't have permissions for... + if(Param("usebuggroups") && + GroupExists($FORM{'product'}) && + !UserInGroup($FORM{'product'})) + { + print "

Permission denied.

\n"; + print "Sorry; you do not have the permissions necessary to view\n"; + print "reports for this product.\n"; + print "

\n"; + PutFooter(); + exit; + } - # we want to be careful about what subroutines - # can be called from outside. modify %reports - # accordingly when a new report type is added - - if (! exists $reports{$::FORM{'output'}}) - { - $::FORM{'output'} = "most_doomed"; # a reasonable default - } - - my $f = $reports{$::FORM{'output'}}; - - if (! defined $f) - { - print "start over, your form data was all messed up.

\n"; - foreach (keys %::FORM) - { - print "$_ : " . - ($::FORM{$_} ? $::FORM{$_} : "undef") . "
\n"; - } - PutFooter() if $::FORM{banner}; - exit; - } - - &{$f}; - } + # we want to be careful about what subroutines + # can be called from outside. modify %reports + # accordingly when a new report type is added + + if (! exists $reports{$FORM{'output'}}) { + $FORM{'output'} = "most_doomed"; # a reasonable default + } + + my $f = $reports{$FORM{'output'}}; + + if (! defined $f) { + print "start over, your form data was all messed up.

\n"; + foreach (keys %::FORM) { + print "$_ : " . + ($FORM{$_} ? $FORM{$_} : "undef") . "
\n"; + } + PutFooter() if $FORM{banner}; + exit; + } + + &{$f}; +} print < FIN -PutFooter() if $::FORM{banner}; +PutFooter() if $FORM{banner}; ################################## # user came in with no form data # ################################## -sub choose_product - { - my $product_popup = make_options (\@myproducts, $myproducts[0]); - my $charts = defined $Chart::Lines::VERSION && -d $dir ? "

Welcome to the Bugzilla Query Kitchen

@@ -177,25 +179,59 @@ $product_popup +FIN + + my @datasets = (); + + my $datafile = daily_stats_filename('-All-'); + if (! open(DATA, "$dir/$datafile")) { + die_politely("Couldn't read daily statistics file"); + } + + while () { + if (/^# fields?: (.+)\s*$/) { + @datasets = grep ! /date/i, (split /\|/, $1); + last; + } + } + + close(DATA); + + my %default_sel = map { $_ => 1 } + qw/UNCONFIRMED NEW ASSIGNED REOPENED/; + foreach my $dataset (@datasets) { + my $sel = $default_sel{$dataset} ? ' selected' : ''; + print qq{\n}; + } + + print < + + + Switches:  Links to Bugs
 Banner
FIN - if (Param('usequip')) { - print " Quip
"; - } else { - print ""; - } - print < Quip
"; + } else { + print ""; + } + print < @@ -209,30 +245,29 @@ FIN FIN #Add this above to get a control for showing the SQL query: # Show SQL
- PutFooter(); - } + PutFooter(); +} -sub most_doomed - { - my $when = localtime (time); +sub most_doomed { + my $when = localtime (time); - print <

-Bug Report for $::FORM{'product'} +Bug Report for $FORM{'product'}

$when

FIN # Build up $query string - my $query; - $query = <$query

\n" - unless (! exists $::FORM{'showsql'}); - - SendSQL ($query); - - my $c = 0; - - my $quip = "Summary"; - my $bugs_count = 0; - my $bugs_new_this_week = 0; - my $bugs_reopened = 0; - my %bugs_owners; - my %bugs_summary; - my %bugs_status; - my %bugs_totals; - my %bugs_lookup; - - ############################# - # suck contents of database # - ############################# - - while (my ($bid, $a, $sev, $st, $prod, $who, $rep, $ts) = FetchSQLData()) - { - next if (exists $bugs_lookup{$bid}); - - $bugs_lookup{$bid} ++; - $bugs_owners{$who} ++; - $bugs_new_this_week ++ if (time - $ts <= $week); - $bugs_status{$st} ++; - $bugs_count ++; - - push @{$bugs_summary{$who}{$st}}, $bid; - - $bugs_totals{$who}{$st} ++; - } - - if ($::FORM{'quip'}) - { - if (open (COMMENTS, ") - { - push @cdata, $_; - } - close COMMENTS; - $quip = "" . $cdata[int(rand($#cdata + 1))] . ""; - } - } - - ######################### - # start painting report # - ######################### - - $bugs_status{'NEW'} ||= '0'; - $bugs_status{'ASSIGNED'} ||= '0'; - $bugs_status{'REOPENED'} ||= '0'; - print <$query

\n" + unless (! exists $FORM{'showsql'}); + + SendSQL ($query); + + my $c = 0; + + my $quip = "Summary"; + my $bugs_count = 0; + my $bugs_new_this_week = 0; + my $bugs_reopened = 0; + my %bugs_owners; + my %bugs_summary; + my %bugs_status; + my %bugs_totals; + my %bugs_lookup; + + ############################# + # suck contents of database # + ############################# + + my $week = 60 * 60 * 24 * 7; + while (my ($bid, $a, $sev, $st, $prod, $who, $rep, $ts) = FetchSQLData()) { + next if (exists $bugs_lookup{$bid}); + + $bugs_lookup{$bid} ++; + $bugs_owners{$who} ++; + $bugs_new_this_week ++ if (time - $ts <= $week); + $bugs_status{$st} ++; + $bugs_count ++; + + push @{$bugs_summary{$who}{$st}}, $bid; + + $bugs_totals{$who}{$st} ++; + } + + if ($FORM{'quip'}) { + if (open (COMMENTS, ") { + push @cdata, $_; + } + close COMMENTS; + $quip = "" . $cdata[int(rand($#cdata + 1))] . ""; + } + } + + ######################### + # start painting report # + ######################### + + $bugs_status{'NEW'} ||= '0'; + $bugs_status{'ASSIGNED'} ||= '0'; + $bugs_status{'REOPENED'} ||= '0'; + print <$quip @@ -345,14 +377,13 @@ FIN

FIN - if ($bugs_count == 0) - { - print "No bugs found!\n"; - PutFooter() if $::FORM{banner}; - exit; - } - - print <Bug Count by Engineer

@@ -364,39 +395,37 @@ FIN FIN - foreach my $who (sort keys %bugs_summary) - { - my $bugz = 0; - print < FIN - - foreach my $st (@status) - { - $bugs_totals{$who}{$st} += 0; - print <$bugs_totals{$who}{$st} FIN - $bugz += $#{$bugs_summary{$who}{$st}} + 1; - } - - print <$bugz FIN - } - - print <

FIN - ############################### - # individual bugs by engineer # - ############################### + ############################### + # individual bugs by engineer # + ############################### - print <Individual Bugs by Engineer

$who
@@ -407,426 +436,451 @@ FIN FIN - foreach my $who (sort keys %bugs_summary) - { - print < FIN - foreach my $st (@status) - { - my @l; - - foreach (sort { $a <=> $b } @{$bugs_summary{$who}{$st}}) - { - if ($::FORM{'links'}) - { - push @l, "$_\n"; - } - else - { - push @l, $_; - } - } - - my $bugz = join ' ', @l; - $bugz = " " unless ($bugz); - - print < $b } @{$bugs_summary{$who}{$st}}) { + if ($FORM{'links'}) { + push @l, "$_\n"; + } + else { + push @l, $_; + } + } + + my $bugz = join ' ', @l; + $bugz = " " unless ($bugz); + + print <$bugz FIN - } + } - print < FIN - } + } - print <

FIN - } +} -sub is_legal_product - { - my $product = shift; - return grep { $_ eq $product} @myproducts; - } +sub is_legal_product { + my $product = shift; + return grep { $_ eq $product} @myproducts; +} -sub show_chart - { - my $when = localtime (time); +sub daily_stats_filename { + my ($prodname) = @_; + $prodname =~ s/\//-/gs; + return $prodname; +} - if (! is_legal_product ($::FORM{'product'})) - { - &die_politely ("Unknown product: $::FORM{'product'}"); - } +sub show_chart { + if (! is_legal_product ($FORM{'product'})) { + &die_politely ("Unknown product: $FORM{'product'}"); + } + + if (! $FORM{datasets}) { + die_politely("You didn't select any datasets to plot"); + } print < FIN - - my @dates; - my @open; my @assigned; my @reopened; - my @resolved; my @verified; my @closed; - - my $prodname = $::FORM{'product'}; - - $prodname =~ s/\//-/gs; - - my $testimg = Chart::Lines->new(2,2); - my $x = '$testimg->gif()'; - eval $x; - my $type = ($@ =~ /Can't locate object method/) ? "png" : "gif"; - - my $file = join '/', $dir, $prodname; - my $image = "$file.$type"; - my $url_image = $dir . "/" . url_quote($prodname) . ".$type"; - - if (! open FILE, $file) - { - &die_politely ("The tool which gathers bug counts has not been run yet."); - } - - while () - { - chomp; - next if ($_ =~ /^#/ or ! $_); - my ($date, $open, $assigned, $reopened, - $resolved, $verified, $closed) = split /\|/, $_; - my ($yy, $mm, $dd) = $date =~ /^\d{2}(\d{2})(\d{2})(\d{2})$/; - - push @dates, "$mm/$dd/$yy"; - push @open, $open; - push @assigned, $assigned; - push @reopened, $reopened; - push @resolved, $resolved; - push @verified, $verified; - push @closed, $closed; - } - - close FILE; - - if ($#dates < 1) - { - &die_politely ("We don't have enough data points to make a graph (yet)"); - } - - my $img = Chart::Lines->new (800, 600); - my @labels = qw (New Assigned Reopened Resolved Verified Closed); - my @when; - my $i = 0; - my @data; - - push @data, \@dates; - push @data, \@open; - push @data, \@assigned; - push @data, \@reopened; - push @data, \@resolved; - push @data, \@verified; - push @data, \@closed; - my $MAXTICKS = 20; # Try not to show any more x ticks than this. - my $skip = 1; - if (@dates > $MAXTICKS) { - $skip = int((@dates + $MAXTICKS - 1) / $MAXTICKS); - } - - my %settings = - ( - "title" => "Status Counts for $::FORM{'product'}", - "x_label" => "Dates", - "y_label" => "Bug Counts", - "legend_labels" => \@labels, - "skip_x_ticks" => $skip, - "y_grid_lines" => "true", - "grey_background" => "false" - ); - - $img->set (%settings); - - open IMAGE, ">$image" or die "$image: $!"; - $img->$type (*IMAGE, \@data); - close IMAGE; - - print <

FIN - } +} -sub die_politely - { - my $msg = shift; +sub chart_image_type { + # what chart type should we be generating? + my $testimg = Chart::Lines->new(2,2); + my $type = $testimg->can('gif') ? "gif" : "png"; + undef $testimg; + return $type; +} - print < 1 } split /:/, $FORM{datasets}; + + my %data = (); + while () { + chomp; + next unless $_; + if (/^#/) { + if (/^# fields?: (.*)\s*$/) { + @fields = split /\|/, $1; + &die_politely("`# fields: ' line didn't start with DATE, but with $fields[0]") + unless $fields[0] =~ /date/i; + push @labels, grep($datasets{$_}, @fields); + } + next; + } + + &die_politely("`# fields: ' line was not found before start of data") + unless @fields; + + my @line = split /\|/; + my $date = $line[0]; + my ($yy, $mm, $dd) = $date =~ /^\d{2}(\d{2})(\d{2})(\d{2})$/; + push @{$data{DATE}}, "$mm/$dd/$yy"; + + for my $i (1 .. $#fields) { + my $field = $fields[$i]; + if (! defined $line[$i] or $line[$i] eq '') { + # no data point given, don't plot (this will probably + # generate loads of Chart::Base warnings, but that's not + # our fault. + push @{$data{$field}}, undef; + } + else { + push @{$data{$field}}, $line[$i]; + } + } + } + + shift @labels; + + close FILE; + + if (! @{$data{DATE}}) { + &die_politely ("We don't have enough data points to make a graph (yet)"); + } + + my $img = Chart::Lines->new (800, 600); + my $i = 0; + + my $MAXTICKS = 20; # Try not to show any more x ticks than this. + my $skip = 1; + if (@{$data{DATE}} > $MAXTICKS) { + $skip = int((@{$data{DATE}} + $MAXTICKS - 1) / $MAXTICKS); + } + + my %settings = + ( + "title" => "Status Counts for $FORM{'product'}", + "x_label" => "Dates", + "y_label" => "Bug Counts", + "legend_labels" => \@labels, + "skip_x_ticks" => $skip, + "y_grid_lines" => "true", + "grey_background" => "false", + "colors" => { + # default dataset colours are too alike + dataset4 => [0, 0, 0], # black + }, + ); + + $img->set (%settings); + $img->$type($image_file, [ @data{('DATE', @labels)} ]); +} + +sub die_politely { + my $msg = shift; + + print <

$who
Sorry, but ...

-There is no graph available for $::FORM{'product'}

+There is no graph available for $FORM{'product'}

- $msg

-

FIN - - PutFooter() if $::FORM{banner}; - exit; - } + + PutFooter() if $FORM{banner}; + exit; +} sub bybugs { $bugsperperson{$a} <=> $bugsperperson{$b} - } +} -sub most_doomed_for_milestone - { - my $when = localtime (time); - my $ms = "M" . Param("curmilestone"); - my $quip = "Summary"; +sub most_doomed_for_milestone { + my $when = localtime (time); + my $ms = "M" . Param("curmilestone"); + my $quip = "Summary"; - print "

\n

"; - if( $::FORM{'product'} ne "-All-" ) { - print "Most Doomed for $ms ($::FORM{'product'})"; - } else { - print "Most Doomed for $ms"; - } - print "

\n$when

\n"; - - ######################### - # start painting report # - ######################### - - if ($::FORM{'quip'}) - { - if (open (COMMENTS, ") - { - push @cdata, $_; - } - close COMMENTS; - $quip = "" . $cdata[int(rand($#cdata + 1))] . ""; } - } + print "

\n

"; + if( $FORM{'product'} ne "-All-" ) { + print "Most Doomed for $ms ($FORM{'product'})"; + } else { + print "Most Doomed for $ms"; + } + print "

\n$when

\n"; + ######################### + # start painting report # + ######################### - # Build up $query string - my $query; - $query = "select distinct assigned_to from bugs where target_milestone=\"$ms\""; - if( $::FORM{'product'} ne "-All-" ) { - $query .= "and bugs.product=".SqlQuote($::FORM{'product'}); - } - $query .= <) { + push @cdata, $_; + } + close COMMENTS; + $quip = "" . $cdata[int(rand($#cdata + 1))] . ""; + } + } + + # Build up $query string + my $query; + $query = "select distinct assigned_to from bugs where target_milestone=\"$ms\""; + if ($FORM{'product'} ne "-All-" ) { + $query .= "and bugs.product=".SqlQuote($FORM{'product'}); + } + $query .= <\n"; - print "\n"; - print "$totalpeople engineers have $bugtotal $ms bugs and features.\n"; - print "\n"; - - while (@people) - { - $person = pop @people; - print "\n"; - SendSQL("select login_name from profiles where userid=$person"); - my $login_name= FetchSQLData(); - print("\n"); - print("$bugsperperson{$person} bugs and features"); - print(""); - print(" for \n"); - print(""); - print("$login_name"); - print("\n"); - print("\n"); - - $person = pop @people; - if ($person) { - SendSQL("select login_name from profiles where userid=$person"); - my $login_name= FetchSQLData(); - print("\n"); - print("$bugsperperson{$person} bugs and features"); - print(""); - print(" for \n"); - print(""); - print("$login_name"); - print("\n"); - print("\n\n"); - } - } - print "\n"; - + print "\n"; + print "\n"; + + while (@people) { + $person = pop @people; + print "\n\n"); } + } + print "
\n"; + print "$totalpeople engineers have $bugtotal $ms bugs and features.\n"; + print "
\n"; + SendSQL("select login_name from profiles where userid=$person"); + my $login_name= FetchSQLData(); + print("\n"); + print("$bugsperperson{$person} bugs and features"); + print(""); + print(" for \n"); + print(""); + print("$login_name"); + print("\n"); + print("\n"); + + $person = pop @people; + if ($person) { + SendSQL("select login_name from profiles where userid=$person"); + my $login_name= FetchSQLData(); + print("\n"); + print("$bugsperperson{$person} bugs and features"); + print(""); + print(" for \n"); + print(""); + print("$login_name"); + print("\n"); + print("
\n"; +} +sub most_recently_doomed { + my $when = localtime (time); + my $ms = "M" . Param("curmilestone"); + my $quip = "Summary"; + + print "

\n

"; + if( $FORM{'product'} ne "-All-" ) { + print "Most Recently Doomed ($FORM{'product'})"; + } else { + print "Most Recently Doomed"; + } + print "

\n$when

\n"; -sub most_recently_doomed - { - my $when = localtime (time); - my $ms = "M" . Param("curmilestone"); - my $quip = "Summary"; + ######################### + # start painting report # + ######################### - print "

\n

"; - if( $::FORM{'product'} ne "-All-" ) { - print "Most Recently Doomed ($::FORM{'product'})"; - } else { - print "Most Recently Doomed"; + if ($FORM{'quip'}) { + if (open (COMMENTS, ") { + push @cdata, $_; } - print "

\n$when

\n"; - - ######################### - # start painting report # - ######################### - - if ($::FORM{'quip'}) - { - if (open (COMMENTS, ") - { - push @cdata, $_; - } - close COMMENTS; - $quip = "" . $cdata[int(rand($#cdata + 1))] . ""; } - } + close COMMENTS; + $quip = "" . $cdata[int(rand($#cdata + 1))] . ""; + } + } - # Build up $query string - my $query; - $query = "select distinct assigned_to from bugs where bugs.bug_status='NEW' and target_milestone='' and bug_severity!='enhancement' and status_whiteboard='' and (product='Browser' or product='MailNews')"; - if( $::FORM{'product'} ne "-All-" ) { - $query .= "and bugs.product=".SqlQuote($::FORM{'product'}); - } + # Build up $query string + my $query = "select distinct assigned_to from bugs where bugs.bug_status='NEW' and target_milestone='' and bug_severity!='enhancement' and status_whiteboard='' and (product='Browser' or product='MailNews')"; + if ($FORM{'product'} ne "-All-" ) { + $query .= "and bugs.product=".SqlQuote($FORM{'product'}); + } # End build up $query string - SendSQL ($query); - my @people = (); - while (my ($person) = FetchSQLData()) - { - push @people, $person; - } + SendSQL ($query); + my @people = (); + while (my ($person) = FetchSQLData()) { + push @people, $person; + } - ############################# - # suck contents of database # - ############################# - my $person = ""; - my $bugtotal = 0; - foreach $person (@people) - { - my $query = "select count(bug_id) from bugs,profiles where bugs.bug_status='NEW' and userid=assigned_to and userid='$person' and target_milestone='' and bug_severity!='enhancement' and status_whiteboard='' and (product='Browser' or product='MailNews')"; - if( $::FORM{'product'} ne "-All-" ) { - $query .= "and bugs.product='$::FORM{'product'}'"; - } - SendSQL ($query); - my $bugcount = FetchSQLData(); - $bugsperperson{$person} = $bugcount; - $bugtotal += $bugcount; - } + ############################# + # suck contents of database # + ############################# + my $person = ""; + my $bugtotal = 0; + foreach $person (@people) { + my $query = "select count(bug_id) from bugs,profiles where bugs.bug_status='NEW' and userid=assigned_to and userid='$person' and target_milestone='' and bug_severity!='enhancement' and status_whiteboard='' and (product='Browser' or product='MailNews')"; + if( $FORM{'product'} ne "-All-" ) { + $query .= "and bugs.product='$FORM{'product'}'"; + } + SendSQL ($query); + my $bugcount = FetchSQLData(); + $bugsperperson{$person} = $bugcount; + $bugtotal += $bugcount; + } -# sort people by the number of bugs they have assigned to this milestone - @people = sort bybugs @people; - my $totalpeople = @people; - - if ($totalpeople > 20) { - splice @people, 0, $totalpeople-20; - } +# sort people by the number of bugs they have assigned to this milestone + @people = sort bybugs @people; + my $totalpeople = @people; + + if ($totalpeople > 20) { + splice @people, 0, $totalpeople-20; + } - print "\n"; - print "\n"; - - while (@people) - { - $person = pop @people; - print "\n\n"); - } - } - print "
\n"; - print "$totalpeople engineers have $bugtotal untouched new bugs.\n"; - if ($totalpeople > 20) { - print "These are the 20 most doomed."; - } - print "
\n"; - SendSQL("select login_name from profiles where userid=$person"); - my $login_name= FetchSQLData(); - print("\n"); - print("$bugsperperson{$person} bugs"); - print(""); - print(" for \n"); - print(""); - print("$login_name"); - print("\n"); - print("\n"); - - $person = pop @people; - if ($person) { - SendSQL("select login_name from profiles where userid=$person"); - my $login_name= FetchSQLData(); - print("\n"); - print("$bugsperperson{$person} bugs"); - print(""); - print(" for \n"); - print(""); - print("$login_name"); - print("\n"); - print("
\n"; - + print "\n"; + print "\n"; + + while (@people) { + $person = pop @people; + print "\n\n"); } + } + print "
\n"; + print "$totalpeople engineers have $bugtotal untouched new bugs.\n"; + if ($totalpeople > 20) { + print "These are the 20 most doomed."; + } + print "
\n"; + SendSQL("select login_name from profiles where userid=$person"); + my $login_name= FetchSQLData(); + print("\n"); + print("$bugsperperson{$person} bugs"); + print(""); + print(" for \n"); + print(""); + print("$login_name"); + print("\n"); + print("\n"); + + $person = pop @people; + if ($person) { + SendSQL("select login_name from profiles where userid=$person"); + my $login_name= FetchSQLData(); + print("\n"); + print("$bugsperperson{$person} bugs"); + print(""); + print(" for \n"); + print(""); + print("$login_name"); + print("\n"); + print("
\n"; + +} -- cgit v1.2.3-24-g4f1b