X-Git-Url: https://git.exim.org/buildfarm-server.git/blobdiff_plain/684f5456cad92a4690fa4e67cb40ea8d2cd4d0dc..aedede4030eba1aea92af8cacd0f09dc8ec26169:/cgi-bin/show_log.pl diff --git a/cgi-bin/show_log.pl b/cgi-bin/show_log.pl index b462cc7..7fea634 100755 --- a/cgi-bin/show_log.pl +++ b/cgi-bin/show_log.pl @@ -1,11 +1,20 @@ #!/usr/bin/perl +=comment + +Copyright (c) 2003-2010, Andrew Dunstan + +See accompanying License file for license details + +=cut + use strict; use DBI; use Template; use CGI; -use vars qw($dbhost $dbname $dbuser $dbpass $dbport $template_dir @log_file_names); +use vars qw($dbhost $dbname $dbuser $dbpass $dbport + $template_dir @log_file_names $local_git_clone); require "$ENV{BFConfDir}/BuildFarmWeb.pl"; @@ -28,48 +37,89 @@ my $log = ""; my $conf = ""; my ($stage,$changed_this_run,$changed_since_success,$sysinfo,$branch,$scmurl); my $scm; +my ($git_head_ref, $last_build_git_ref, $last_success_git_ref); +my ($stage_times, $run_time); use vars qw($info_row); if ($system && $logdate) { - my $db = DBI->connect($dsn,$dbuser,$dbpass); + my $db = DBI->connect($dsn,$dbuser,$dbpass,{pg_expand_array => 0}); die $DBI::errstr unless $db; my $statement = q{ - select log,conf_sum,stage, changed_this_run, changed_since_success,branch, - log_archive_filenames, scm, scmurl + select log,conf_sum,stage, changed_this_run, changed_since_success, + branch, log_archive_filenames, scm, scmurl, git_head_ref from build_status where sysname = ? and snapshot = ? }; + my $last_build_statement = q{ + select git_head_ref + from build_status + where sysname = ? and branch = ? and snapshot = + (select max(snapshot) + from build_status + where sysname = ? and branch = ? and snapshot < ?) + }; + my $last_success_statement = q{ + select git_head_ref + from build_status + where sysname = ? and branch = ? and snapshot = + (select max(snapshot) + from build_status + where sysname = ? and branch = ? and snapshot < ? and stage = 'OK') + }; my $sth=$db->prepare($statement); $sth->execute($system,$logdate); my $row=$sth->fetchrow_arrayref; + $branch = $row->[5]; + $git_head_ref = $row->[9]; + $sth->finish; + my $last_build_row; + if ($git_head_ref) + { + $last_build_row = + $db->selectrow_hashref($last_build_statement,undef, + $system, $branch,$system,$branch,$logdate); + $last_build_git_ref = $last_build_row->{git_head_ref} + if $last_build_row; + + } + my $last_success_row; + if (ref $last_build_row && $last_build_row->{stage} ne 'OK') + { + $last_success_row = + $db->selectrow_hashref($last_success_statement,undef, + $system,$branch,$system,$branch,$logdate); + $last_success_git_ref = $last_success_row->{git_head_ref} + if $last_success_row; + } $log=$row->[0]; $conf=$row->[1] || "not recorded" ; $stage=$row->[2] || "unknown"; $changed_this_run = $row->[3]; $changed_since_success = $row->[4]; - $branch = $row->[5]; my $log_file_names = $row->[6]; $scm = $row->[7]; $scm ||= 'cvs'; # legacy scripts $scmurl = $row->[8]; + $scmurl = undef unless $scmurl =~ /^http/; # slight sanity check + $scmurl = 'http://git.postgresql.org/gitweb?p=postgresql.git;a=commit;h=' + if ($scmurl eq 'http://git.postgresql.org/git/postgresql.git'); $log_file_names =~ s/^\{(.*)\}$/$1/; @log_file_names=split(',',$log_file_names) if $log_file_names; - $sth->finish; $statement = q{ select operating_system, os_version, compiler, compiler_version, architecture, - replace(owner_email,'\@',' [ a t ] ') as owner_email, + replace(owner_email,E'\@',' [ a t ] ') as owner_email, sys_notes_ts::date AS sys_notes_date, sys_notes from buildsystems where status = 'approved' @@ -79,24 +129,45 @@ if ($system && $logdate) $sth=$db->prepare($statement); $sth->execute($system); $info_row=$sth->fetchrow_hashref; - # $sysinfo = join(" ",@$row); + + my $latest_personality = $db->selectrow_arrayref(q{ + select os_version, compiler_version + from personality + where effective_date < ? + and name = ? + order by effective_date desc limit 1 + }, undef, $logdate, $system); + if ($latest_personality) + { + $info_row->{os_version} = $latest_personality->[0]; + $info_row->{compiler_version} = $latest_personality->[1]; + } $sth->finish; + my $stage_times_query = q{ + select log_stage, stage_duration + from build_status_log + where sysname = ? and snapshot = ? + }; + $stage_times = + $db->selectall_hashref($stage_times_query,'log_stage',undef, + $system,$logdate); + $stage_times_query = q{ + select sum(stage_duration) + from build_status_log + where sysname = ? and snapshot = ? + }; + ($run_time) = $db->selectrow_array($stage_times_query,undef, + $system,$logdate); $db->disconnect; } -foreach my $chgd ($changed_this_run,$changed_since_success) -{ - my $cvsurl = 'http://anoncvs.postgresql.org/cvsweb.cgi'; - my $giturl = $scmurl || 'http://git.postgresql.org/gitweb?p=postgresql.git;a=commit;h='; - my @lines = split(/!/,$chgd); - my $changed_rows = []; - foreach (@lines) - { - next if ($scm eq 'cvs' and ! m!^(pgsql|master|REL\d_\d_STABLE)/!); - push(@$changed_rows,[$1,$3]) if (m!(^\S+)(\s+)(\S+)!); - } - $chgd = $changed_rows; -} +my ($changed_this_run_logs, $changed_since_success_logs); +($changed_this_run, $changed_this_run_logs) = + process_changed($changed_this_run, + $git_head_ref,$last_build_git_ref); +($changed_since_success, $changed_since_success_logs) = + process_changed($changed_since_success, + $last_build_git_ref,$last_success_git_ref); $conf =~ s/\@/ [ a t ] /g; @@ -109,13 +180,64 @@ $template->process('log.tt', system => $system, branch => $branch, stage => $stage, + stage_times => $stage_times, + run_time => $run_time, urldt => $logdate, log_file_names => \@log_file_names, conf => $conf, log => $log, changed_this_run => $changed_this_run, changed_since_success => $changed_since_success, + changed_this_run_logs => $changed_this_run_logs, + changed_since_success_logs => $changed_since_success_logs, info_row => $info_row, + git_head_ref => $git_head_ref, + last_build_git_ref => $last_build_git_ref, + last_success_git_ref => $last_success_git_ref, }); +exit; + +########################################################## + +sub process_changed +{ + + my $chgd = shift; + my $git_to = shift; + my $git_from = shift; + + my @lines = split(/!/,$chgd); + my @changed_rows; + my %commits; + my @commit_logs; + my $gitcmd = "TZ=UTC GIT_DIR=$local_git_clone git log --date=local"; + foreach (@lines) + { + next if ($scm eq 'cvs' and ! m!^(pgsql|master|REL\d_\d_STABLE)/!); + push(@changed_rows,[$1,$3]) if (m!(^\S+)(\s+)(\S+)!); + $commits{$3} = 1 if $scm eq 'git'; + } + if ($git_from && $git_to) + { + my $format = 'commit %h %cd UTC%w(160,2,2)%s'; + my $gitlog = `$gitcmd --pretty=format:"$format" $git_from..$git_to 2>&1`; + @commit_logs = split(/(?=^commit)/m,$gitlog) + } + else + { + # normally we expect to have the git refs. this is just a fallback. + my $format = 'epoch: %at%ncommit %h %cd UTC%w(160,2,2)%s'; + foreach my $commit ( keys %commits ) + { + my $commitlog = + `$gitcmd -n 1 --pretty=format:"$format" $commit 2>&1`; + push(@commit_logs,$commitlog); + } + @commit_logs = reverse (sort @commit_logs); + s/epoch:.*\n// for (@commit_logs); + } + return (\@changed_rows,\@commit_logs); +} +